1*67e74705SXin Li //===--- CFG.cpp - Classes for representing and building CFGs----*- C++ -*-===//
2*67e74705SXin Li //
3*67e74705SXin Li // The LLVM Compiler Infrastructure
4*67e74705SXin Li //
5*67e74705SXin Li // This file is distributed under the University of Illinois Open Source
6*67e74705SXin Li // License. See LICENSE.TXT for details.
7*67e74705SXin Li //
8*67e74705SXin Li //===----------------------------------------------------------------------===//
9*67e74705SXin Li //
10*67e74705SXin Li // This file defines the CFG and CFGBuilder classes for representing and
11*67e74705SXin Li // building Control-Flow Graphs (CFGs) from ASTs.
12*67e74705SXin Li //
13*67e74705SXin Li //===----------------------------------------------------------------------===//
14*67e74705SXin Li
15*67e74705SXin Li #include "clang/Analysis/CFG.h"
16*67e74705SXin Li #include "clang/AST/ASTContext.h"
17*67e74705SXin Li #include "clang/AST/Attr.h"
18*67e74705SXin Li #include "clang/AST/CharUnits.h"
19*67e74705SXin Li #include "clang/AST/DeclCXX.h"
20*67e74705SXin Li #include "clang/AST/PrettyPrinter.h"
21*67e74705SXin Li #include "clang/AST/StmtVisitor.h"
22*67e74705SXin Li #include "clang/Basic/Builtins.h"
23*67e74705SXin Li #include "llvm/ADT/DenseMap.h"
24*67e74705SXin Li #include <memory>
25*67e74705SXin Li #include "llvm/ADT/SmallPtrSet.h"
26*67e74705SXin Li #include "llvm/Support/Allocator.h"
27*67e74705SXin Li #include "llvm/Support/Format.h"
28*67e74705SXin Li #include "llvm/Support/GraphWriter.h"
29*67e74705SXin Li #include "llvm/Support/SaveAndRestore.h"
30*67e74705SXin Li
31*67e74705SXin Li using namespace clang;
32*67e74705SXin Li
33*67e74705SXin Li namespace {
34*67e74705SXin Li
GetEndLoc(Decl * D)35*67e74705SXin Li static SourceLocation GetEndLoc(Decl *D) {
36*67e74705SXin Li if (VarDecl *VD = dyn_cast<VarDecl>(D))
37*67e74705SXin Li if (Expr *Ex = VD->getInit())
38*67e74705SXin Li return Ex->getSourceRange().getEnd();
39*67e74705SXin Li return D->getLocation();
40*67e74705SXin Li }
41*67e74705SXin Li
42*67e74705SXin Li /// Helper for tryNormalizeBinaryOperator. Attempts to extract an IntegerLiteral
43*67e74705SXin Li /// or EnumConstantDecl from the given Expr. If it fails, returns nullptr.
tryTransformToIntOrEnumConstant(const Expr * E)44*67e74705SXin Li const Expr *tryTransformToIntOrEnumConstant(const Expr *E) {
45*67e74705SXin Li E = E->IgnoreParens();
46*67e74705SXin Li if (isa<IntegerLiteral>(E))
47*67e74705SXin Li return E;
48*67e74705SXin Li if (auto *DR = dyn_cast<DeclRefExpr>(E->IgnoreParenImpCasts()))
49*67e74705SXin Li return isa<EnumConstantDecl>(DR->getDecl()) ? DR : nullptr;
50*67e74705SXin Li return nullptr;
51*67e74705SXin Li }
52*67e74705SXin Li
53*67e74705SXin Li /// Tries to interpret a binary operator into `Decl Op Expr` form, if Expr is
54*67e74705SXin Li /// an integer literal or an enum constant.
55*67e74705SXin Li ///
56*67e74705SXin Li /// If this fails, at least one of the returned DeclRefExpr or Expr will be
57*67e74705SXin Li /// null.
58*67e74705SXin Li static std::tuple<const DeclRefExpr *, BinaryOperatorKind, const Expr *>
tryNormalizeBinaryOperator(const BinaryOperator * B)59*67e74705SXin Li tryNormalizeBinaryOperator(const BinaryOperator *B) {
60*67e74705SXin Li BinaryOperatorKind Op = B->getOpcode();
61*67e74705SXin Li
62*67e74705SXin Li const Expr *MaybeDecl = B->getLHS();
63*67e74705SXin Li const Expr *Constant = tryTransformToIntOrEnumConstant(B->getRHS());
64*67e74705SXin Li // Expr looked like `0 == Foo` instead of `Foo == 0`
65*67e74705SXin Li if (Constant == nullptr) {
66*67e74705SXin Li // Flip the operator
67*67e74705SXin Li if (Op == BO_GT)
68*67e74705SXin Li Op = BO_LT;
69*67e74705SXin Li else if (Op == BO_GE)
70*67e74705SXin Li Op = BO_LE;
71*67e74705SXin Li else if (Op == BO_LT)
72*67e74705SXin Li Op = BO_GT;
73*67e74705SXin Li else if (Op == BO_LE)
74*67e74705SXin Li Op = BO_GE;
75*67e74705SXin Li
76*67e74705SXin Li MaybeDecl = B->getRHS();
77*67e74705SXin Li Constant = tryTransformToIntOrEnumConstant(B->getLHS());
78*67e74705SXin Li }
79*67e74705SXin Li
80*67e74705SXin Li auto *D = dyn_cast<DeclRefExpr>(MaybeDecl->IgnoreParenImpCasts());
81*67e74705SXin Li return std::make_tuple(D, Op, Constant);
82*67e74705SXin Li }
83*67e74705SXin Li
84*67e74705SXin Li /// For an expression `x == Foo && x == Bar`, this determines whether the
85*67e74705SXin Li /// `Foo` and `Bar` are either of the same enumeration type, or both integer
86*67e74705SXin Li /// literals.
87*67e74705SXin Li ///
88*67e74705SXin Li /// It's an error to pass this arguments that are not either IntegerLiterals
89*67e74705SXin Li /// or DeclRefExprs (that have decls of type EnumConstantDecl)
areExprTypesCompatible(const Expr * E1,const Expr * E2)90*67e74705SXin Li static bool areExprTypesCompatible(const Expr *E1, const Expr *E2) {
91*67e74705SXin Li // User intent isn't clear if they're mixing int literals with enum
92*67e74705SXin Li // constants.
93*67e74705SXin Li if (isa<IntegerLiteral>(E1) != isa<IntegerLiteral>(E2))
94*67e74705SXin Li return false;
95*67e74705SXin Li
96*67e74705SXin Li // Integer literal comparisons, regardless of literal type, are acceptable.
97*67e74705SXin Li if (isa<IntegerLiteral>(E1))
98*67e74705SXin Li return true;
99*67e74705SXin Li
100*67e74705SXin Li // IntegerLiterals are handled above and only EnumConstantDecls are expected
101*67e74705SXin Li // beyond this point
102*67e74705SXin Li assert(isa<DeclRefExpr>(E1) && isa<DeclRefExpr>(E2));
103*67e74705SXin Li auto *Decl1 = cast<DeclRefExpr>(E1)->getDecl();
104*67e74705SXin Li auto *Decl2 = cast<DeclRefExpr>(E2)->getDecl();
105*67e74705SXin Li
106*67e74705SXin Li assert(isa<EnumConstantDecl>(Decl1) && isa<EnumConstantDecl>(Decl2));
107*67e74705SXin Li const DeclContext *DC1 = Decl1->getDeclContext();
108*67e74705SXin Li const DeclContext *DC2 = Decl2->getDeclContext();
109*67e74705SXin Li
110*67e74705SXin Li assert(isa<EnumDecl>(DC1) && isa<EnumDecl>(DC2));
111*67e74705SXin Li return DC1 == DC2;
112*67e74705SXin Li }
113*67e74705SXin Li
114*67e74705SXin Li class CFGBuilder;
115*67e74705SXin Li
116*67e74705SXin Li /// The CFG builder uses a recursive algorithm to build the CFG. When
117*67e74705SXin Li /// we process an expression, sometimes we know that we must add the
118*67e74705SXin Li /// subexpressions as block-level expressions. For example:
119*67e74705SXin Li ///
120*67e74705SXin Li /// exp1 || exp2
121*67e74705SXin Li ///
122*67e74705SXin Li /// When processing the '||' expression, we know that exp1 and exp2
123*67e74705SXin Li /// need to be added as block-level expressions, even though they
124*67e74705SXin Li /// might not normally need to be. AddStmtChoice records this
125*67e74705SXin Li /// contextual information. If AddStmtChoice is 'NotAlwaysAdd', then
126*67e74705SXin Li /// the builder has an option not to add a subexpression as a
127*67e74705SXin Li /// block-level expression.
128*67e74705SXin Li ///
129*67e74705SXin Li class AddStmtChoice {
130*67e74705SXin Li public:
131*67e74705SXin Li enum Kind { NotAlwaysAdd = 0, AlwaysAdd = 1 };
132*67e74705SXin Li
AddStmtChoice(Kind a_kind=NotAlwaysAdd)133*67e74705SXin Li AddStmtChoice(Kind a_kind = NotAlwaysAdd) : kind(a_kind) {}
134*67e74705SXin Li
135*67e74705SXin Li bool alwaysAdd(CFGBuilder &builder,
136*67e74705SXin Li const Stmt *stmt) const;
137*67e74705SXin Li
138*67e74705SXin Li /// Return a copy of this object, except with the 'always-add' bit
139*67e74705SXin Li /// set as specified.
withAlwaysAdd(bool alwaysAdd) const140*67e74705SXin Li AddStmtChoice withAlwaysAdd(bool alwaysAdd) const {
141*67e74705SXin Li return AddStmtChoice(alwaysAdd ? AlwaysAdd : NotAlwaysAdd);
142*67e74705SXin Li }
143*67e74705SXin Li
144*67e74705SXin Li private:
145*67e74705SXin Li Kind kind;
146*67e74705SXin Li };
147*67e74705SXin Li
148*67e74705SXin Li /// LocalScope - Node in tree of local scopes created for C++ implicit
149*67e74705SXin Li /// destructor calls generation. It contains list of automatic variables
150*67e74705SXin Li /// declared in the scope and link to position in previous scope this scope
151*67e74705SXin Li /// began in.
152*67e74705SXin Li ///
153*67e74705SXin Li /// The process of creating local scopes is as follows:
154*67e74705SXin Li /// - Init CFGBuilder::ScopePos with invalid position (equivalent for null),
155*67e74705SXin Li /// - Before processing statements in scope (e.g. CompoundStmt) create
156*67e74705SXin Li /// LocalScope object using CFGBuilder::ScopePos as link to previous scope
157*67e74705SXin Li /// and set CFGBuilder::ScopePos to the end of new scope,
158*67e74705SXin Li /// - On every occurrence of VarDecl increase CFGBuilder::ScopePos if it points
159*67e74705SXin Li /// at this VarDecl,
160*67e74705SXin Li /// - For every normal (without jump) end of scope add to CFGBlock destructors
161*67e74705SXin Li /// for objects in the current scope,
162*67e74705SXin Li /// - For every jump add to CFGBlock destructors for objects
163*67e74705SXin Li /// between CFGBuilder::ScopePos and local scope position saved for jump
164*67e74705SXin Li /// target. Thanks to C++ restrictions on goto jumps we can be sure that
165*67e74705SXin Li /// jump target position will be on the path to root from CFGBuilder::ScopePos
166*67e74705SXin Li /// (adding any variable that doesn't need constructor to be called to
167*67e74705SXin Li /// LocalScope can break this assumption),
168*67e74705SXin Li ///
169*67e74705SXin Li class LocalScope {
170*67e74705SXin Li public:
171*67e74705SXin Li typedef BumpVector<VarDecl*> AutomaticVarsTy;
172*67e74705SXin Li
173*67e74705SXin Li /// const_iterator - Iterates local scope backwards and jumps to previous
174*67e74705SXin Li /// scope on reaching the beginning of currently iterated scope.
175*67e74705SXin Li class const_iterator {
176*67e74705SXin Li const LocalScope* Scope;
177*67e74705SXin Li
178*67e74705SXin Li /// VarIter is guaranteed to be greater then 0 for every valid iterator.
179*67e74705SXin Li /// Invalid iterator (with null Scope) has VarIter equal to 0.
180*67e74705SXin Li unsigned VarIter;
181*67e74705SXin Li
182*67e74705SXin Li public:
183*67e74705SXin Li /// Create invalid iterator. Dereferencing invalid iterator is not allowed.
184*67e74705SXin Li /// Incrementing invalid iterator is allowed and will result in invalid
185*67e74705SXin Li /// iterator.
const_iterator()186*67e74705SXin Li const_iterator()
187*67e74705SXin Li : Scope(nullptr), VarIter(0) {}
188*67e74705SXin Li
189*67e74705SXin Li /// Create valid iterator. In case when S.Prev is an invalid iterator and
190*67e74705SXin Li /// I is equal to 0, this will create invalid iterator.
const_iterator(const LocalScope & S,unsigned I)191*67e74705SXin Li const_iterator(const LocalScope& S, unsigned I)
192*67e74705SXin Li : Scope(&S), VarIter(I) {
193*67e74705SXin Li // Iterator to "end" of scope is not allowed. Handle it by going up
194*67e74705SXin Li // in scopes tree possibly up to invalid iterator in the root.
195*67e74705SXin Li if (VarIter == 0 && Scope)
196*67e74705SXin Li *this = Scope->Prev;
197*67e74705SXin Li }
198*67e74705SXin Li
operator ->() const199*67e74705SXin Li VarDecl *const* operator->() const {
200*67e74705SXin Li assert (Scope && "Dereferencing invalid iterator is not allowed");
201*67e74705SXin Li assert (VarIter != 0 && "Iterator has invalid value of VarIter member");
202*67e74705SXin Li return &Scope->Vars[VarIter - 1];
203*67e74705SXin Li }
operator *() const204*67e74705SXin Li VarDecl *operator*() const {
205*67e74705SXin Li return *this->operator->();
206*67e74705SXin Li }
207*67e74705SXin Li
operator ++()208*67e74705SXin Li const_iterator &operator++() {
209*67e74705SXin Li if (!Scope)
210*67e74705SXin Li return *this;
211*67e74705SXin Li
212*67e74705SXin Li assert (VarIter != 0 && "Iterator has invalid value of VarIter member");
213*67e74705SXin Li --VarIter;
214*67e74705SXin Li if (VarIter == 0)
215*67e74705SXin Li *this = Scope->Prev;
216*67e74705SXin Li return *this;
217*67e74705SXin Li }
operator ++(int)218*67e74705SXin Li const_iterator operator++(int) {
219*67e74705SXin Li const_iterator P = *this;
220*67e74705SXin Li ++*this;
221*67e74705SXin Li return P;
222*67e74705SXin Li }
223*67e74705SXin Li
operator ==(const const_iterator & rhs) const224*67e74705SXin Li bool operator==(const const_iterator &rhs) const {
225*67e74705SXin Li return Scope == rhs.Scope && VarIter == rhs.VarIter;
226*67e74705SXin Li }
operator !=(const const_iterator & rhs) const227*67e74705SXin Li bool operator!=(const const_iterator &rhs) const {
228*67e74705SXin Li return !(*this == rhs);
229*67e74705SXin Li }
230*67e74705SXin Li
operator bool() const231*67e74705SXin Li explicit operator bool() const {
232*67e74705SXin Li return *this != const_iterator();
233*67e74705SXin Li }
234*67e74705SXin Li
235*67e74705SXin Li int distance(const_iterator L);
236*67e74705SXin Li };
237*67e74705SXin Li
238*67e74705SXin Li friend class const_iterator;
239*67e74705SXin Li
240*67e74705SXin Li private:
241*67e74705SXin Li BumpVectorContext ctx;
242*67e74705SXin Li
243*67e74705SXin Li /// Automatic variables in order of declaration.
244*67e74705SXin Li AutomaticVarsTy Vars;
245*67e74705SXin Li /// Iterator to variable in previous scope that was declared just before
246*67e74705SXin Li /// begin of this scope.
247*67e74705SXin Li const_iterator Prev;
248*67e74705SXin Li
249*67e74705SXin Li public:
250*67e74705SXin Li /// Constructs empty scope linked to previous scope in specified place.
LocalScope(BumpVectorContext ctx,const_iterator P)251*67e74705SXin Li LocalScope(BumpVectorContext ctx, const_iterator P)
252*67e74705SXin Li : ctx(std::move(ctx)), Vars(this->ctx, 4), Prev(P) {}
253*67e74705SXin Li
254*67e74705SXin Li /// Begin of scope in direction of CFG building (backwards).
begin() const255*67e74705SXin Li const_iterator begin() const { return const_iterator(*this, Vars.size()); }
256*67e74705SXin Li
addVar(VarDecl * VD)257*67e74705SXin Li void addVar(VarDecl *VD) {
258*67e74705SXin Li Vars.push_back(VD, ctx);
259*67e74705SXin Li }
260*67e74705SXin Li };
261*67e74705SXin Li
262*67e74705SXin Li /// distance - Calculates distance from this to L. L must be reachable from this
263*67e74705SXin Li /// (with use of ++ operator). Cost of calculating the distance is linear w.r.t.
264*67e74705SXin Li /// number of scopes between this and L.
distance(LocalScope::const_iterator L)265*67e74705SXin Li int LocalScope::const_iterator::distance(LocalScope::const_iterator L) {
266*67e74705SXin Li int D = 0;
267*67e74705SXin Li const_iterator F = *this;
268*67e74705SXin Li while (F.Scope != L.Scope) {
269*67e74705SXin Li assert (F != const_iterator()
270*67e74705SXin Li && "L iterator is not reachable from F iterator.");
271*67e74705SXin Li D += F.VarIter;
272*67e74705SXin Li F = F.Scope->Prev;
273*67e74705SXin Li }
274*67e74705SXin Li D += F.VarIter - L.VarIter;
275*67e74705SXin Li return D;
276*67e74705SXin Li }
277*67e74705SXin Li
278*67e74705SXin Li /// Structure for specifying position in CFG during its build process. It
279*67e74705SXin Li /// consists of CFGBlock that specifies position in CFG and
280*67e74705SXin Li /// LocalScope::const_iterator that specifies position in LocalScope graph.
281*67e74705SXin Li struct BlockScopePosPair {
BlockScopePosPair__anonc5699e550111::BlockScopePosPair282*67e74705SXin Li BlockScopePosPair() : block(nullptr) {}
BlockScopePosPair__anonc5699e550111::BlockScopePosPair283*67e74705SXin Li BlockScopePosPair(CFGBlock *b, LocalScope::const_iterator scopePos)
284*67e74705SXin Li : block(b), scopePosition(scopePos) {}
285*67e74705SXin Li
286*67e74705SXin Li CFGBlock *block;
287*67e74705SXin Li LocalScope::const_iterator scopePosition;
288*67e74705SXin Li };
289*67e74705SXin Li
290*67e74705SXin Li /// TryResult - a class representing a variant over the values
291*67e74705SXin Li /// 'true', 'false', or 'unknown'. This is returned by tryEvaluateBool,
292*67e74705SXin Li /// and is used by the CFGBuilder to decide if a branch condition
293*67e74705SXin Li /// can be decided up front during CFG construction.
294*67e74705SXin Li class TryResult {
295*67e74705SXin Li int X;
296*67e74705SXin Li public:
TryResult(bool b)297*67e74705SXin Li TryResult(bool b) : X(b ? 1 : 0) {}
TryResult()298*67e74705SXin Li TryResult() : X(-1) {}
299*67e74705SXin Li
isTrue() const300*67e74705SXin Li bool isTrue() const { return X == 1; }
isFalse() const301*67e74705SXin Li bool isFalse() const { return X == 0; }
isKnown() const302*67e74705SXin Li bool isKnown() const { return X >= 0; }
negate()303*67e74705SXin Li void negate() {
304*67e74705SXin Li assert(isKnown());
305*67e74705SXin Li X ^= 0x1;
306*67e74705SXin Li }
307*67e74705SXin Li };
308*67e74705SXin Li
bothKnownTrue(TryResult R1,TryResult R2)309*67e74705SXin Li TryResult bothKnownTrue(TryResult R1, TryResult R2) {
310*67e74705SXin Li if (!R1.isKnown() || !R2.isKnown())
311*67e74705SXin Li return TryResult();
312*67e74705SXin Li return TryResult(R1.isTrue() && R2.isTrue());
313*67e74705SXin Li }
314*67e74705SXin Li
315*67e74705SXin Li class reverse_children {
316*67e74705SXin Li llvm::SmallVector<Stmt *, 12> childrenBuf;
317*67e74705SXin Li ArrayRef<Stmt*> children;
318*67e74705SXin Li public:
319*67e74705SXin Li reverse_children(Stmt *S);
320*67e74705SXin Li
321*67e74705SXin Li typedef ArrayRef<Stmt*>::reverse_iterator iterator;
begin() const322*67e74705SXin Li iterator begin() const { return children.rbegin(); }
end() const323*67e74705SXin Li iterator end() const { return children.rend(); }
324*67e74705SXin Li };
325*67e74705SXin Li
326*67e74705SXin Li
reverse_children(Stmt * S)327*67e74705SXin Li reverse_children::reverse_children(Stmt *S) {
328*67e74705SXin Li if (CallExpr *CE = dyn_cast<CallExpr>(S)) {
329*67e74705SXin Li children = CE->getRawSubExprs();
330*67e74705SXin Li return;
331*67e74705SXin Li }
332*67e74705SXin Li switch (S->getStmtClass()) {
333*67e74705SXin Li // Note: Fill in this switch with more cases we want to optimize.
334*67e74705SXin Li case Stmt::InitListExprClass: {
335*67e74705SXin Li InitListExpr *IE = cast<InitListExpr>(S);
336*67e74705SXin Li children = llvm::makeArrayRef(reinterpret_cast<Stmt**>(IE->getInits()),
337*67e74705SXin Li IE->getNumInits());
338*67e74705SXin Li return;
339*67e74705SXin Li }
340*67e74705SXin Li default:
341*67e74705SXin Li break;
342*67e74705SXin Li }
343*67e74705SXin Li
344*67e74705SXin Li // Default case for all other statements.
345*67e74705SXin Li for (Stmt *SubStmt : S->children())
346*67e74705SXin Li childrenBuf.push_back(SubStmt);
347*67e74705SXin Li
348*67e74705SXin Li // This needs to be done *after* childrenBuf has been populated.
349*67e74705SXin Li children = childrenBuf;
350*67e74705SXin Li }
351*67e74705SXin Li
352*67e74705SXin Li /// CFGBuilder - This class implements CFG construction from an AST.
353*67e74705SXin Li /// The builder is stateful: an instance of the builder should be used to only
354*67e74705SXin Li /// construct a single CFG.
355*67e74705SXin Li ///
356*67e74705SXin Li /// Example usage:
357*67e74705SXin Li ///
358*67e74705SXin Li /// CFGBuilder builder;
359*67e74705SXin Li /// std::unique_ptr<CFG> cfg = builder.buildCFG(decl, stmt1);
360*67e74705SXin Li ///
361*67e74705SXin Li /// CFG construction is done via a recursive walk of an AST. We actually parse
362*67e74705SXin Li /// the AST in reverse order so that the successor of a basic block is
363*67e74705SXin Li /// constructed prior to its predecessor. This allows us to nicely capture
364*67e74705SXin Li /// implicit fall-throughs without extra basic blocks.
365*67e74705SXin Li ///
366*67e74705SXin Li class CFGBuilder {
367*67e74705SXin Li typedef BlockScopePosPair JumpTarget;
368*67e74705SXin Li typedef BlockScopePosPair JumpSource;
369*67e74705SXin Li
370*67e74705SXin Li ASTContext *Context;
371*67e74705SXin Li std::unique_ptr<CFG> cfg;
372*67e74705SXin Li
373*67e74705SXin Li CFGBlock *Block;
374*67e74705SXin Li CFGBlock *Succ;
375*67e74705SXin Li JumpTarget ContinueJumpTarget;
376*67e74705SXin Li JumpTarget BreakJumpTarget;
377*67e74705SXin Li CFGBlock *SwitchTerminatedBlock;
378*67e74705SXin Li CFGBlock *DefaultCaseBlock;
379*67e74705SXin Li CFGBlock *TryTerminatedBlock;
380*67e74705SXin Li
381*67e74705SXin Li // Current position in local scope.
382*67e74705SXin Li LocalScope::const_iterator ScopePos;
383*67e74705SXin Li
384*67e74705SXin Li // LabelMap records the mapping from Label expressions to their jump targets.
385*67e74705SXin Li typedef llvm::DenseMap<LabelDecl*, JumpTarget> LabelMapTy;
386*67e74705SXin Li LabelMapTy LabelMap;
387*67e74705SXin Li
388*67e74705SXin Li // A list of blocks that end with a "goto" that must be backpatched to their
389*67e74705SXin Li // resolved targets upon completion of CFG construction.
390*67e74705SXin Li typedef std::vector<JumpSource> BackpatchBlocksTy;
391*67e74705SXin Li BackpatchBlocksTy BackpatchBlocks;
392*67e74705SXin Li
393*67e74705SXin Li // A list of labels whose address has been taken (for indirect gotos).
394*67e74705SXin Li typedef llvm::SmallPtrSet<LabelDecl*, 5> LabelSetTy;
395*67e74705SXin Li LabelSetTy AddressTakenLabels;
396*67e74705SXin Li
397*67e74705SXin Li bool badCFG;
398*67e74705SXin Li const CFG::BuildOptions &BuildOpts;
399*67e74705SXin Li
400*67e74705SXin Li // State to track for building switch statements.
401*67e74705SXin Li bool switchExclusivelyCovered;
402*67e74705SXin Li Expr::EvalResult *switchCond;
403*67e74705SXin Li
404*67e74705SXin Li CFG::BuildOptions::ForcedBlkExprs::value_type *cachedEntry;
405*67e74705SXin Li const Stmt *lastLookup;
406*67e74705SXin Li
407*67e74705SXin Li // Caches boolean evaluations of expressions to avoid multiple re-evaluations
408*67e74705SXin Li // during construction of branches for chained logical operators.
409*67e74705SXin Li typedef llvm::DenseMap<Expr *, TryResult> CachedBoolEvalsTy;
410*67e74705SXin Li CachedBoolEvalsTy CachedBoolEvals;
411*67e74705SXin Li
412*67e74705SXin Li public:
CFGBuilder(ASTContext * astContext,const CFG::BuildOptions & buildOpts)413*67e74705SXin Li explicit CFGBuilder(ASTContext *astContext,
414*67e74705SXin Li const CFG::BuildOptions &buildOpts)
415*67e74705SXin Li : Context(astContext), cfg(new CFG()), // crew a new CFG
416*67e74705SXin Li Block(nullptr), Succ(nullptr),
417*67e74705SXin Li SwitchTerminatedBlock(nullptr), DefaultCaseBlock(nullptr),
418*67e74705SXin Li TryTerminatedBlock(nullptr), badCFG(false), BuildOpts(buildOpts),
419*67e74705SXin Li switchExclusivelyCovered(false), switchCond(nullptr),
420*67e74705SXin Li cachedEntry(nullptr), lastLookup(nullptr) {}
421*67e74705SXin Li
422*67e74705SXin Li // buildCFG - Used by external clients to construct the CFG.
423*67e74705SXin Li std::unique_ptr<CFG> buildCFG(const Decl *D, Stmt *Statement);
424*67e74705SXin Li
425*67e74705SXin Li bool alwaysAdd(const Stmt *stmt);
426*67e74705SXin Li
427*67e74705SXin Li private:
428*67e74705SXin Li // Visitors to walk an AST and construct the CFG.
429*67e74705SXin Li CFGBlock *VisitAddrLabelExpr(AddrLabelExpr *A, AddStmtChoice asc);
430*67e74705SXin Li CFGBlock *VisitBinaryOperator(BinaryOperator *B, AddStmtChoice asc);
431*67e74705SXin Li CFGBlock *VisitBreakStmt(BreakStmt *B);
432*67e74705SXin Li CFGBlock *VisitCallExpr(CallExpr *C, AddStmtChoice asc);
433*67e74705SXin Li CFGBlock *VisitCaseStmt(CaseStmt *C);
434*67e74705SXin Li CFGBlock *VisitChooseExpr(ChooseExpr *C, AddStmtChoice asc);
435*67e74705SXin Li CFGBlock *VisitCompoundStmt(CompoundStmt *C);
436*67e74705SXin Li CFGBlock *VisitConditionalOperator(AbstractConditionalOperator *C,
437*67e74705SXin Li AddStmtChoice asc);
438*67e74705SXin Li CFGBlock *VisitContinueStmt(ContinueStmt *C);
439*67e74705SXin Li CFGBlock *VisitCXXBindTemporaryExpr(CXXBindTemporaryExpr *E,
440*67e74705SXin Li AddStmtChoice asc);
441*67e74705SXin Li CFGBlock *VisitCXXCatchStmt(CXXCatchStmt *S);
442*67e74705SXin Li CFGBlock *VisitCXXConstructExpr(CXXConstructExpr *C, AddStmtChoice asc);
443*67e74705SXin Li CFGBlock *VisitCXXNewExpr(CXXNewExpr *DE, AddStmtChoice asc);
444*67e74705SXin Li CFGBlock *VisitCXXDeleteExpr(CXXDeleteExpr *DE, AddStmtChoice asc);
445*67e74705SXin Li CFGBlock *VisitCXXForRangeStmt(CXXForRangeStmt *S);
446*67e74705SXin Li CFGBlock *VisitCXXFunctionalCastExpr(CXXFunctionalCastExpr *E,
447*67e74705SXin Li AddStmtChoice asc);
448*67e74705SXin Li CFGBlock *VisitCXXTemporaryObjectExpr(CXXTemporaryObjectExpr *C,
449*67e74705SXin Li AddStmtChoice asc);
450*67e74705SXin Li CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
451*67e74705SXin Li CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
452*67e74705SXin Li CFGBlock *VisitDeclStmt(DeclStmt *DS);
453*67e74705SXin Li CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
454*67e74705SXin Li CFGBlock *VisitDefaultStmt(DefaultStmt *D);
455*67e74705SXin Li CFGBlock *VisitDoStmt(DoStmt *D);
456*67e74705SXin Li CFGBlock *VisitExprWithCleanups(ExprWithCleanups *E, AddStmtChoice asc);
457*67e74705SXin Li CFGBlock *VisitForStmt(ForStmt *F);
458*67e74705SXin Li CFGBlock *VisitGotoStmt(GotoStmt *G);
459*67e74705SXin Li CFGBlock *VisitIfStmt(IfStmt *I);
460*67e74705SXin Li CFGBlock *VisitImplicitCastExpr(ImplicitCastExpr *E, AddStmtChoice asc);
461*67e74705SXin Li CFGBlock *VisitIndirectGotoStmt(IndirectGotoStmt *I);
462*67e74705SXin Li CFGBlock *VisitLabelStmt(LabelStmt *L);
463*67e74705SXin Li CFGBlock *VisitBlockExpr(BlockExpr *E, AddStmtChoice asc);
464*67e74705SXin Li CFGBlock *VisitLambdaExpr(LambdaExpr *E, AddStmtChoice asc);
465*67e74705SXin Li CFGBlock *VisitLogicalOperator(BinaryOperator *B);
466*67e74705SXin Li std::pair<CFGBlock *, CFGBlock *> VisitLogicalOperator(BinaryOperator *B,
467*67e74705SXin Li Stmt *Term,
468*67e74705SXin Li CFGBlock *TrueBlock,
469*67e74705SXin Li CFGBlock *FalseBlock);
470*67e74705SXin Li CFGBlock *VisitMemberExpr(MemberExpr *M, AddStmtChoice asc);
471*67e74705SXin Li CFGBlock *VisitObjCAtCatchStmt(ObjCAtCatchStmt *S);
472*67e74705SXin Li CFGBlock *VisitObjCAtSynchronizedStmt(ObjCAtSynchronizedStmt *S);
473*67e74705SXin Li CFGBlock *VisitObjCAtThrowStmt(ObjCAtThrowStmt *S);
474*67e74705SXin Li CFGBlock *VisitObjCAtTryStmt(ObjCAtTryStmt *S);
475*67e74705SXin Li CFGBlock *VisitObjCAutoreleasePoolStmt(ObjCAutoreleasePoolStmt *S);
476*67e74705SXin Li CFGBlock *VisitObjCForCollectionStmt(ObjCForCollectionStmt *S);
477*67e74705SXin Li CFGBlock *VisitPseudoObjectExpr(PseudoObjectExpr *E);
478*67e74705SXin Li CFGBlock *VisitReturnStmt(ReturnStmt *R);
479*67e74705SXin Li CFGBlock *VisitStmtExpr(StmtExpr *S, AddStmtChoice asc);
480*67e74705SXin Li CFGBlock *VisitSwitchStmt(SwitchStmt *S);
481*67e74705SXin Li CFGBlock *VisitUnaryExprOrTypeTraitExpr(UnaryExprOrTypeTraitExpr *E,
482*67e74705SXin Li AddStmtChoice asc);
483*67e74705SXin Li CFGBlock *VisitUnaryOperator(UnaryOperator *U, AddStmtChoice asc);
484*67e74705SXin Li CFGBlock *VisitWhileStmt(WhileStmt *W);
485*67e74705SXin Li
486*67e74705SXin Li CFGBlock *Visit(Stmt *S, AddStmtChoice asc = AddStmtChoice::NotAlwaysAdd);
487*67e74705SXin Li CFGBlock *VisitStmt(Stmt *S, AddStmtChoice asc);
488*67e74705SXin Li CFGBlock *VisitChildren(Stmt *S);
489*67e74705SXin Li CFGBlock *VisitNoRecurse(Expr *E, AddStmtChoice asc);
490*67e74705SXin Li
491*67e74705SXin Li /// When creating the CFG for temporary destructors, we want to mirror the
492*67e74705SXin Li /// branch structure of the corresponding constructor calls.
493*67e74705SXin Li /// Thus, while visiting a statement for temporary destructors, we keep a
494*67e74705SXin Li /// context to keep track of the following information:
495*67e74705SXin Li /// - whether a subexpression is executed unconditionally
496*67e74705SXin Li /// - if a subexpression is executed conditionally, the first
497*67e74705SXin Li /// CXXBindTemporaryExpr we encounter in that subexpression (which
498*67e74705SXin Li /// corresponds to the last temporary destructor we have to call for this
499*67e74705SXin Li /// subexpression) and the CFG block at that point (which will become the
500*67e74705SXin Li /// successor block when inserting the decision point).
501*67e74705SXin Li ///
502*67e74705SXin Li /// That way, we can build the branch structure for temporary destructors as
503*67e74705SXin Li /// follows:
504*67e74705SXin Li /// 1. If a subexpression is executed unconditionally, we add the temporary
505*67e74705SXin Li /// destructor calls to the current block.
506*67e74705SXin Li /// 2. If a subexpression is executed conditionally, when we encounter a
507*67e74705SXin Li /// CXXBindTemporaryExpr:
508*67e74705SXin Li /// a) If it is the first temporary destructor call in the subexpression,
509*67e74705SXin Li /// we remember the CXXBindTemporaryExpr and the current block in the
510*67e74705SXin Li /// TempDtorContext; we start a new block, and insert the temporary
511*67e74705SXin Li /// destructor call.
512*67e74705SXin Li /// b) Otherwise, add the temporary destructor call to the current block.
513*67e74705SXin Li /// 3. When we finished visiting a conditionally executed subexpression,
514*67e74705SXin Li /// and we found at least one temporary constructor during the visitation
515*67e74705SXin Li /// (2.a has executed), we insert a decision block that uses the
516*67e74705SXin Li /// CXXBindTemporaryExpr as terminator, and branches to the current block
517*67e74705SXin Li /// if the CXXBindTemporaryExpr was marked executed, and otherwise
518*67e74705SXin Li /// branches to the stored successor.
519*67e74705SXin Li struct TempDtorContext {
TempDtorContext__anonc5699e550111::CFGBuilder::TempDtorContext520*67e74705SXin Li TempDtorContext()
521*67e74705SXin Li : IsConditional(false), KnownExecuted(true), Succ(nullptr),
522*67e74705SXin Li TerminatorExpr(nullptr) {}
523*67e74705SXin Li
TempDtorContext__anonc5699e550111::CFGBuilder::TempDtorContext524*67e74705SXin Li TempDtorContext(TryResult KnownExecuted)
525*67e74705SXin Li : IsConditional(true), KnownExecuted(KnownExecuted), Succ(nullptr),
526*67e74705SXin Li TerminatorExpr(nullptr) {}
527*67e74705SXin Li
528*67e74705SXin Li /// Returns whether we need to start a new branch for a temporary destructor
529*67e74705SXin Li /// call. This is the case when the temporary destructor is
530*67e74705SXin Li /// conditionally executed, and it is the first one we encounter while
531*67e74705SXin Li /// visiting a subexpression - other temporary destructors at the same level
532*67e74705SXin Li /// will be added to the same block and are executed under the same
533*67e74705SXin Li /// condition.
needsTempDtorBranch__anonc5699e550111::CFGBuilder::TempDtorContext534*67e74705SXin Li bool needsTempDtorBranch() const {
535*67e74705SXin Li return IsConditional && !TerminatorExpr;
536*67e74705SXin Li }
537*67e74705SXin Li
538*67e74705SXin Li /// Remember the successor S of a temporary destructor decision branch for
539*67e74705SXin Li /// the corresponding CXXBindTemporaryExpr E.
setDecisionPoint__anonc5699e550111::CFGBuilder::TempDtorContext540*67e74705SXin Li void setDecisionPoint(CFGBlock *S, CXXBindTemporaryExpr *E) {
541*67e74705SXin Li Succ = S;
542*67e74705SXin Li TerminatorExpr = E;
543*67e74705SXin Li }
544*67e74705SXin Li
545*67e74705SXin Li const bool IsConditional;
546*67e74705SXin Li const TryResult KnownExecuted;
547*67e74705SXin Li CFGBlock *Succ;
548*67e74705SXin Li CXXBindTemporaryExpr *TerminatorExpr;
549*67e74705SXin Li };
550*67e74705SXin Li
551*67e74705SXin Li // Visitors to walk an AST and generate destructors of temporaries in
552*67e74705SXin Li // full expression.
553*67e74705SXin Li CFGBlock *VisitForTemporaryDtors(Stmt *E, bool BindToTemporary,
554*67e74705SXin Li TempDtorContext &Context);
555*67e74705SXin Li CFGBlock *VisitChildrenForTemporaryDtors(Stmt *E, TempDtorContext &Context);
556*67e74705SXin Li CFGBlock *VisitBinaryOperatorForTemporaryDtors(BinaryOperator *E,
557*67e74705SXin Li TempDtorContext &Context);
558*67e74705SXin Li CFGBlock *VisitCXXBindTemporaryExprForTemporaryDtors(
559*67e74705SXin Li CXXBindTemporaryExpr *E, bool BindToTemporary, TempDtorContext &Context);
560*67e74705SXin Li CFGBlock *VisitConditionalOperatorForTemporaryDtors(
561*67e74705SXin Li AbstractConditionalOperator *E, bool BindToTemporary,
562*67e74705SXin Li TempDtorContext &Context);
563*67e74705SXin Li void InsertTempDtorDecisionBlock(const TempDtorContext &Context,
564*67e74705SXin Li CFGBlock *FalseSucc = nullptr);
565*67e74705SXin Li
566*67e74705SXin Li // NYS == Not Yet Supported
NYS()567*67e74705SXin Li CFGBlock *NYS() {
568*67e74705SXin Li badCFG = true;
569*67e74705SXin Li return Block;
570*67e74705SXin Li }
571*67e74705SXin Li
autoCreateBlock()572*67e74705SXin Li void autoCreateBlock() { if (!Block) Block = createBlock(); }
573*67e74705SXin Li CFGBlock *createBlock(bool add_successor = true);
574*67e74705SXin Li CFGBlock *createNoReturnBlock();
575*67e74705SXin Li
addStmt(Stmt * S)576*67e74705SXin Li CFGBlock *addStmt(Stmt *S) {
577*67e74705SXin Li return Visit(S, AddStmtChoice::AlwaysAdd);
578*67e74705SXin Li }
579*67e74705SXin Li CFGBlock *addInitializer(CXXCtorInitializer *I);
580*67e74705SXin Li void addAutomaticObjDtors(LocalScope::const_iterator B,
581*67e74705SXin Li LocalScope::const_iterator E, Stmt *S);
582*67e74705SXin Li void addImplicitDtorsForDestructor(const CXXDestructorDecl *DD);
583*67e74705SXin Li
584*67e74705SXin Li // Local scopes creation.
585*67e74705SXin Li LocalScope* createOrReuseLocalScope(LocalScope* Scope);
586*67e74705SXin Li
587*67e74705SXin Li void addLocalScopeForStmt(Stmt *S);
588*67e74705SXin Li LocalScope* addLocalScopeForDeclStmt(DeclStmt *DS,
589*67e74705SXin Li LocalScope* Scope = nullptr);
590*67e74705SXin Li LocalScope* addLocalScopeForVarDecl(VarDecl *VD, LocalScope* Scope = nullptr);
591*67e74705SXin Li
592*67e74705SXin Li void addLocalScopeAndDtors(Stmt *S);
593*67e74705SXin Li
594*67e74705SXin Li // Interface to CFGBlock - adding CFGElements.
appendStmt(CFGBlock * B,const Stmt * S)595*67e74705SXin Li void appendStmt(CFGBlock *B, const Stmt *S) {
596*67e74705SXin Li if (alwaysAdd(S) && cachedEntry)
597*67e74705SXin Li cachedEntry->second = B;
598*67e74705SXin Li
599*67e74705SXin Li // All block-level expressions should have already been IgnoreParens()ed.
600*67e74705SXin Li assert(!isa<Expr>(S) || cast<Expr>(S)->IgnoreParens() == S);
601*67e74705SXin Li B->appendStmt(const_cast<Stmt*>(S), cfg->getBumpVectorContext());
602*67e74705SXin Li }
appendInitializer(CFGBlock * B,CXXCtorInitializer * I)603*67e74705SXin Li void appendInitializer(CFGBlock *B, CXXCtorInitializer *I) {
604*67e74705SXin Li B->appendInitializer(I, cfg->getBumpVectorContext());
605*67e74705SXin Li }
appendNewAllocator(CFGBlock * B,CXXNewExpr * NE)606*67e74705SXin Li void appendNewAllocator(CFGBlock *B, CXXNewExpr *NE) {
607*67e74705SXin Li B->appendNewAllocator(NE, cfg->getBumpVectorContext());
608*67e74705SXin Li }
appendBaseDtor(CFGBlock * B,const CXXBaseSpecifier * BS)609*67e74705SXin Li void appendBaseDtor(CFGBlock *B, const CXXBaseSpecifier *BS) {
610*67e74705SXin Li B->appendBaseDtor(BS, cfg->getBumpVectorContext());
611*67e74705SXin Li }
appendMemberDtor(CFGBlock * B,FieldDecl * FD)612*67e74705SXin Li void appendMemberDtor(CFGBlock *B, FieldDecl *FD) {
613*67e74705SXin Li B->appendMemberDtor(FD, cfg->getBumpVectorContext());
614*67e74705SXin Li }
appendTemporaryDtor(CFGBlock * B,CXXBindTemporaryExpr * E)615*67e74705SXin Li void appendTemporaryDtor(CFGBlock *B, CXXBindTemporaryExpr *E) {
616*67e74705SXin Li B->appendTemporaryDtor(E, cfg->getBumpVectorContext());
617*67e74705SXin Li }
appendAutomaticObjDtor(CFGBlock * B,VarDecl * VD,Stmt * S)618*67e74705SXin Li void appendAutomaticObjDtor(CFGBlock *B, VarDecl *VD, Stmt *S) {
619*67e74705SXin Li B->appendAutomaticObjDtor(VD, S, cfg->getBumpVectorContext());
620*67e74705SXin Li }
621*67e74705SXin Li
appendDeleteDtor(CFGBlock * B,CXXRecordDecl * RD,CXXDeleteExpr * DE)622*67e74705SXin Li void appendDeleteDtor(CFGBlock *B, CXXRecordDecl *RD, CXXDeleteExpr *DE) {
623*67e74705SXin Li B->appendDeleteDtor(RD, DE, cfg->getBumpVectorContext());
624*67e74705SXin Li }
625*67e74705SXin Li
626*67e74705SXin Li void prependAutomaticObjDtorsWithTerminator(CFGBlock *Blk,
627*67e74705SXin Li LocalScope::const_iterator B, LocalScope::const_iterator E);
628*67e74705SXin Li
addSuccessor(CFGBlock * B,CFGBlock * S,bool IsReachable=true)629*67e74705SXin Li void addSuccessor(CFGBlock *B, CFGBlock *S, bool IsReachable = true) {
630*67e74705SXin Li B->addSuccessor(CFGBlock::AdjacentBlock(S, IsReachable),
631*67e74705SXin Li cfg->getBumpVectorContext());
632*67e74705SXin Li }
633*67e74705SXin Li
634*67e74705SXin Li /// Add a reachable successor to a block, with the alternate variant that is
635*67e74705SXin Li /// unreachable.
addSuccessor(CFGBlock * B,CFGBlock * ReachableBlock,CFGBlock * AltBlock)636*67e74705SXin Li void addSuccessor(CFGBlock *B, CFGBlock *ReachableBlock, CFGBlock *AltBlock) {
637*67e74705SXin Li B->addSuccessor(CFGBlock::AdjacentBlock(ReachableBlock, AltBlock),
638*67e74705SXin Li cfg->getBumpVectorContext());
639*67e74705SXin Li }
640*67e74705SXin Li
641*67e74705SXin Li /// \brief Find a relational comparison with an expression evaluating to a
642*67e74705SXin Li /// boolean and a constant other than 0 and 1.
643*67e74705SXin Li /// e.g. if ((x < y) == 10)
checkIncorrectRelationalOperator(const BinaryOperator * B)644*67e74705SXin Li TryResult checkIncorrectRelationalOperator(const BinaryOperator *B) {
645*67e74705SXin Li const Expr *LHSExpr = B->getLHS()->IgnoreParens();
646*67e74705SXin Li const Expr *RHSExpr = B->getRHS()->IgnoreParens();
647*67e74705SXin Li
648*67e74705SXin Li const IntegerLiteral *IntLiteral = dyn_cast<IntegerLiteral>(LHSExpr);
649*67e74705SXin Li const Expr *BoolExpr = RHSExpr;
650*67e74705SXin Li bool IntFirst = true;
651*67e74705SXin Li if (!IntLiteral) {
652*67e74705SXin Li IntLiteral = dyn_cast<IntegerLiteral>(RHSExpr);
653*67e74705SXin Li BoolExpr = LHSExpr;
654*67e74705SXin Li IntFirst = false;
655*67e74705SXin Li }
656*67e74705SXin Li
657*67e74705SXin Li if (!IntLiteral || !BoolExpr->isKnownToHaveBooleanValue())
658*67e74705SXin Li return TryResult();
659*67e74705SXin Li
660*67e74705SXin Li llvm::APInt IntValue = IntLiteral->getValue();
661*67e74705SXin Li if ((IntValue == 1) || (IntValue == 0))
662*67e74705SXin Li return TryResult();
663*67e74705SXin Li
664*67e74705SXin Li bool IntLarger = IntLiteral->getType()->isUnsignedIntegerType() ||
665*67e74705SXin Li !IntValue.isNegative();
666*67e74705SXin Li
667*67e74705SXin Li BinaryOperatorKind Bok = B->getOpcode();
668*67e74705SXin Li if (Bok == BO_GT || Bok == BO_GE) {
669*67e74705SXin Li // Always true for 10 > bool and bool > -1
670*67e74705SXin Li // Always false for -1 > bool and bool > 10
671*67e74705SXin Li return TryResult(IntFirst == IntLarger);
672*67e74705SXin Li } else {
673*67e74705SXin Li // Always true for -1 < bool and bool < 10
674*67e74705SXin Li // Always false for 10 < bool and bool < -1
675*67e74705SXin Li return TryResult(IntFirst != IntLarger);
676*67e74705SXin Li }
677*67e74705SXin Li }
678*67e74705SXin Li
679*67e74705SXin Li /// Find an incorrect equality comparison. Either with an expression
680*67e74705SXin Li /// evaluating to a boolean and a constant other than 0 and 1.
681*67e74705SXin Li /// e.g. if (!x == 10) or a bitwise and/or operation that always evaluates to
682*67e74705SXin Li /// true/false e.q. (x & 8) == 4.
checkIncorrectEqualityOperator(const BinaryOperator * B)683*67e74705SXin Li TryResult checkIncorrectEqualityOperator(const BinaryOperator *B) {
684*67e74705SXin Li const Expr *LHSExpr = B->getLHS()->IgnoreParens();
685*67e74705SXin Li const Expr *RHSExpr = B->getRHS()->IgnoreParens();
686*67e74705SXin Li
687*67e74705SXin Li const IntegerLiteral *IntLiteral = dyn_cast<IntegerLiteral>(LHSExpr);
688*67e74705SXin Li const Expr *BoolExpr = RHSExpr;
689*67e74705SXin Li
690*67e74705SXin Li if (!IntLiteral) {
691*67e74705SXin Li IntLiteral = dyn_cast<IntegerLiteral>(RHSExpr);
692*67e74705SXin Li BoolExpr = LHSExpr;
693*67e74705SXin Li }
694*67e74705SXin Li
695*67e74705SXin Li if (!IntLiteral)
696*67e74705SXin Li return TryResult();
697*67e74705SXin Li
698*67e74705SXin Li const BinaryOperator *BitOp = dyn_cast<BinaryOperator>(BoolExpr);
699*67e74705SXin Li if (BitOp && (BitOp->getOpcode() == BO_And ||
700*67e74705SXin Li BitOp->getOpcode() == BO_Or)) {
701*67e74705SXin Li const Expr *LHSExpr2 = BitOp->getLHS()->IgnoreParens();
702*67e74705SXin Li const Expr *RHSExpr2 = BitOp->getRHS()->IgnoreParens();
703*67e74705SXin Li
704*67e74705SXin Li const IntegerLiteral *IntLiteral2 = dyn_cast<IntegerLiteral>(LHSExpr2);
705*67e74705SXin Li
706*67e74705SXin Li if (!IntLiteral2)
707*67e74705SXin Li IntLiteral2 = dyn_cast<IntegerLiteral>(RHSExpr2);
708*67e74705SXin Li
709*67e74705SXin Li if (!IntLiteral2)
710*67e74705SXin Li return TryResult();
711*67e74705SXin Li
712*67e74705SXin Li llvm::APInt L1 = IntLiteral->getValue();
713*67e74705SXin Li llvm::APInt L2 = IntLiteral2->getValue();
714*67e74705SXin Li if ((BitOp->getOpcode() == BO_And && (L2 & L1) != L1) ||
715*67e74705SXin Li (BitOp->getOpcode() == BO_Or && (L2 | L1) != L1)) {
716*67e74705SXin Li if (BuildOpts.Observer)
717*67e74705SXin Li BuildOpts.Observer->compareBitwiseEquality(B,
718*67e74705SXin Li B->getOpcode() != BO_EQ);
719*67e74705SXin Li TryResult(B->getOpcode() != BO_EQ);
720*67e74705SXin Li }
721*67e74705SXin Li } else if (BoolExpr->isKnownToHaveBooleanValue()) {
722*67e74705SXin Li llvm::APInt IntValue = IntLiteral->getValue();
723*67e74705SXin Li if ((IntValue == 1) || (IntValue == 0)) {
724*67e74705SXin Li return TryResult();
725*67e74705SXin Li }
726*67e74705SXin Li return TryResult(B->getOpcode() != BO_EQ);
727*67e74705SXin Li }
728*67e74705SXin Li
729*67e74705SXin Li return TryResult();
730*67e74705SXin Li }
731*67e74705SXin Li
analyzeLogicOperatorCondition(BinaryOperatorKind Relation,const llvm::APSInt & Value1,const llvm::APSInt & Value2)732*67e74705SXin Li TryResult analyzeLogicOperatorCondition(BinaryOperatorKind Relation,
733*67e74705SXin Li const llvm::APSInt &Value1,
734*67e74705SXin Li const llvm::APSInt &Value2) {
735*67e74705SXin Li assert(Value1.isSigned() == Value2.isSigned());
736*67e74705SXin Li switch (Relation) {
737*67e74705SXin Li default:
738*67e74705SXin Li return TryResult();
739*67e74705SXin Li case BO_EQ:
740*67e74705SXin Li return TryResult(Value1 == Value2);
741*67e74705SXin Li case BO_NE:
742*67e74705SXin Li return TryResult(Value1 != Value2);
743*67e74705SXin Li case BO_LT:
744*67e74705SXin Li return TryResult(Value1 < Value2);
745*67e74705SXin Li case BO_LE:
746*67e74705SXin Li return TryResult(Value1 <= Value2);
747*67e74705SXin Li case BO_GT:
748*67e74705SXin Li return TryResult(Value1 > Value2);
749*67e74705SXin Li case BO_GE:
750*67e74705SXin Li return TryResult(Value1 >= Value2);
751*67e74705SXin Li }
752*67e74705SXin Li }
753*67e74705SXin Li
754*67e74705SXin Li /// \brief Find a pair of comparison expressions with or without parentheses
755*67e74705SXin Li /// with a shared variable and constants and a logical operator between them
756*67e74705SXin Li /// that always evaluates to either true or false.
757*67e74705SXin Li /// e.g. if (x != 3 || x != 4)
checkIncorrectLogicOperator(const BinaryOperator * B)758*67e74705SXin Li TryResult checkIncorrectLogicOperator(const BinaryOperator *B) {
759*67e74705SXin Li assert(B->isLogicalOp());
760*67e74705SXin Li const BinaryOperator *LHS =
761*67e74705SXin Li dyn_cast<BinaryOperator>(B->getLHS()->IgnoreParens());
762*67e74705SXin Li const BinaryOperator *RHS =
763*67e74705SXin Li dyn_cast<BinaryOperator>(B->getRHS()->IgnoreParens());
764*67e74705SXin Li if (!LHS || !RHS)
765*67e74705SXin Li return TryResult();
766*67e74705SXin Li
767*67e74705SXin Li if (!LHS->isComparisonOp() || !RHS->isComparisonOp())
768*67e74705SXin Li return TryResult();
769*67e74705SXin Li
770*67e74705SXin Li const DeclRefExpr *Decl1;
771*67e74705SXin Li const Expr *Expr1;
772*67e74705SXin Li BinaryOperatorKind BO1;
773*67e74705SXin Li std::tie(Decl1, BO1, Expr1) = tryNormalizeBinaryOperator(LHS);
774*67e74705SXin Li
775*67e74705SXin Li if (!Decl1 || !Expr1)
776*67e74705SXin Li return TryResult();
777*67e74705SXin Li
778*67e74705SXin Li const DeclRefExpr *Decl2;
779*67e74705SXin Li const Expr *Expr2;
780*67e74705SXin Li BinaryOperatorKind BO2;
781*67e74705SXin Li std::tie(Decl2, BO2, Expr2) = tryNormalizeBinaryOperator(RHS);
782*67e74705SXin Li
783*67e74705SXin Li if (!Decl2 || !Expr2)
784*67e74705SXin Li return TryResult();
785*67e74705SXin Li
786*67e74705SXin Li // Check that it is the same variable on both sides.
787*67e74705SXin Li if (Decl1->getDecl() != Decl2->getDecl())
788*67e74705SXin Li return TryResult();
789*67e74705SXin Li
790*67e74705SXin Li // Make sure the user's intent is clear (e.g. they're comparing against two
791*67e74705SXin Li // int literals, or two things from the same enum)
792*67e74705SXin Li if (!areExprTypesCompatible(Expr1, Expr2))
793*67e74705SXin Li return TryResult();
794*67e74705SXin Li
795*67e74705SXin Li llvm::APSInt L1, L2;
796*67e74705SXin Li
797*67e74705SXin Li if (!Expr1->EvaluateAsInt(L1, *Context) ||
798*67e74705SXin Li !Expr2->EvaluateAsInt(L2, *Context))
799*67e74705SXin Li return TryResult();
800*67e74705SXin Li
801*67e74705SXin Li // Can't compare signed with unsigned or with different bit width.
802*67e74705SXin Li if (L1.isSigned() != L2.isSigned() || L1.getBitWidth() != L2.getBitWidth())
803*67e74705SXin Li return TryResult();
804*67e74705SXin Li
805*67e74705SXin Li // Values that will be used to determine if result of logical
806*67e74705SXin Li // operator is always true/false
807*67e74705SXin Li const llvm::APSInt Values[] = {
808*67e74705SXin Li // Value less than both Value1 and Value2
809*67e74705SXin Li llvm::APSInt::getMinValue(L1.getBitWidth(), L1.isUnsigned()),
810*67e74705SXin Li // L1
811*67e74705SXin Li L1,
812*67e74705SXin Li // Value between Value1 and Value2
813*67e74705SXin Li ((L1 < L2) ? L1 : L2) + llvm::APSInt(llvm::APInt(L1.getBitWidth(), 1),
814*67e74705SXin Li L1.isUnsigned()),
815*67e74705SXin Li // L2
816*67e74705SXin Li L2,
817*67e74705SXin Li // Value greater than both Value1 and Value2
818*67e74705SXin Li llvm::APSInt::getMaxValue(L1.getBitWidth(), L1.isUnsigned()),
819*67e74705SXin Li };
820*67e74705SXin Li
821*67e74705SXin Li // Check whether expression is always true/false by evaluating the following
822*67e74705SXin Li // * variable x is less than the smallest literal.
823*67e74705SXin Li // * variable x is equal to the smallest literal.
824*67e74705SXin Li // * Variable x is between smallest and largest literal.
825*67e74705SXin Li // * Variable x is equal to the largest literal.
826*67e74705SXin Li // * Variable x is greater than largest literal.
827*67e74705SXin Li bool AlwaysTrue = true, AlwaysFalse = true;
828*67e74705SXin Li for (const llvm::APSInt &Value : Values) {
829*67e74705SXin Li TryResult Res1, Res2;
830*67e74705SXin Li Res1 = analyzeLogicOperatorCondition(BO1, Value, L1);
831*67e74705SXin Li Res2 = analyzeLogicOperatorCondition(BO2, Value, L2);
832*67e74705SXin Li
833*67e74705SXin Li if (!Res1.isKnown() || !Res2.isKnown())
834*67e74705SXin Li return TryResult();
835*67e74705SXin Li
836*67e74705SXin Li if (B->getOpcode() == BO_LAnd) {
837*67e74705SXin Li AlwaysTrue &= (Res1.isTrue() && Res2.isTrue());
838*67e74705SXin Li AlwaysFalse &= !(Res1.isTrue() && Res2.isTrue());
839*67e74705SXin Li } else {
840*67e74705SXin Li AlwaysTrue &= (Res1.isTrue() || Res2.isTrue());
841*67e74705SXin Li AlwaysFalse &= !(Res1.isTrue() || Res2.isTrue());
842*67e74705SXin Li }
843*67e74705SXin Li }
844*67e74705SXin Li
845*67e74705SXin Li if (AlwaysTrue || AlwaysFalse) {
846*67e74705SXin Li if (BuildOpts.Observer)
847*67e74705SXin Li BuildOpts.Observer->compareAlwaysTrue(B, AlwaysTrue);
848*67e74705SXin Li return TryResult(AlwaysTrue);
849*67e74705SXin Li }
850*67e74705SXin Li return TryResult();
851*67e74705SXin Li }
852*67e74705SXin Li
853*67e74705SXin Li /// Try and evaluate an expression to an integer constant.
tryEvaluate(Expr * S,Expr::EvalResult & outResult)854*67e74705SXin Li bool tryEvaluate(Expr *S, Expr::EvalResult &outResult) {
855*67e74705SXin Li if (!BuildOpts.PruneTriviallyFalseEdges)
856*67e74705SXin Li return false;
857*67e74705SXin Li return !S->isTypeDependent() &&
858*67e74705SXin Li !S->isValueDependent() &&
859*67e74705SXin Li S->EvaluateAsRValue(outResult, *Context);
860*67e74705SXin Li }
861*67e74705SXin Li
862*67e74705SXin Li /// tryEvaluateBool - Try and evaluate the Stmt and return 0 or 1
863*67e74705SXin Li /// if we can evaluate to a known value, otherwise return -1.
tryEvaluateBool(Expr * S)864*67e74705SXin Li TryResult tryEvaluateBool(Expr *S) {
865*67e74705SXin Li if (!BuildOpts.PruneTriviallyFalseEdges ||
866*67e74705SXin Li S->isTypeDependent() || S->isValueDependent())
867*67e74705SXin Li return TryResult();
868*67e74705SXin Li
869*67e74705SXin Li if (BinaryOperator *Bop = dyn_cast<BinaryOperator>(S)) {
870*67e74705SXin Li if (Bop->isLogicalOp()) {
871*67e74705SXin Li // Check the cache first.
872*67e74705SXin Li CachedBoolEvalsTy::iterator I = CachedBoolEvals.find(S);
873*67e74705SXin Li if (I != CachedBoolEvals.end())
874*67e74705SXin Li return I->second; // already in map;
875*67e74705SXin Li
876*67e74705SXin Li // Retrieve result at first, or the map might be updated.
877*67e74705SXin Li TryResult Result = evaluateAsBooleanConditionNoCache(S);
878*67e74705SXin Li CachedBoolEvals[S] = Result; // update or insert
879*67e74705SXin Li return Result;
880*67e74705SXin Li }
881*67e74705SXin Li else {
882*67e74705SXin Li switch (Bop->getOpcode()) {
883*67e74705SXin Li default: break;
884*67e74705SXin Li // For 'x & 0' and 'x * 0', we can determine that
885*67e74705SXin Li // the value is always false.
886*67e74705SXin Li case BO_Mul:
887*67e74705SXin Li case BO_And: {
888*67e74705SXin Li // If either operand is zero, we know the value
889*67e74705SXin Li // must be false.
890*67e74705SXin Li llvm::APSInt IntVal;
891*67e74705SXin Li if (Bop->getLHS()->EvaluateAsInt(IntVal, *Context)) {
892*67e74705SXin Li if (!IntVal.getBoolValue()) {
893*67e74705SXin Li return TryResult(false);
894*67e74705SXin Li }
895*67e74705SXin Li }
896*67e74705SXin Li if (Bop->getRHS()->EvaluateAsInt(IntVal, *Context)) {
897*67e74705SXin Li if (!IntVal.getBoolValue()) {
898*67e74705SXin Li return TryResult(false);
899*67e74705SXin Li }
900*67e74705SXin Li }
901*67e74705SXin Li }
902*67e74705SXin Li break;
903*67e74705SXin Li }
904*67e74705SXin Li }
905*67e74705SXin Li }
906*67e74705SXin Li
907*67e74705SXin Li return evaluateAsBooleanConditionNoCache(S);
908*67e74705SXin Li }
909*67e74705SXin Li
910*67e74705SXin Li /// \brief Evaluate as boolean \param E without using the cache.
evaluateAsBooleanConditionNoCache(Expr * E)911*67e74705SXin Li TryResult evaluateAsBooleanConditionNoCache(Expr *E) {
912*67e74705SXin Li if (BinaryOperator *Bop = dyn_cast<BinaryOperator>(E)) {
913*67e74705SXin Li if (Bop->isLogicalOp()) {
914*67e74705SXin Li TryResult LHS = tryEvaluateBool(Bop->getLHS());
915*67e74705SXin Li if (LHS.isKnown()) {
916*67e74705SXin Li // We were able to evaluate the LHS, see if we can get away with not
917*67e74705SXin Li // evaluating the RHS: 0 && X -> 0, 1 || X -> 1
918*67e74705SXin Li if (LHS.isTrue() == (Bop->getOpcode() == BO_LOr))
919*67e74705SXin Li return LHS.isTrue();
920*67e74705SXin Li
921*67e74705SXin Li TryResult RHS = tryEvaluateBool(Bop->getRHS());
922*67e74705SXin Li if (RHS.isKnown()) {
923*67e74705SXin Li if (Bop->getOpcode() == BO_LOr)
924*67e74705SXin Li return LHS.isTrue() || RHS.isTrue();
925*67e74705SXin Li else
926*67e74705SXin Li return LHS.isTrue() && RHS.isTrue();
927*67e74705SXin Li }
928*67e74705SXin Li } else {
929*67e74705SXin Li TryResult RHS = tryEvaluateBool(Bop->getRHS());
930*67e74705SXin Li if (RHS.isKnown()) {
931*67e74705SXin Li // We can't evaluate the LHS; however, sometimes the result
932*67e74705SXin Li // is determined by the RHS: X && 0 -> 0, X || 1 -> 1.
933*67e74705SXin Li if (RHS.isTrue() == (Bop->getOpcode() == BO_LOr))
934*67e74705SXin Li return RHS.isTrue();
935*67e74705SXin Li } else {
936*67e74705SXin Li TryResult BopRes = checkIncorrectLogicOperator(Bop);
937*67e74705SXin Li if (BopRes.isKnown())
938*67e74705SXin Li return BopRes.isTrue();
939*67e74705SXin Li }
940*67e74705SXin Li }
941*67e74705SXin Li
942*67e74705SXin Li return TryResult();
943*67e74705SXin Li } else if (Bop->isEqualityOp()) {
944*67e74705SXin Li TryResult BopRes = checkIncorrectEqualityOperator(Bop);
945*67e74705SXin Li if (BopRes.isKnown())
946*67e74705SXin Li return BopRes.isTrue();
947*67e74705SXin Li } else if (Bop->isRelationalOp()) {
948*67e74705SXin Li TryResult BopRes = checkIncorrectRelationalOperator(Bop);
949*67e74705SXin Li if (BopRes.isKnown())
950*67e74705SXin Li return BopRes.isTrue();
951*67e74705SXin Li }
952*67e74705SXin Li }
953*67e74705SXin Li
954*67e74705SXin Li bool Result;
955*67e74705SXin Li if (E->EvaluateAsBooleanCondition(Result, *Context))
956*67e74705SXin Li return Result;
957*67e74705SXin Li
958*67e74705SXin Li return TryResult();
959*67e74705SXin Li }
960*67e74705SXin Li
961*67e74705SXin Li };
962*67e74705SXin Li
alwaysAdd(CFGBuilder & builder,const Stmt * stmt) const963*67e74705SXin Li inline bool AddStmtChoice::alwaysAdd(CFGBuilder &builder,
964*67e74705SXin Li const Stmt *stmt) const {
965*67e74705SXin Li return builder.alwaysAdd(stmt) || kind == AlwaysAdd;
966*67e74705SXin Li }
967*67e74705SXin Li
alwaysAdd(const Stmt * stmt)968*67e74705SXin Li bool CFGBuilder::alwaysAdd(const Stmt *stmt) {
969*67e74705SXin Li bool shouldAdd = BuildOpts.alwaysAdd(stmt);
970*67e74705SXin Li
971*67e74705SXin Li if (!BuildOpts.forcedBlkExprs)
972*67e74705SXin Li return shouldAdd;
973*67e74705SXin Li
974*67e74705SXin Li if (lastLookup == stmt) {
975*67e74705SXin Li if (cachedEntry) {
976*67e74705SXin Li assert(cachedEntry->first == stmt);
977*67e74705SXin Li return true;
978*67e74705SXin Li }
979*67e74705SXin Li return shouldAdd;
980*67e74705SXin Li }
981*67e74705SXin Li
982*67e74705SXin Li lastLookup = stmt;
983*67e74705SXin Li
984*67e74705SXin Li // Perform the lookup!
985*67e74705SXin Li CFG::BuildOptions::ForcedBlkExprs *fb = *BuildOpts.forcedBlkExprs;
986*67e74705SXin Li
987*67e74705SXin Li if (!fb) {
988*67e74705SXin Li // No need to update 'cachedEntry', since it will always be null.
989*67e74705SXin Li assert(!cachedEntry);
990*67e74705SXin Li return shouldAdd;
991*67e74705SXin Li }
992*67e74705SXin Li
993*67e74705SXin Li CFG::BuildOptions::ForcedBlkExprs::iterator itr = fb->find(stmt);
994*67e74705SXin Li if (itr == fb->end()) {
995*67e74705SXin Li cachedEntry = nullptr;
996*67e74705SXin Li return shouldAdd;
997*67e74705SXin Li }
998*67e74705SXin Li
999*67e74705SXin Li cachedEntry = &*itr;
1000*67e74705SXin Li return true;
1001*67e74705SXin Li }
1002*67e74705SXin Li
1003*67e74705SXin Li // FIXME: Add support for dependent-sized array types in C++?
1004*67e74705SXin Li // Does it even make sense to build a CFG for an uninstantiated template?
FindVA(const Type * t)1005*67e74705SXin Li static const VariableArrayType *FindVA(const Type *t) {
1006*67e74705SXin Li while (const ArrayType *vt = dyn_cast<ArrayType>(t)) {
1007*67e74705SXin Li if (const VariableArrayType *vat = dyn_cast<VariableArrayType>(vt))
1008*67e74705SXin Li if (vat->getSizeExpr())
1009*67e74705SXin Li return vat;
1010*67e74705SXin Li
1011*67e74705SXin Li t = vt->getElementType().getTypePtr();
1012*67e74705SXin Li }
1013*67e74705SXin Li
1014*67e74705SXin Li return nullptr;
1015*67e74705SXin Li }
1016*67e74705SXin Li
1017*67e74705SXin Li /// BuildCFG - Constructs a CFG from an AST (a Stmt*). The AST can represent an
1018*67e74705SXin Li /// arbitrary statement. Examples include a single expression or a function
1019*67e74705SXin Li /// body (compound statement). The ownership of the returned CFG is
1020*67e74705SXin Li /// transferred to the caller. If CFG construction fails, this method returns
1021*67e74705SXin Li /// NULL.
buildCFG(const Decl * D,Stmt * Statement)1022*67e74705SXin Li std::unique_ptr<CFG> CFGBuilder::buildCFG(const Decl *D, Stmt *Statement) {
1023*67e74705SXin Li assert(cfg.get());
1024*67e74705SXin Li if (!Statement)
1025*67e74705SXin Li return nullptr;
1026*67e74705SXin Li
1027*67e74705SXin Li // Create an empty block that will serve as the exit block for the CFG. Since
1028*67e74705SXin Li // this is the first block added to the CFG, it will be implicitly registered
1029*67e74705SXin Li // as the exit block.
1030*67e74705SXin Li Succ = createBlock();
1031*67e74705SXin Li assert(Succ == &cfg->getExit());
1032*67e74705SXin Li Block = nullptr; // the EXIT block is empty. Create all other blocks lazily.
1033*67e74705SXin Li
1034*67e74705SXin Li if (BuildOpts.AddImplicitDtors)
1035*67e74705SXin Li if (const CXXDestructorDecl *DD = dyn_cast_or_null<CXXDestructorDecl>(D))
1036*67e74705SXin Li addImplicitDtorsForDestructor(DD);
1037*67e74705SXin Li
1038*67e74705SXin Li // Visit the statements and create the CFG.
1039*67e74705SXin Li CFGBlock *B = addStmt(Statement);
1040*67e74705SXin Li
1041*67e74705SXin Li if (badCFG)
1042*67e74705SXin Li return nullptr;
1043*67e74705SXin Li
1044*67e74705SXin Li // For C++ constructor add initializers to CFG.
1045*67e74705SXin Li if (const CXXConstructorDecl *CD = dyn_cast_or_null<CXXConstructorDecl>(D)) {
1046*67e74705SXin Li for (auto *I : llvm::reverse(CD->inits())) {
1047*67e74705SXin Li B = addInitializer(I);
1048*67e74705SXin Li if (badCFG)
1049*67e74705SXin Li return nullptr;
1050*67e74705SXin Li }
1051*67e74705SXin Li }
1052*67e74705SXin Li
1053*67e74705SXin Li if (B)
1054*67e74705SXin Li Succ = B;
1055*67e74705SXin Li
1056*67e74705SXin Li // Backpatch the gotos whose label -> block mappings we didn't know when we
1057*67e74705SXin Li // encountered them.
1058*67e74705SXin Li for (BackpatchBlocksTy::iterator I = BackpatchBlocks.begin(),
1059*67e74705SXin Li E = BackpatchBlocks.end(); I != E; ++I ) {
1060*67e74705SXin Li
1061*67e74705SXin Li CFGBlock *B = I->block;
1062*67e74705SXin Li const GotoStmt *G = cast<GotoStmt>(B->getTerminator());
1063*67e74705SXin Li LabelMapTy::iterator LI = LabelMap.find(G->getLabel());
1064*67e74705SXin Li
1065*67e74705SXin Li // If there is no target for the goto, then we are looking at an
1066*67e74705SXin Li // incomplete AST. Handle this by not registering a successor.
1067*67e74705SXin Li if (LI == LabelMap.end()) continue;
1068*67e74705SXin Li
1069*67e74705SXin Li JumpTarget JT = LI->second;
1070*67e74705SXin Li prependAutomaticObjDtorsWithTerminator(B, I->scopePosition,
1071*67e74705SXin Li JT.scopePosition);
1072*67e74705SXin Li addSuccessor(B, JT.block);
1073*67e74705SXin Li }
1074*67e74705SXin Li
1075*67e74705SXin Li // Add successors to the Indirect Goto Dispatch block (if we have one).
1076*67e74705SXin Li if (CFGBlock *B = cfg->getIndirectGotoBlock())
1077*67e74705SXin Li for (LabelSetTy::iterator I = AddressTakenLabels.begin(),
1078*67e74705SXin Li E = AddressTakenLabels.end(); I != E; ++I ) {
1079*67e74705SXin Li
1080*67e74705SXin Li // Lookup the target block.
1081*67e74705SXin Li LabelMapTy::iterator LI = LabelMap.find(*I);
1082*67e74705SXin Li
1083*67e74705SXin Li // If there is no target block that contains label, then we are looking
1084*67e74705SXin Li // at an incomplete AST. Handle this by not registering a successor.
1085*67e74705SXin Li if (LI == LabelMap.end()) continue;
1086*67e74705SXin Li
1087*67e74705SXin Li addSuccessor(B, LI->second.block);
1088*67e74705SXin Li }
1089*67e74705SXin Li
1090*67e74705SXin Li // Create an empty entry block that has no predecessors.
1091*67e74705SXin Li cfg->setEntry(createBlock());
1092*67e74705SXin Li
1093*67e74705SXin Li return std::move(cfg);
1094*67e74705SXin Li }
1095*67e74705SXin Li
1096*67e74705SXin Li /// createBlock - Used to lazily create blocks that are connected
1097*67e74705SXin Li /// to the current (global) succcessor.
createBlock(bool add_successor)1098*67e74705SXin Li CFGBlock *CFGBuilder::createBlock(bool add_successor) {
1099*67e74705SXin Li CFGBlock *B = cfg->createBlock();
1100*67e74705SXin Li if (add_successor && Succ)
1101*67e74705SXin Li addSuccessor(B, Succ);
1102*67e74705SXin Li return B;
1103*67e74705SXin Li }
1104*67e74705SXin Li
1105*67e74705SXin Li /// createNoReturnBlock - Used to create a block is a 'noreturn' point in the
1106*67e74705SXin Li /// CFG. It is *not* connected to the current (global) successor, and instead
1107*67e74705SXin Li /// directly tied to the exit block in order to be reachable.
createNoReturnBlock()1108*67e74705SXin Li CFGBlock *CFGBuilder::createNoReturnBlock() {
1109*67e74705SXin Li CFGBlock *B = createBlock(false);
1110*67e74705SXin Li B->setHasNoReturnElement();
1111*67e74705SXin Li addSuccessor(B, &cfg->getExit(), Succ);
1112*67e74705SXin Li return B;
1113*67e74705SXin Li }
1114*67e74705SXin Li
1115*67e74705SXin Li /// addInitializer - Add C++ base or member initializer element to CFG.
addInitializer(CXXCtorInitializer * I)1116*67e74705SXin Li CFGBlock *CFGBuilder::addInitializer(CXXCtorInitializer *I) {
1117*67e74705SXin Li if (!BuildOpts.AddInitializers)
1118*67e74705SXin Li return Block;
1119*67e74705SXin Li
1120*67e74705SXin Li bool HasTemporaries = false;
1121*67e74705SXin Li
1122*67e74705SXin Li // Destructors of temporaries in initialization expression should be called
1123*67e74705SXin Li // after initialization finishes.
1124*67e74705SXin Li Expr *Init = I->getInit();
1125*67e74705SXin Li if (Init) {
1126*67e74705SXin Li HasTemporaries = isa<ExprWithCleanups>(Init);
1127*67e74705SXin Li
1128*67e74705SXin Li if (BuildOpts.AddTemporaryDtors && HasTemporaries) {
1129*67e74705SXin Li // Generate destructors for temporaries in initialization expression.
1130*67e74705SXin Li TempDtorContext Context;
1131*67e74705SXin Li VisitForTemporaryDtors(cast<ExprWithCleanups>(Init)->getSubExpr(),
1132*67e74705SXin Li /*BindToTemporary=*/false, Context);
1133*67e74705SXin Li }
1134*67e74705SXin Li }
1135*67e74705SXin Li
1136*67e74705SXin Li autoCreateBlock();
1137*67e74705SXin Li appendInitializer(Block, I);
1138*67e74705SXin Li
1139*67e74705SXin Li if (Init) {
1140*67e74705SXin Li if (HasTemporaries) {
1141*67e74705SXin Li // For expression with temporaries go directly to subexpression to omit
1142*67e74705SXin Li // generating destructors for the second time.
1143*67e74705SXin Li return Visit(cast<ExprWithCleanups>(Init)->getSubExpr());
1144*67e74705SXin Li }
1145*67e74705SXin Li if (BuildOpts.AddCXXDefaultInitExprInCtors) {
1146*67e74705SXin Li if (CXXDefaultInitExpr *Default = dyn_cast<CXXDefaultInitExpr>(Init)) {
1147*67e74705SXin Li // In general, appending the expression wrapped by a CXXDefaultInitExpr
1148*67e74705SXin Li // may cause the same Expr to appear more than once in the CFG. Doing it
1149*67e74705SXin Li // here is safe because there's only one initializer per field.
1150*67e74705SXin Li autoCreateBlock();
1151*67e74705SXin Li appendStmt(Block, Default);
1152*67e74705SXin Li if (Stmt *Child = Default->getExpr())
1153*67e74705SXin Li if (CFGBlock *R = Visit(Child))
1154*67e74705SXin Li Block = R;
1155*67e74705SXin Li return Block;
1156*67e74705SXin Li }
1157*67e74705SXin Li }
1158*67e74705SXin Li return Visit(Init);
1159*67e74705SXin Li }
1160*67e74705SXin Li
1161*67e74705SXin Li return Block;
1162*67e74705SXin Li }
1163*67e74705SXin Li
1164*67e74705SXin Li /// \brief Retrieve the type of the temporary object whose lifetime was
1165*67e74705SXin Li /// extended by a local reference with the given initializer.
getReferenceInitTemporaryType(ASTContext & Context,const Expr * Init)1166*67e74705SXin Li static QualType getReferenceInitTemporaryType(ASTContext &Context,
1167*67e74705SXin Li const Expr *Init) {
1168*67e74705SXin Li while (true) {
1169*67e74705SXin Li // Skip parentheses.
1170*67e74705SXin Li Init = Init->IgnoreParens();
1171*67e74705SXin Li
1172*67e74705SXin Li // Skip through cleanups.
1173*67e74705SXin Li if (const ExprWithCleanups *EWC = dyn_cast<ExprWithCleanups>(Init)) {
1174*67e74705SXin Li Init = EWC->getSubExpr();
1175*67e74705SXin Li continue;
1176*67e74705SXin Li }
1177*67e74705SXin Li
1178*67e74705SXin Li // Skip through the temporary-materialization expression.
1179*67e74705SXin Li if (const MaterializeTemporaryExpr *MTE
1180*67e74705SXin Li = dyn_cast<MaterializeTemporaryExpr>(Init)) {
1181*67e74705SXin Li Init = MTE->GetTemporaryExpr();
1182*67e74705SXin Li continue;
1183*67e74705SXin Li }
1184*67e74705SXin Li
1185*67e74705SXin Li // Skip derived-to-base and no-op casts.
1186*67e74705SXin Li if (const CastExpr *CE = dyn_cast<CastExpr>(Init)) {
1187*67e74705SXin Li if ((CE->getCastKind() == CK_DerivedToBase ||
1188*67e74705SXin Li CE->getCastKind() == CK_UncheckedDerivedToBase ||
1189*67e74705SXin Li CE->getCastKind() == CK_NoOp) &&
1190*67e74705SXin Li Init->getType()->isRecordType()) {
1191*67e74705SXin Li Init = CE->getSubExpr();
1192*67e74705SXin Li continue;
1193*67e74705SXin Li }
1194*67e74705SXin Li }
1195*67e74705SXin Li
1196*67e74705SXin Li // Skip member accesses into rvalues.
1197*67e74705SXin Li if (const MemberExpr *ME = dyn_cast<MemberExpr>(Init)) {
1198*67e74705SXin Li if (!ME->isArrow() && ME->getBase()->isRValue()) {
1199*67e74705SXin Li Init = ME->getBase();
1200*67e74705SXin Li continue;
1201*67e74705SXin Li }
1202*67e74705SXin Li }
1203*67e74705SXin Li
1204*67e74705SXin Li break;
1205*67e74705SXin Li }
1206*67e74705SXin Li
1207*67e74705SXin Li return Init->getType();
1208*67e74705SXin Li }
1209*67e74705SXin Li
1210*67e74705SXin Li /// addAutomaticObjDtors - Add to current block automatic objects destructors
1211*67e74705SXin Li /// for objects in range of local scope positions. Use S as trigger statement
1212*67e74705SXin Li /// for destructors.
addAutomaticObjDtors(LocalScope::const_iterator B,LocalScope::const_iterator E,Stmt * S)1213*67e74705SXin Li void CFGBuilder::addAutomaticObjDtors(LocalScope::const_iterator B,
1214*67e74705SXin Li LocalScope::const_iterator E, Stmt *S) {
1215*67e74705SXin Li if (!BuildOpts.AddImplicitDtors)
1216*67e74705SXin Li return;
1217*67e74705SXin Li
1218*67e74705SXin Li if (B == E)
1219*67e74705SXin Li return;
1220*67e74705SXin Li
1221*67e74705SXin Li // We need to append the destructors in reverse order, but any one of them
1222*67e74705SXin Li // may be a no-return destructor which changes the CFG. As a result, buffer
1223*67e74705SXin Li // this sequence up and replay them in reverse order when appending onto the
1224*67e74705SXin Li // CFGBlock(s).
1225*67e74705SXin Li SmallVector<VarDecl*, 10> Decls;
1226*67e74705SXin Li Decls.reserve(B.distance(E));
1227*67e74705SXin Li for (LocalScope::const_iterator I = B; I != E; ++I)
1228*67e74705SXin Li Decls.push_back(*I);
1229*67e74705SXin Li
1230*67e74705SXin Li for (SmallVectorImpl<VarDecl*>::reverse_iterator I = Decls.rbegin(),
1231*67e74705SXin Li E = Decls.rend();
1232*67e74705SXin Li I != E; ++I) {
1233*67e74705SXin Li // If this destructor is marked as a no-return destructor, we need to
1234*67e74705SXin Li // create a new block for the destructor which does not have as a successor
1235*67e74705SXin Li // anything built thus far: control won't flow out of this block.
1236*67e74705SXin Li QualType Ty = (*I)->getType();
1237*67e74705SXin Li if (Ty->isReferenceType()) {
1238*67e74705SXin Li Ty = getReferenceInitTemporaryType(*Context, (*I)->getInit());
1239*67e74705SXin Li }
1240*67e74705SXin Li Ty = Context->getBaseElementType(Ty);
1241*67e74705SXin Li
1242*67e74705SXin Li if (Ty->getAsCXXRecordDecl()->isAnyDestructorNoReturn())
1243*67e74705SXin Li Block = createNoReturnBlock();
1244*67e74705SXin Li else
1245*67e74705SXin Li autoCreateBlock();
1246*67e74705SXin Li
1247*67e74705SXin Li appendAutomaticObjDtor(Block, *I, S);
1248*67e74705SXin Li }
1249*67e74705SXin Li }
1250*67e74705SXin Li
1251*67e74705SXin Li /// addImplicitDtorsForDestructor - Add implicit destructors generated for
1252*67e74705SXin Li /// base and member objects in destructor.
addImplicitDtorsForDestructor(const CXXDestructorDecl * DD)1253*67e74705SXin Li void CFGBuilder::addImplicitDtorsForDestructor(const CXXDestructorDecl *DD) {
1254*67e74705SXin Li assert (BuildOpts.AddImplicitDtors
1255*67e74705SXin Li && "Can be called only when dtors should be added");
1256*67e74705SXin Li const CXXRecordDecl *RD = DD->getParent();
1257*67e74705SXin Li
1258*67e74705SXin Li // At the end destroy virtual base objects.
1259*67e74705SXin Li for (const auto &VI : RD->vbases()) {
1260*67e74705SXin Li const CXXRecordDecl *CD = VI.getType()->getAsCXXRecordDecl();
1261*67e74705SXin Li if (!CD->hasTrivialDestructor()) {
1262*67e74705SXin Li autoCreateBlock();
1263*67e74705SXin Li appendBaseDtor(Block, &VI);
1264*67e74705SXin Li }
1265*67e74705SXin Li }
1266*67e74705SXin Li
1267*67e74705SXin Li // Before virtual bases destroy direct base objects.
1268*67e74705SXin Li for (const auto &BI : RD->bases()) {
1269*67e74705SXin Li if (!BI.isVirtual()) {
1270*67e74705SXin Li const CXXRecordDecl *CD = BI.getType()->getAsCXXRecordDecl();
1271*67e74705SXin Li if (!CD->hasTrivialDestructor()) {
1272*67e74705SXin Li autoCreateBlock();
1273*67e74705SXin Li appendBaseDtor(Block, &BI);
1274*67e74705SXin Li }
1275*67e74705SXin Li }
1276*67e74705SXin Li }
1277*67e74705SXin Li
1278*67e74705SXin Li // First destroy member objects.
1279*67e74705SXin Li for (auto *FI : RD->fields()) {
1280*67e74705SXin Li // Check for constant size array. Set type to array element type.
1281*67e74705SXin Li QualType QT = FI->getType();
1282*67e74705SXin Li if (const ConstantArrayType *AT = Context->getAsConstantArrayType(QT)) {
1283*67e74705SXin Li if (AT->getSize() == 0)
1284*67e74705SXin Li continue;
1285*67e74705SXin Li QT = AT->getElementType();
1286*67e74705SXin Li }
1287*67e74705SXin Li
1288*67e74705SXin Li if (const CXXRecordDecl *CD = QT->getAsCXXRecordDecl())
1289*67e74705SXin Li if (!CD->hasTrivialDestructor()) {
1290*67e74705SXin Li autoCreateBlock();
1291*67e74705SXin Li appendMemberDtor(Block, FI);
1292*67e74705SXin Li }
1293*67e74705SXin Li }
1294*67e74705SXin Li }
1295*67e74705SXin Li
1296*67e74705SXin Li /// createOrReuseLocalScope - If Scope is NULL create new LocalScope. Either
1297*67e74705SXin Li /// way return valid LocalScope object.
createOrReuseLocalScope(LocalScope * Scope)1298*67e74705SXin Li LocalScope* CFGBuilder::createOrReuseLocalScope(LocalScope* Scope) {
1299*67e74705SXin Li if (Scope)
1300*67e74705SXin Li return Scope;
1301*67e74705SXin Li llvm::BumpPtrAllocator &alloc = cfg->getAllocator();
1302*67e74705SXin Li return new (alloc.Allocate<LocalScope>())
1303*67e74705SXin Li LocalScope(BumpVectorContext(alloc), ScopePos);
1304*67e74705SXin Li }
1305*67e74705SXin Li
1306*67e74705SXin Li /// addLocalScopeForStmt - Add LocalScope to local scopes tree for statement
1307*67e74705SXin Li /// that should create implicit scope (e.g. if/else substatements).
addLocalScopeForStmt(Stmt * S)1308*67e74705SXin Li void CFGBuilder::addLocalScopeForStmt(Stmt *S) {
1309*67e74705SXin Li if (!BuildOpts.AddImplicitDtors)
1310*67e74705SXin Li return;
1311*67e74705SXin Li
1312*67e74705SXin Li LocalScope *Scope = nullptr;
1313*67e74705SXin Li
1314*67e74705SXin Li // For compound statement we will be creating explicit scope.
1315*67e74705SXin Li if (CompoundStmt *CS = dyn_cast<CompoundStmt>(S)) {
1316*67e74705SXin Li for (auto *BI : CS->body()) {
1317*67e74705SXin Li Stmt *SI = BI->stripLabelLikeStatements();
1318*67e74705SXin Li if (DeclStmt *DS = dyn_cast<DeclStmt>(SI))
1319*67e74705SXin Li Scope = addLocalScopeForDeclStmt(DS, Scope);
1320*67e74705SXin Li }
1321*67e74705SXin Li return;
1322*67e74705SXin Li }
1323*67e74705SXin Li
1324*67e74705SXin Li // For any other statement scope will be implicit and as such will be
1325*67e74705SXin Li // interesting only for DeclStmt.
1326*67e74705SXin Li if (DeclStmt *DS = dyn_cast<DeclStmt>(S->stripLabelLikeStatements()))
1327*67e74705SXin Li addLocalScopeForDeclStmt(DS);
1328*67e74705SXin Li }
1329*67e74705SXin Li
1330*67e74705SXin Li /// addLocalScopeForDeclStmt - Add LocalScope for declaration statement. Will
1331*67e74705SXin Li /// reuse Scope if not NULL.
addLocalScopeForDeclStmt(DeclStmt * DS,LocalScope * Scope)1332*67e74705SXin Li LocalScope* CFGBuilder::addLocalScopeForDeclStmt(DeclStmt *DS,
1333*67e74705SXin Li LocalScope* Scope) {
1334*67e74705SXin Li if (!BuildOpts.AddImplicitDtors)
1335*67e74705SXin Li return Scope;
1336*67e74705SXin Li
1337*67e74705SXin Li for (auto *DI : DS->decls())
1338*67e74705SXin Li if (VarDecl *VD = dyn_cast<VarDecl>(DI))
1339*67e74705SXin Li Scope = addLocalScopeForVarDecl(VD, Scope);
1340*67e74705SXin Li return Scope;
1341*67e74705SXin Li }
1342*67e74705SXin Li
1343*67e74705SXin Li /// addLocalScopeForVarDecl - Add LocalScope for variable declaration. It will
1344*67e74705SXin Li /// create add scope for automatic objects and temporary objects bound to
1345*67e74705SXin Li /// const reference. Will reuse Scope if not NULL.
addLocalScopeForVarDecl(VarDecl * VD,LocalScope * Scope)1346*67e74705SXin Li LocalScope* CFGBuilder::addLocalScopeForVarDecl(VarDecl *VD,
1347*67e74705SXin Li LocalScope* Scope) {
1348*67e74705SXin Li if (!BuildOpts.AddImplicitDtors)
1349*67e74705SXin Li return Scope;
1350*67e74705SXin Li
1351*67e74705SXin Li // Check if variable is local.
1352*67e74705SXin Li switch (VD->getStorageClass()) {
1353*67e74705SXin Li case SC_None:
1354*67e74705SXin Li case SC_Auto:
1355*67e74705SXin Li case SC_Register:
1356*67e74705SXin Li break;
1357*67e74705SXin Li default: return Scope;
1358*67e74705SXin Li }
1359*67e74705SXin Li
1360*67e74705SXin Li // Check for const references bound to temporary. Set type to pointee.
1361*67e74705SXin Li QualType QT = VD->getType();
1362*67e74705SXin Li if (QT.getTypePtr()->isReferenceType()) {
1363*67e74705SXin Li // Attempt to determine whether this declaration lifetime-extends a
1364*67e74705SXin Li // temporary.
1365*67e74705SXin Li //
1366*67e74705SXin Li // FIXME: This is incorrect. Non-reference declarations can lifetime-extend
1367*67e74705SXin Li // temporaries, and a single declaration can extend multiple temporaries.
1368*67e74705SXin Li // We should look at the storage duration on each nested
1369*67e74705SXin Li // MaterializeTemporaryExpr instead.
1370*67e74705SXin Li const Expr *Init = VD->getInit();
1371*67e74705SXin Li if (!Init)
1372*67e74705SXin Li return Scope;
1373*67e74705SXin Li if (const ExprWithCleanups *EWC = dyn_cast<ExprWithCleanups>(Init))
1374*67e74705SXin Li Init = EWC->getSubExpr();
1375*67e74705SXin Li if (!isa<MaterializeTemporaryExpr>(Init))
1376*67e74705SXin Li return Scope;
1377*67e74705SXin Li
1378*67e74705SXin Li // Lifetime-extending a temporary.
1379*67e74705SXin Li QT = getReferenceInitTemporaryType(*Context, Init);
1380*67e74705SXin Li }
1381*67e74705SXin Li
1382*67e74705SXin Li // Check for constant size array. Set type to array element type.
1383*67e74705SXin Li while (const ConstantArrayType *AT = Context->getAsConstantArrayType(QT)) {
1384*67e74705SXin Li if (AT->getSize() == 0)
1385*67e74705SXin Li return Scope;
1386*67e74705SXin Li QT = AT->getElementType();
1387*67e74705SXin Li }
1388*67e74705SXin Li
1389*67e74705SXin Li // Check if type is a C++ class with non-trivial destructor.
1390*67e74705SXin Li if (const CXXRecordDecl *CD = QT->getAsCXXRecordDecl())
1391*67e74705SXin Li if (!CD->hasTrivialDestructor()) {
1392*67e74705SXin Li // Add the variable to scope
1393*67e74705SXin Li Scope = createOrReuseLocalScope(Scope);
1394*67e74705SXin Li Scope->addVar(VD);
1395*67e74705SXin Li ScopePos = Scope->begin();
1396*67e74705SXin Li }
1397*67e74705SXin Li return Scope;
1398*67e74705SXin Li }
1399*67e74705SXin Li
1400*67e74705SXin Li /// addLocalScopeAndDtors - For given statement add local scope for it and
1401*67e74705SXin Li /// add destructors that will cleanup the scope. Will reuse Scope if not NULL.
addLocalScopeAndDtors(Stmt * S)1402*67e74705SXin Li void CFGBuilder::addLocalScopeAndDtors(Stmt *S) {
1403*67e74705SXin Li if (!BuildOpts.AddImplicitDtors)
1404*67e74705SXin Li return;
1405*67e74705SXin Li
1406*67e74705SXin Li LocalScope::const_iterator scopeBeginPos = ScopePos;
1407*67e74705SXin Li addLocalScopeForStmt(S);
1408*67e74705SXin Li addAutomaticObjDtors(ScopePos, scopeBeginPos, S);
1409*67e74705SXin Li }
1410*67e74705SXin Li
1411*67e74705SXin Li /// prependAutomaticObjDtorsWithTerminator - Prepend destructor CFGElements for
1412*67e74705SXin Li /// variables with automatic storage duration to CFGBlock's elements vector.
1413*67e74705SXin Li /// Elements will be prepended to physical beginning of the vector which
1414*67e74705SXin Li /// happens to be logical end. Use blocks terminator as statement that specifies
1415*67e74705SXin Li /// destructors call site.
1416*67e74705SXin Li /// FIXME: This mechanism for adding automatic destructors doesn't handle
1417*67e74705SXin Li /// no-return destructors properly.
prependAutomaticObjDtorsWithTerminator(CFGBlock * Blk,LocalScope::const_iterator B,LocalScope::const_iterator E)1418*67e74705SXin Li void CFGBuilder::prependAutomaticObjDtorsWithTerminator(CFGBlock *Blk,
1419*67e74705SXin Li LocalScope::const_iterator B, LocalScope::const_iterator E) {
1420*67e74705SXin Li BumpVectorContext &C = cfg->getBumpVectorContext();
1421*67e74705SXin Li CFGBlock::iterator InsertPos
1422*67e74705SXin Li = Blk->beginAutomaticObjDtorsInsert(Blk->end(), B.distance(E), C);
1423*67e74705SXin Li for (LocalScope::const_iterator I = B; I != E; ++I)
1424*67e74705SXin Li InsertPos = Blk->insertAutomaticObjDtor(InsertPos, *I,
1425*67e74705SXin Li Blk->getTerminator());
1426*67e74705SXin Li }
1427*67e74705SXin Li
1428*67e74705SXin Li /// Visit - Walk the subtree of a statement and add extra
1429*67e74705SXin Li /// blocks for ternary operators, &&, and ||. We also process "," and
1430*67e74705SXin Li /// DeclStmts (which may contain nested control-flow).
Visit(Stmt * S,AddStmtChoice asc)1431*67e74705SXin Li CFGBlock *CFGBuilder::Visit(Stmt * S, AddStmtChoice asc) {
1432*67e74705SXin Li if (!S) {
1433*67e74705SXin Li badCFG = true;
1434*67e74705SXin Li return nullptr;
1435*67e74705SXin Li }
1436*67e74705SXin Li
1437*67e74705SXin Li if (Expr *E = dyn_cast<Expr>(S))
1438*67e74705SXin Li S = E->IgnoreParens();
1439*67e74705SXin Li
1440*67e74705SXin Li switch (S->getStmtClass()) {
1441*67e74705SXin Li default:
1442*67e74705SXin Li return VisitStmt(S, asc);
1443*67e74705SXin Li
1444*67e74705SXin Li case Stmt::AddrLabelExprClass:
1445*67e74705SXin Li return VisitAddrLabelExpr(cast<AddrLabelExpr>(S), asc);
1446*67e74705SXin Li
1447*67e74705SXin Li case Stmt::BinaryConditionalOperatorClass:
1448*67e74705SXin Li return VisitConditionalOperator(cast<BinaryConditionalOperator>(S), asc);
1449*67e74705SXin Li
1450*67e74705SXin Li case Stmt::BinaryOperatorClass:
1451*67e74705SXin Li return VisitBinaryOperator(cast<BinaryOperator>(S), asc);
1452*67e74705SXin Li
1453*67e74705SXin Li case Stmt::BlockExprClass:
1454*67e74705SXin Li return VisitBlockExpr(cast<BlockExpr>(S), asc);
1455*67e74705SXin Li
1456*67e74705SXin Li case Stmt::BreakStmtClass:
1457*67e74705SXin Li return VisitBreakStmt(cast<BreakStmt>(S));
1458*67e74705SXin Li
1459*67e74705SXin Li case Stmt::CallExprClass:
1460*67e74705SXin Li case Stmt::CXXOperatorCallExprClass:
1461*67e74705SXin Li case Stmt::CXXMemberCallExprClass:
1462*67e74705SXin Li case Stmt::UserDefinedLiteralClass:
1463*67e74705SXin Li return VisitCallExpr(cast<CallExpr>(S), asc);
1464*67e74705SXin Li
1465*67e74705SXin Li case Stmt::CaseStmtClass:
1466*67e74705SXin Li return VisitCaseStmt(cast<CaseStmt>(S));
1467*67e74705SXin Li
1468*67e74705SXin Li case Stmt::ChooseExprClass:
1469*67e74705SXin Li return VisitChooseExpr(cast<ChooseExpr>(S), asc);
1470*67e74705SXin Li
1471*67e74705SXin Li case Stmt::CompoundStmtClass:
1472*67e74705SXin Li return VisitCompoundStmt(cast<CompoundStmt>(S));
1473*67e74705SXin Li
1474*67e74705SXin Li case Stmt::ConditionalOperatorClass:
1475*67e74705SXin Li return VisitConditionalOperator(cast<ConditionalOperator>(S), asc);
1476*67e74705SXin Li
1477*67e74705SXin Li case Stmt::ContinueStmtClass:
1478*67e74705SXin Li return VisitContinueStmt(cast<ContinueStmt>(S));
1479*67e74705SXin Li
1480*67e74705SXin Li case Stmt::CXXCatchStmtClass:
1481*67e74705SXin Li return VisitCXXCatchStmt(cast<CXXCatchStmt>(S));
1482*67e74705SXin Li
1483*67e74705SXin Li case Stmt::ExprWithCleanupsClass:
1484*67e74705SXin Li return VisitExprWithCleanups(cast<ExprWithCleanups>(S), asc);
1485*67e74705SXin Li
1486*67e74705SXin Li case Stmt::CXXDefaultArgExprClass:
1487*67e74705SXin Li case Stmt::CXXDefaultInitExprClass:
1488*67e74705SXin Li // FIXME: The expression inside a CXXDefaultArgExpr is owned by the
1489*67e74705SXin Li // called function's declaration, not by the caller. If we simply add
1490*67e74705SXin Li // this expression to the CFG, we could end up with the same Expr
1491*67e74705SXin Li // appearing multiple times.
1492*67e74705SXin Li // PR13385 / <rdar://problem/12156507>
1493*67e74705SXin Li //
1494*67e74705SXin Li // It's likewise possible for multiple CXXDefaultInitExprs for the same
1495*67e74705SXin Li // expression to be used in the same function (through aggregate
1496*67e74705SXin Li // initialization).
1497*67e74705SXin Li return VisitStmt(S, asc);
1498*67e74705SXin Li
1499*67e74705SXin Li case Stmt::CXXBindTemporaryExprClass:
1500*67e74705SXin Li return VisitCXXBindTemporaryExpr(cast<CXXBindTemporaryExpr>(S), asc);
1501*67e74705SXin Li
1502*67e74705SXin Li case Stmt::CXXConstructExprClass:
1503*67e74705SXin Li return VisitCXXConstructExpr(cast<CXXConstructExpr>(S), asc);
1504*67e74705SXin Li
1505*67e74705SXin Li case Stmt::CXXNewExprClass:
1506*67e74705SXin Li return VisitCXXNewExpr(cast<CXXNewExpr>(S), asc);
1507*67e74705SXin Li
1508*67e74705SXin Li case Stmt::CXXDeleteExprClass:
1509*67e74705SXin Li return VisitCXXDeleteExpr(cast<CXXDeleteExpr>(S), asc);
1510*67e74705SXin Li
1511*67e74705SXin Li case Stmt::CXXFunctionalCastExprClass:
1512*67e74705SXin Li return VisitCXXFunctionalCastExpr(cast<CXXFunctionalCastExpr>(S), asc);
1513*67e74705SXin Li
1514*67e74705SXin Li case Stmt::CXXTemporaryObjectExprClass:
1515*67e74705SXin Li return VisitCXXTemporaryObjectExpr(cast<CXXTemporaryObjectExpr>(S), asc);
1516*67e74705SXin Li
1517*67e74705SXin Li case Stmt::CXXThrowExprClass:
1518*67e74705SXin Li return VisitCXXThrowExpr(cast<CXXThrowExpr>(S));
1519*67e74705SXin Li
1520*67e74705SXin Li case Stmt::CXXTryStmtClass:
1521*67e74705SXin Li return VisitCXXTryStmt(cast<CXXTryStmt>(S));
1522*67e74705SXin Li
1523*67e74705SXin Li case Stmt::CXXForRangeStmtClass:
1524*67e74705SXin Li return VisitCXXForRangeStmt(cast<CXXForRangeStmt>(S));
1525*67e74705SXin Li
1526*67e74705SXin Li case Stmt::DeclStmtClass:
1527*67e74705SXin Li return VisitDeclStmt(cast<DeclStmt>(S));
1528*67e74705SXin Li
1529*67e74705SXin Li case Stmt::DefaultStmtClass:
1530*67e74705SXin Li return VisitDefaultStmt(cast<DefaultStmt>(S));
1531*67e74705SXin Li
1532*67e74705SXin Li case Stmt::DoStmtClass:
1533*67e74705SXin Li return VisitDoStmt(cast<DoStmt>(S));
1534*67e74705SXin Li
1535*67e74705SXin Li case Stmt::ForStmtClass:
1536*67e74705SXin Li return VisitForStmt(cast<ForStmt>(S));
1537*67e74705SXin Li
1538*67e74705SXin Li case Stmt::GotoStmtClass:
1539*67e74705SXin Li return VisitGotoStmt(cast<GotoStmt>(S));
1540*67e74705SXin Li
1541*67e74705SXin Li case Stmt::IfStmtClass:
1542*67e74705SXin Li return VisitIfStmt(cast<IfStmt>(S));
1543*67e74705SXin Li
1544*67e74705SXin Li case Stmt::ImplicitCastExprClass:
1545*67e74705SXin Li return VisitImplicitCastExpr(cast<ImplicitCastExpr>(S), asc);
1546*67e74705SXin Li
1547*67e74705SXin Li case Stmt::IndirectGotoStmtClass:
1548*67e74705SXin Li return VisitIndirectGotoStmt(cast<IndirectGotoStmt>(S));
1549*67e74705SXin Li
1550*67e74705SXin Li case Stmt::LabelStmtClass:
1551*67e74705SXin Li return VisitLabelStmt(cast<LabelStmt>(S));
1552*67e74705SXin Li
1553*67e74705SXin Li case Stmt::LambdaExprClass:
1554*67e74705SXin Li return VisitLambdaExpr(cast<LambdaExpr>(S), asc);
1555*67e74705SXin Li
1556*67e74705SXin Li case Stmt::MemberExprClass:
1557*67e74705SXin Li return VisitMemberExpr(cast<MemberExpr>(S), asc);
1558*67e74705SXin Li
1559*67e74705SXin Li case Stmt::NullStmtClass:
1560*67e74705SXin Li return Block;
1561*67e74705SXin Li
1562*67e74705SXin Li case Stmt::ObjCAtCatchStmtClass:
1563*67e74705SXin Li return VisitObjCAtCatchStmt(cast<ObjCAtCatchStmt>(S));
1564*67e74705SXin Li
1565*67e74705SXin Li case Stmt::ObjCAutoreleasePoolStmtClass:
1566*67e74705SXin Li return VisitObjCAutoreleasePoolStmt(cast<ObjCAutoreleasePoolStmt>(S));
1567*67e74705SXin Li
1568*67e74705SXin Li case Stmt::ObjCAtSynchronizedStmtClass:
1569*67e74705SXin Li return VisitObjCAtSynchronizedStmt(cast<ObjCAtSynchronizedStmt>(S));
1570*67e74705SXin Li
1571*67e74705SXin Li case Stmt::ObjCAtThrowStmtClass:
1572*67e74705SXin Li return VisitObjCAtThrowStmt(cast<ObjCAtThrowStmt>(S));
1573*67e74705SXin Li
1574*67e74705SXin Li case Stmt::ObjCAtTryStmtClass:
1575*67e74705SXin Li return VisitObjCAtTryStmt(cast<ObjCAtTryStmt>(S));
1576*67e74705SXin Li
1577*67e74705SXin Li case Stmt::ObjCForCollectionStmtClass:
1578*67e74705SXin Li return VisitObjCForCollectionStmt(cast<ObjCForCollectionStmt>(S));
1579*67e74705SXin Li
1580*67e74705SXin Li case Stmt::OpaqueValueExprClass:
1581*67e74705SXin Li return Block;
1582*67e74705SXin Li
1583*67e74705SXin Li case Stmt::PseudoObjectExprClass:
1584*67e74705SXin Li return VisitPseudoObjectExpr(cast<PseudoObjectExpr>(S));
1585*67e74705SXin Li
1586*67e74705SXin Li case Stmt::ReturnStmtClass:
1587*67e74705SXin Li return VisitReturnStmt(cast<ReturnStmt>(S));
1588*67e74705SXin Li
1589*67e74705SXin Li case Stmt::UnaryExprOrTypeTraitExprClass:
1590*67e74705SXin Li return VisitUnaryExprOrTypeTraitExpr(cast<UnaryExprOrTypeTraitExpr>(S),
1591*67e74705SXin Li asc);
1592*67e74705SXin Li
1593*67e74705SXin Li case Stmt::StmtExprClass:
1594*67e74705SXin Li return VisitStmtExpr(cast<StmtExpr>(S), asc);
1595*67e74705SXin Li
1596*67e74705SXin Li case Stmt::SwitchStmtClass:
1597*67e74705SXin Li return VisitSwitchStmt(cast<SwitchStmt>(S));
1598*67e74705SXin Li
1599*67e74705SXin Li case Stmt::UnaryOperatorClass:
1600*67e74705SXin Li return VisitUnaryOperator(cast<UnaryOperator>(S), asc);
1601*67e74705SXin Li
1602*67e74705SXin Li case Stmt::WhileStmtClass:
1603*67e74705SXin Li return VisitWhileStmt(cast<WhileStmt>(S));
1604*67e74705SXin Li }
1605*67e74705SXin Li }
1606*67e74705SXin Li
VisitStmt(Stmt * S,AddStmtChoice asc)1607*67e74705SXin Li CFGBlock *CFGBuilder::VisitStmt(Stmt *S, AddStmtChoice asc) {
1608*67e74705SXin Li if (asc.alwaysAdd(*this, S)) {
1609*67e74705SXin Li autoCreateBlock();
1610*67e74705SXin Li appendStmt(Block, S);
1611*67e74705SXin Li }
1612*67e74705SXin Li
1613*67e74705SXin Li return VisitChildren(S);
1614*67e74705SXin Li }
1615*67e74705SXin Li
1616*67e74705SXin Li /// VisitChildren - Visit the children of a Stmt.
VisitChildren(Stmt * S)1617*67e74705SXin Li CFGBlock *CFGBuilder::VisitChildren(Stmt *S) {
1618*67e74705SXin Li CFGBlock *B = Block;
1619*67e74705SXin Li
1620*67e74705SXin Li // Visit the children in their reverse order so that they appear in
1621*67e74705SXin Li // left-to-right (natural) order in the CFG.
1622*67e74705SXin Li reverse_children RChildren(S);
1623*67e74705SXin Li for (reverse_children::iterator I = RChildren.begin(), E = RChildren.end();
1624*67e74705SXin Li I != E; ++I) {
1625*67e74705SXin Li if (Stmt *Child = *I)
1626*67e74705SXin Li if (CFGBlock *R = Visit(Child))
1627*67e74705SXin Li B = R;
1628*67e74705SXin Li }
1629*67e74705SXin Li return B;
1630*67e74705SXin Li }
1631*67e74705SXin Li
VisitAddrLabelExpr(AddrLabelExpr * A,AddStmtChoice asc)1632*67e74705SXin Li CFGBlock *CFGBuilder::VisitAddrLabelExpr(AddrLabelExpr *A,
1633*67e74705SXin Li AddStmtChoice asc) {
1634*67e74705SXin Li AddressTakenLabels.insert(A->getLabel());
1635*67e74705SXin Li
1636*67e74705SXin Li if (asc.alwaysAdd(*this, A)) {
1637*67e74705SXin Li autoCreateBlock();
1638*67e74705SXin Li appendStmt(Block, A);
1639*67e74705SXin Li }
1640*67e74705SXin Li
1641*67e74705SXin Li return Block;
1642*67e74705SXin Li }
1643*67e74705SXin Li
VisitUnaryOperator(UnaryOperator * U,AddStmtChoice asc)1644*67e74705SXin Li CFGBlock *CFGBuilder::VisitUnaryOperator(UnaryOperator *U,
1645*67e74705SXin Li AddStmtChoice asc) {
1646*67e74705SXin Li if (asc.alwaysAdd(*this, U)) {
1647*67e74705SXin Li autoCreateBlock();
1648*67e74705SXin Li appendStmt(Block, U);
1649*67e74705SXin Li }
1650*67e74705SXin Li
1651*67e74705SXin Li return Visit(U->getSubExpr(), AddStmtChoice());
1652*67e74705SXin Li }
1653*67e74705SXin Li
VisitLogicalOperator(BinaryOperator * B)1654*67e74705SXin Li CFGBlock *CFGBuilder::VisitLogicalOperator(BinaryOperator *B) {
1655*67e74705SXin Li CFGBlock *ConfluenceBlock = Block ? Block : createBlock();
1656*67e74705SXin Li appendStmt(ConfluenceBlock, B);
1657*67e74705SXin Li
1658*67e74705SXin Li if (badCFG)
1659*67e74705SXin Li return nullptr;
1660*67e74705SXin Li
1661*67e74705SXin Li return VisitLogicalOperator(B, nullptr, ConfluenceBlock,
1662*67e74705SXin Li ConfluenceBlock).first;
1663*67e74705SXin Li }
1664*67e74705SXin Li
1665*67e74705SXin Li std::pair<CFGBlock*, CFGBlock*>
VisitLogicalOperator(BinaryOperator * B,Stmt * Term,CFGBlock * TrueBlock,CFGBlock * FalseBlock)1666*67e74705SXin Li CFGBuilder::VisitLogicalOperator(BinaryOperator *B,
1667*67e74705SXin Li Stmt *Term,
1668*67e74705SXin Li CFGBlock *TrueBlock,
1669*67e74705SXin Li CFGBlock *FalseBlock) {
1670*67e74705SXin Li
1671*67e74705SXin Li // Introspect the RHS. If it is a nested logical operation, we recursively
1672*67e74705SXin Li // build the CFG using this function. Otherwise, resort to default
1673*67e74705SXin Li // CFG construction behavior.
1674*67e74705SXin Li Expr *RHS = B->getRHS()->IgnoreParens();
1675*67e74705SXin Li CFGBlock *RHSBlock, *ExitBlock;
1676*67e74705SXin Li
1677*67e74705SXin Li do {
1678*67e74705SXin Li if (BinaryOperator *B_RHS = dyn_cast<BinaryOperator>(RHS))
1679*67e74705SXin Li if (B_RHS->isLogicalOp()) {
1680*67e74705SXin Li std::tie(RHSBlock, ExitBlock) =
1681*67e74705SXin Li VisitLogicalOperator(B_RHS, Term, TrueBlock, FalseBlock);
1682*67e74705SXin Li break;
1683*67e74705SXin Li }
1684*67e74705SXin Li
1685*67e74705SXin Li // The RHS is not a nested logical operation. Don't push the terminator
1686*67e74705SXin Li // down further, but instead visit RHS and construct the respective
1687*67e74705SXin Li // pieces of the CFG, and link up the RHSBlock with the terminator
1688*67e74705SXin Li // we have been provided.
1689*67e74705SXin Li ExitBlock = RHSBlock = createBlock(false);
1690*67e74705SXin Li
1691*67e74705SXin Li if (!Term) {
1692*67e74705SXin Li assert(TrueBlock == FalseBlock);
1693*67e74705SXin Li addSuccessor(RHSBlock, TrueBlock);
1694*67e74705SXin Li }
1695*67e74705SXin Li else {
1696*67e74705SXin Li RHSBlock->setTerminator(Term);
1697*67e74705SXin Li TryResult KnownVal = tryEvaluateBool(RHS);
1698*67e74705SXin Li if (!KnownVal.isKnown())
1699*67e74705SXin Li KnownVal = tryEvaluateBool(B);
1700*67e74705SXin Li addSuccessor(RHSBlock, TrueBlock, !KnownVal.isFalse());
1701*67e74705SXin Li addSuccessor(RHSBlock, FalseBlock, !KnownVal.isTrue());
1702*67e74705SXin Li }
1703*67e74705SXin Li
1704*67e74705SXin Li Block = RHSBlock;
1705*67e74705SXin Li RHSBlock = addStmt(RHS);
1706*67e74705SXin Li }
1707*67e74705SXin Li while (false);
1708*67e74705SXin Li
1709*67e74705SXin Li if (badCFG)
1710*67e74705SXin Li return std::make_pair(nullptr, nullptr);
1711*67e74705SXin Li
1712*67e74705SXin Li // Generate the blocks for evaluating the LHS.
1713*67e74705SXin Li Expr *LHS = B->getLHS()->IgnoreParens();
1714*67e74705SXin Li
1715*67e74705SXin Li if (BinaryOperator *B_LHS = dyn_cast<BinaryOperator>(LHS))
1716*67e74705SXin Li if (B_LHS->isLogicalOp()) {
1717*67e74705SXin Li if (B->getOpcode() == BO_LOr)
1718*67e74705SXin Li FalseBlock = RHSBlock;
1719*67e74705SXin Li else
1720*67e74705SXin Li TrueBlock = RHSBlock;
1721*67e74705SXin Li
1722*67e74705SXin Li // For the LHS, treat 'B' as the terminator that we want to sink
1723*67e74705SXin Li // into the nested branch. The RHS always gets the top-most
1724*67e74705SXin Li // terminator.
1725*67e74705SXin Li return VisitLogicalOperator(B_LHS, B, TrueBlock, FalseBlock);
1726*67e74705SXin Li }
1727*67e74705SXin Li
1728*67e74705SXin Li // Create the block evaluating the LHS.
1729*67e74705SXin Li // This contains the '&&' or '||' as the terminator.
1730*67e74705SXin Li CFGBlock *LHSBlock = createBlock(false);
1731*67e74705SXin Li LHSBlock->setTerminator(B);
1732*67e74705SXin Li
1733*67e74705SXin Li Block = LHSBlock;
1734*67e74705SXin Li CFGBlock *EntryLHSBlock = addStmt(LHS);
1735*67e74705SXin Li
1736*67e74705SXin Li if (badCFG)
1737*67e74705SXin Li return std::make_pair(nullptr, nullptr);
1738*67e74705SXin Li
1739*67e74705SXin Li // See if this is a known constant.
1740*67e74705SXin Li TryResult KnownVal = tryEvaluateBool(LHS);
1741*67e74705SXin Li
1742*67e74705SXin Li // Now link the LHSBlock with RHSBlock.
1743*67e74705SXin Li if (B->getOpcode() == BO_LOr) {
1744*67e74705SXin Li addSuccessor(LHSBlock, TrueBlock, !KnownVal.isFalse());
1745*67e74705SXin Li addSuccessor(LHSBlock, RHSBlock, !KnownVal.isTrue());
1746*67e74705SXin Li } else {
1747*67e74705SXin Li assert(B->getOpcode() == BO_LAnd);
1748*67e74705SXin Li addSuccessor(LHSBlock, RHSBlock, !KnownVal.isFalse());
1749*67e74705SXin Li addSuccessor(LHSBlock, FalseBlock, !KnownVal.isTrue());
1750*67e74705SXin Li }
1751*67e74705SXin Li
1752*67e74705SXin Li return std::make_pair(EntryLHSBlock, ExitBlock);
1753*67e74705SXin Li }
1754*67e74705SXin Li
1755*67e74705SXin Li
VisitBinaryOperator(BinaryOperator * B,AddStmtChoice asc)1756*67e74705SXin Li CFGBlock *CFGBuilder::VisitBinaryOperator(BinaryOperator *B,
1757*67e74705SXin Li AddStmtChoice asc) {
1758*67e74705SXin Li // && or ||
1759*67e74705SXin Li if (B->isLogicalOp())
1760*67e74705SXin Li return VisitLogicalOperator(B);
1761*67e74705SXin Li
1762*67e74705SXin Li if (B->getOpcode() == BO_Comma) { // ,
1763*67e74705SXin Li autoCreateBlock();
1764*67e74705SXin Li appendStmt(Block, B);
1765*67e74705SXin Li addStmt(B->getRHS());
1766*67e74705SXin Li return addStmt(B->getLHS());
1767*67e74705SXin Li }
1768*67e74705SXin Li
1769*67e74705SXin Li if (B->isAssignmentOp()) {
1770*67e74705SXin Li if (asc.alwaysAdd(*this, B)) {
1771*67e74705SXin Li autoCreateBlock();
1772*67e74705SXin Li appendStmt(Block, B);
1773*67e74705SXin Li }
1774*67e74705SXin Li Visit(B->getLHS());
1775*67e74705SXin Li return Visit(B->getRHS());
1776*67e74705SXin Li }
1777*67e74705SXin Li
1778*67e74705SXin Li if (asc.alwaysAdd(*this, B)) {
1779*67e74705SXin Li autoCreateBlock();
1780*67e74705SXin Li appendStmt(Block, B);
1781*67e74705SXin Li }
1782*67e74705SXin Li
1783*67e74705SXin Li CFGBlock *RBlock = Visit(B->getRHS());
1784*67e74705SXin Li CFGBlock *LBlock = Visit(B->getLHS());
1785*67e74705SXin Li // If visiting RHS causes us to finish 'Block', e.g. the RHS is a StmtExpr
1786*67e74705SXin Li // containing a DoStmt, and the LHS doesn't create a new block, then we should
1787*67e74705SXin Li // return RBlock. Otherwise we'll incorrectly return NULL.
1788*67e74705SXin Li return (LBlock ? LBlock : RBlock);
1789*67e74705SXin Li }
1790*67e74705SXin Li
VisitNoRecurse(Expr * E,AddStmtChoice asc)1791*67e74705SXin Li CFGBlock *CFGBuilder::VisitNoRecurse(Expr *E, AddStmtChoice asc) {
1792*67e74705SXin Li if (asc.alwaysAdd(*this, E)) {
1793*67e74705SXin Li autoCreateBlock();
1794*67e74705SXin Li appendStmt(Block, E);
1795*67e74705SXin Li }
1796*67e74705SXin Li return Block;
1797*67e74705SXin Li }
1798*67e74705SXin Li
VisitBreakStmt(BreakStmt * B)1799*67e74705SXin Li CFGBlock *CFGBuilder::VisitBreakStmt(BreakStmt *B) {
1800*67e74705SXin Li // "break" is a control-flow statement. Thus we stop processing the current
1801*67e74705SXin Li // block.
1802*67e74705SXin Li if (badCFG)
1803*67e74705SXin Li return nullptr;
1804*67e74705SXin Li
1805*67e74705SXin Li // Now create a new block that ends with the break statement.
1806*67e74705SXin Li Block = createBlock(false);
1807*67e74705SXin Li Block->setTerminator(B);
1808*67e74705SXin Li
1809*67e74705SXin Li // If there is no target for the break, then we are looking at an incomplete
1810*67e74705SXin Li // AST. This means that the CFG cannot be constructed.
1811*67e74705SXin Li if (BreakJumpTarget.block) {
1812*67e74705SXin Li addAutomaticObjDtors(ScopePos, BreakJumpTarget.scopePosition, B);
1813*67e74705SXin Li addSuccessor(Block, BreakJumpTarget.block);
1814*67e74705SXin Li } else
1815*67e74705SXin Li badCFG = true;
1816*67e74705SXin Li
1817*67e74705SXin Li
1818*67e74705SXin Li return Block;
1819*67e74705SXin Li }
1820*67e74705SXin Li
CanThrow(Expr * E,ASTContext & Ctx)1821*67e74705SXin Li static bool CanThrow(Expr *E, ASTContext &Ctx) {
1822*67e74705SXin Li QualType Ty = E->getType();
1823*67e74705SXin Li if (Ty->isFunctionPointerType())
1824*67e74705SXin Li Ty = Ty->getAs<PointerType>()->getPointeeType();
1825*67e74705SXin Li else if (Ty->isBlockPointerType())
1826*67e74705SXin Li Ty = Ty->getAs<BlockPointerType>()->getPointeeType();
1827*67e74705SXin Li
1828*67e74705SXin Li const FunctionType *FT = Ty->getAs<FunctionType>();
1829*67e74705SXin Li if (FT) {
1830*67e74705SXin Li if (const FunctionProtoType *Proto = dyn_cast<FunctionProtoType>(FT))
1831*67e74705SXin Li if (!isUnresolvedExceptionSpec(Proto->getExceptionSpecType()) &&
1832*67e74705SXin Li Proto->isNothrow(Ctx))
1833*67e74705SXin Li return false;
1834*67e74705SXin Li }
1835*67e74705SXin Li return true;
1836*67e74705SXin Li }
1837*67e74705SXin Li
VisitCallExpr(CallExpr * C,AddStmtChoice asc)1838*67e74705SXin Li CFGBlock *CFGBuilder::VisitCallExpr(CallExpr *C, AddStmtChoice asc) {
1839*67e74705SXin Li // Compute the callee type.
1840*67e74705SXin Li QualType calleeType = C->getCallee()->getType();
1841*67e74705SXin Li if (calleeType == Context->BoundMemberTy) {
1842*67e74705SXin Li QualType boundType = Expr::findBoundMemberType(C->getCallee());
1843*67e74705SXin Li
1844*67e74705SXin Li // We should only get a null bound type if processing a dependent
1845*67e74705SXin Li // CFG. Recover by assuming nothing.
1846*67e74705SXin Li if (!boundType.isNull()) calleeType = boundType;
1847*67e74705SXin Li }
1848*67e74705SXin Li
1849*67e74705SXin Li // If this is a call to a no-return function, this stops the block here.
1850*67e74705SXin Li bool NoReturn = getFunctionExtInfo(*calleeType).getNoReturn();
1851*67e74705SXin Li
1852*67e74705SXin Li bool AddEHEdge = false;
1853*67e74705SXin Li
1854*67e74705SXin Li // Languages without exceptions are assumed to not throw.
1855*67e74705SXin Li if (Context->getLangOpts().Exceptions) {
1856*67e74705SXin Li if (BuildOpts.AddEHEdges)
1857*67e74705SXin Li AddEHEdge = true;
1858*67e74705SXin Li }
1859*67e74705SXin Li
1860*67e74705SXin Li // If this is a call to a builtin function, it might not actually evaluate
1861*67e74705SXin Li // its arguments. Don't add them to the CFG if this is the case.
1862*67e74705SXin Li bool OmitArguments = false;
1863*67e74705SXin Li
1864*67e74705SXin Li if (FunctionDecl *FD = C->getDirectCallee()) {
1865*67e74705SXin Li if (FD->isNoReturn())
1866*67e74705SXin Li NoReturn = true;
1867*67e74705SXin Li if (FD->hasAttr<NoThrowAttr>())
1868*67e74705SXin Li AddEHEdge = false;
1869*67e74705SXin Li if (FD->getBuiltinID() == Builtin::BI__builtin_object_size)
1870*67e74705SXin Li OmitArguments = true;
1871*67e74705SXin Li }
1872*67e74705SXin Li
1873*67e74705SXin Li if (!CanThrow(C->getCallee(), *Context))
1874*67e74705SXin Li AddEHEdge = false;
1875*67e74705SXin Li
1876*67e74705SXin Li if (OmitArguments) {
1877*67e74705SXin Li assert(!NoReturn && "noreturn calls with unevaluated args not implemented");
1878*67e74705SXin Li assert(!AddEHEdge && "EH calls with unevaluated args not implemented");
1879*67e74705SXin Li autoCreateBlock();
1880*67e74705SXin Li appendStmt(Block, C);
1881*67e74705SXin Li return Visit(C->getCallee());
1882*67e74705SXin Li }
1883*67e74705SXin Li
1884*67e74705SXin Li if (!NoReturn && !AddEHEdge) {
1885*67e74705SXin Li return VisitStmt(C, asc.withAlwaysAdd(true));
1886*67e74705SXin Li }
1887*67e74705SXin Li
1888*67e74705SXin Li if (Block) {
1889*67e74705SXin Li Succ = Block;
1890*67e74705SXin Li if (badCFG)
1891*67e74705SXin Li return nullptr;
1892*67e74705SXin Li }
1893*67e74705SXin Li
1894*67e74705SXin Li if (NoReturn)
1895*67e74705SXin Li Block = createNoReturnBlock();
1896*67e74705SXin Li else
1897*67e74705SXin Li Block = createBlock();
1898*67e74705SXin Li
1899*67e74705SXin Li appendStmt(Block, C);
1900*67e74705SXin Li
1901*67e74705SXin Li if (AddEHEdge) {
1902*67e74705SXin Li // Add exceptional edges.
1903*67e74705SXin Li if (TryTerminatedBlock)
1904*67e74705SXin Li addSuccessor(Block, TryTerminatedBlock);
1905*67e74705SXin Li else
1906*67e74705SXin Li addSuccessor(Block, &cfg->getExit());
1907*67e74705SXin Li }
1908*67e74705SXin Li
1909*67e74705SXin Li return VisitChildren(C);
1910*67e74705SXin Li }
1911*67e74705SXin Li
VisitChooseExpr(ChooseExpr * C,AddStmtChoice asc)1912*67e74705SXin Li CFGBlock *CFGBuilder::VisitChooseExpr(ChooseExpr *C,
1913*67e74705SXin Li AddStmtChoice asc) {
1914*67e74705SXin Li CFGBlock *ConfluenceBlock = Block ? Block : createBlock();
1915*67e74705SXin Li appendStmt(ConfluenceBlock, C);
1916*67e74705SXin Li if (badCFG)
1917*67e74705SXin Li return nullptr;
1918*67e74705SXin Li
1919*67e74705SXin Li AddStmtChoice alwaysAdd = asc.withAlwaysAdd(true);
1920*67e74705SXin Li Succ = ConfluenceBlock;
1921*67e74705SXin Li Block = nullptr;
1922*67e74705SXin Li CFGBlock *LHSBlock = Visit(C->getLHS(), alwaysAdd);
1923*67e74705SXin Li if (badCFG)
1924*67e74705SXin Li return nullptr;
1925*67e74705SXin Li
1926*67e74705SXin Li Succ = ConfluenceBlock;
1927*67e74705SXin Li Block = nullptr;
1928*67e74705SXin Li CFGBlock *RHSBlock = Visit(C->getRHS(), alwaysAdd);
1929*67e74705SXin Li if (badCFG)
1930*67e74705SXin Li return nullptr;
1931*67e74705SXin Li
1932*67e74705SXin Li Block = createBlock(false);
1933*67e74705SXin Li // See if this is a known constant.
1934*67e74705SXin Li const TryResult& KnownVal = tryEvaluateBool(C->getCond());
1935*67e74705SXin Li addSuccessor(Block, KnownVal.isFalse() ? nullptr : LHSBlock);
1936*67e74705SXin Li addSuccessor(Block, KnownVal.isTrue() ? nullptr : RHSBlock);
1937*67e74705SXin Li Block->setTerminator(C);
1938*67e74705SXin Li return addStmt(C->getCond());
1939*67e74705SXin Li }
1940*67e74705SXin Li
1941*67e74705SXin Li
VisitCompoundStmt(CompoundStmt * C)1942*67e74705SXin Li CFGBlock *CFGBuilder::VisitCompoundStmt(CompoundStmt *C) {
1943*67e74705SXin Li LocalScope::const_iterator scopeBeginPos = ScopePos;
1944*67e74705SXin Li if (BuildOpts.AddImplicitDtors) {
1945*67e74705SXin Li addLocalScopeForStmt(C);
1946*67e74705SXin Li }
1947*67e74705SXin Li if (!C->body_empty() && !isa<ReturnStmt>(*C->body_rbegin())) {
1948*67e74705SXin Li // If the body ends with a ReturnStmt, the dtors will be added in
1949*67e74705SXin Li // VisitReturnStmt.
1950*67e74705SXin Li addAutomaticObjDtors(ScopePos, scopeBeginPos, C);
1951*67e74705SXin Li }
1952*67e74705SXin Li
1953*67e74705SXin Li CFGBlock *LastBlock = Block;
1954*67e74705SXin Li
1955*67e74705SXin Li for (CompoundStmt::reverse_body_iterator I=C->body_rbegin(), E=C->body_rend();
1956*67e74705SXin Li I != E; ++I ) {
1957*67e74705SXin Li // If we hit a segment of code just containing ';' (NullStmts), we can
1958*67e74705SXin Li // get a null block back. In such cases, just use the LastBlock
1959*67e74705SXin Li if (CFGBlock *newBlock = addStmt(*I))
1960*67e74705SXin Li LastBlock = newBlock;
1961*67e74705SXin Li
1962*67e74705SXin Li if (badCFG)
1963*67e74705SXin Li return nullptr;
1964*67e74705SXin Li }
1965*67e74705SXin Li
1966*67e74705SXin Li return LastBlock;
1967*67e74705SXin Li }
1968*67e74705SXin Li
VisitConditionalOperator(AbstractConditionalOperator * C,AddStmtChoice asc)1969*67e74705SXin Li CFGBlock *CFGBuilder::VisitConditionalOperator(AbstractConditionalOperator *C,
1970*67e74705SXin Li AddStmtChoice asc) {
1971*67e74705SXin Li const BinaryConditionalOperator *BCO = dyn_cast<BinaryConditionalOperator>(C);
1972*67e74705SXin Li const OpaqueValueExpr *opaqueValue = (BCO ? BCO->getOpaqueValue() : nullptr);
1973*67e74705SXin Li
1974*67e74705SXin Li // Create the confluence block that will "merge" the results of the ternary
1975*67e74705SXin Li // expression.
1976*67e74705SXin Li CFGBlock *ConfluenceBlock = Block ? Block : createBlock();
1977*67e74705SXin Li appendStmt(ConfluenceBlock, C);
1978*67e74705SXin Li if (badCFG)
1979*67e74705SXin Li return nullptr;
1980*67e74705SXin Li
1981*67e74705SXin Li AddStmtChoice alwaysAdd = asc.withAlwaysAdd(true);
1982*67e74705SXin Li
1983*67e74705SXin Li // Create a block for the LHS expression if there is an LHS expression. A
1984*67e74705SXin Li // GCC extension allows LHS to be NULL, causing the condition to be the
1985*67e74705SXin Li // value that is returned instead.
1986*67e74705SXin Li // e.g: x ?: y is shorthand for: x ? x : y;
1987*67e74705SXin Li Succ = ConfluenceBlock;
1988*67e74705SXin Li Block = nullptr;
1989*67e74705SXin Li CFGBlock *LHSBlock = nullptr;
1990*67e74705SXin Li const Expr *trueExpr = C->getTrueExpr();
1991*67e74705SXin Li if (trueExpr != opaqueValue) {
1992*67e74705SXin Li LHSBlock = Visit(C->getTrueExpr(), alwaysAdd);
1993*67e74705SXin Li if (badCFG)
1994*67e74705SXin Li return nullptr;
1995*67e74705SXin Li Block = nullptr;
1996*67e74705SXin Li }
1997*67e74705SXin Li else
1998*67e74705SXin Li LHSBlock = ConfluenceBlock;
1999*67e74705SXin Li
2000*67e74705SXin Li // Create the block for the RHS expression.
2001*67e74705SXin Li Succ = ConfluenceBlock;
2002*67e74705SXin Li CFGBlock *RHSBlock = Visit(C->getFalseExpr(), alwaysAdd);
2003*67e74705SXin Li if (badCFG)
2004*67e74705SXin Li return nullptr;
2005*67e74705SXin Li
2006*67e74705SXin Li // If the condition is a logical '&&' or '||', build a more accurate CFG.
2007*67e74705SXin Li if (BinaryOperator *Cond =
2008*67e74705SXin Li dyn_cast<BinaryOperator>(C->getCond()->IgnoreParens()))
2009*67e74705SXin Li if (Cond->isLogicalOp())
2010*67e74705SXin Li return VisitLogicalOperator(Cond, C, LHSBlock, RHSBlock).first;
2011*67e74705SXin Li
2012*67e74705SXin Li // Create the block that will contain the condition.
2013*67e74705SXin Li Block = createBlock(false);
2014*67e74705SXin Li
2015*67e74705SXin Li // See if this is a known constant.
2016*67e74705SXin Li const TryResult& KnownVal = tryEvaluateBool(C->getCond());
2017*67e74705SXin Li addSuccessor(Block, LHSBlock, !KnownVal.isFalse());
2018*67e74705SXin Li addSuccessor(Block, RHSBlock, !KnownVal.isTrue());
2019*67e74705SXin Li Block->setTerminator(C);
2020*67e74705SXin Li Expr *condExpr = C->getCond();
2021*67e74705SXin Li
2022*67e74705SXin Li if (opaqueValue) {
2023*67e74705SXin Li // Run the condition expression if it's not trivially expressed in
2024*67e74705SXin Li // terms of the opaque value (or if there is no opaque value).
2025*67e74705SXin Li if (condExpr != opaqueValue)
2026*67e74705SXin Li addStmt(condExpr);
2027*67e74705SXin Li
2028*67e74705SXin Li // Before that, run the common subexpression if there was one.
2029*67e74705SXin Li // At least one of this or the above will be run.
2030*67e74705SXin Li return addStmt(BCO->getCommon());
2031*67e74705SXin Li }
2032*67e74705SXin Li
2033*67e74705SXin Li return addStmt(condExpr);
2034*67e74705SXin Li }
2035*67e74705SXin Li
VisitDeclStmt(DeclStmt * DS)2036*67e74705SXin Li CFGBlock *CFGBuilder::VisitDeclStmt(DeclStmt *DS) {
2037*67e74705SXin Li // Check if the Decl is for an __label__. If so, elide it from the
2038*67e74705SXin Li // CFG entirely.
2039*67e74705SXin Li if (isa<LabelDecl>(*DS->decl_begin()))
2040*67e74705SXin Li return Block;
2041*67e74705SXin Li
2042*67e74705SXin Li // This case also handles static_asserts.
2043*67e74705SXin Li if (DS->isSingleDecl())
2044*67e74705SXin Li return VisitDeclSubExpr(DS);
2045*67e74705SXin Li
2046*67e74705SXin Li CFGBlock *B = nullptr;
2047*67e74705SXin Li
2048*67e74705SXin Li // Build an individual DeclStmt for each decl.
2049*67e74705SXin Li for (DeclStmt::reverse_decl_iterator I = DS->decl_rbegin(),
2050*67e74705SXin Li E = DS->decl_rend();
2051*67e74705SXin Li I != E; ++I) {
2052*67e74705SXin Li // Get the alignment of the new DeclStmt, padding out to >=8 bytes.
2053*67e74705SXin Li unsigned A = llvm::AlignOf<DeclStmt>::Alignment < 8
2054*67e74705SXin Li ? 8 : llvm::AlignOf<DeclStmt>::Alignment;
2055*67e74705SXin Li
2056*67e74705SXin Li // Allocate the DeclStmt using the BumpPtrAllocator. It will get
2057*67e74705SXin Li // automatically freed with the CFG.
2058*67e74705SXin Li DeclGroupRef DG(*I);
2059*67e74705SXin Li Decl *D = *I;
2060*67e74705SXin Li void *Mem = cfg->getAllocator().Allocate(sizeof(DeclStmt), A);
2061*67e74705SXin Li DeclStmt *DSNew = new (Mem) DeclStmt(DG, D->getLocation(), GetEndLoc(D));
2062*67e74705SXin Li cfg->addSyntheticDeclStmt(DSNew, DS);
2063*67e74705SXin Li
2064*67e74705SXin Li // Append the fake DeclStmt to block.
2065*67e74705SXin Li B = VisitDeclSubExpr(DSNew);
2066*67e74705SXin Li }
2067*67e74705SXin Li
2068*67e74705SXin Li return B;
2069*67e74705SXin Li }
2070*67e74705SXin Li
2071*67e74705SXin Li /// VisitDeclSubExpr - Utility method to add block-level expressions for
2072*67e74705SXin Li /// DeclStmts and initializers in them.
VisitDeclSubExpr(DeclStmt * DS)2073*67e74705SXin Li CFGBlock *CFGBuilder::VisitDeclSubExpr(DeclStmt *DS) {
2074*67e74705SXin Li assert(DS->isSingleDecl() && "Can handle single declarations only.");
2075*67e74705SXin Li VarDecl *VD = dyn_cast<VarDecl>(DS->getSingleDecl());
2076*67e74705SXin Li
2077*67e74705SXin Li if (!VD) {
2078*67e74705SXin Li // Of everything that can be declared in a DeclStmt, only VarDecls impact
2079*67e74705SXin Li // runtime semantics.
2080*67e74705SXin Li return Block;
2081*67e74705SXin Li }
2082*67e74705SXin Li
2083*67e74705SXin Li bool HasTemporaries = false;
2084*67e74705SXin Li
2085*67e74705SXin Li // Guard static initializers under a branch.
2086*67e74705SXin Li CFGBlock *blockAfterStaticInit = nullptr;
2087*67e74705SXin Li
2088*67e74705SXin Li if (BuildOpts.AddStaticInitBranches && VD->isStaticLocal()) {
2089*67e74705SXin Li // For static variables, we need to create a branch to track
2090*67e74705SXin Li // whether or not they are initialized.
2091*67e74705SXin Li if (Block) {
2092*67e74705SXin Li Succ = Block;
2093*67e74705SXin Li Block = nullptr;
2094*67e74705SXin Li if (badCFG)
2095*67e74705SXin Li return nullptr;
2096*67e74705SXin Li }
2097*67e74705SXin Li blockAfterStaticInit = Succ;
2098*67e74705SXin Li }
2099*67e74705SXin Li
2100*67e74705SXin Li // Destructors of temporaries in initialization expression should be called
2101*67e74705SXin Li // after initialization finishes.
2102*67e74705SXin Li Expr *Init = VD->getInit();
2103*67e74705SXin Li if (Init) {
2104*67e74705SXin Li HasTemporaries = isa<ExprWithCleanups>(Init);
2105*67e74705SXin Li
2106*67e74705SXin Li if (BuildOpts.AddTemporaryDtors && HasTemporaries) {
2107*67e74705SXin Li // Generate destructors for temporaries in initialization expression.
2108*67e74705SXin Li TempDtorContext Context;
2109*67e74705SXin Li VisitForTemporaryDtors(cast<ExprWithCleanups>(Init)->getSubExpr(),
2110*67e74705SXin Li /*BindToTemporary=*/false, Context);
2111*67e74705SXin Li }
2112*67e74705SXin Li }
2113*67e74705SXin Li
2114*67e74705SXin Li autoCreateBlock();
2115*67e74705SXin Li appendStmt(Block, DS);
2116*67e74705SXin Li
2117*67e74705SXin Li // Keep track of the last non-null block, as 'Block' can be nulled out
2118*67e74705SXin Li // if the initializer expression is something like a 'while' in a
2119*67e74705SXin Li // statement-expression.
2120*67e74705SXin Li CFGBlock *LastBlock = Block;
2121*67e74705SXin Li
2122*67e74705SXin Li if (Init) {
2123*67e74705SXin Li if (HasTemporaries) {
2124*67e74705SXin Li // For expression with temporaries go directly to subexpression to omit
2125*67e74705SXin Li // generating destructors for the second time.
2126*67e74705SXin Li ExprWithCleanups *EC = cast<ExprWithCleanups>(Init);
2127*67e74705SXin Li if (CFGBlock *newBlock = Visit(EC->getSubExpr()))
2128*67e74705SXin Li LastBlock = newBlock;
2129*67e74705SXin Li }
2130*67e74705SXin Li else {
2131*67e74705SXin Li if (CFGBlock *newBlock = Visit(Init))
2132*67e74705SXin Li LastBlock = newBlock;
2133*67e74705SXin Li }
2134*67e74705SXin Li }
2135*67e74705SXin Li
2136*67e74705SXin Li // If the type of VD is a VLA, then we must process its size expressions.
2137*67e74705SXin Li for (const VariableArrayType* VA = FindVA(VD->getType().getTypePtr());
2138*67e74705SXin Li VA != nullptr; VA = FindVA(VA->getElementType().getTypePtr())) {
2139*67e74705SXin Li if (CFGBlock *newBlock = addStmt(VA->getSizeExpr()))
2140*67e74705SXin Li LastBlock = newBlock;
2141*67e74705SXin Li }
2142*67e74705SXin Li
2143*67e74705SXin Li // Remove variable from local scope.
2144*67e74705SXin Li if (ScopePos && VD == *ScopePos)
2145*67e74705SXin Li ++ScopePos;
2146*67e74705SXin Li
2147*67e74705SXin Li CFGBlock *B = LastBlock;
2148*67e74705SXin Li if (blockAfterStaticInit) {
2149*67e74705SXin Li Succ = B;
2150*67e74705SXin Li Block = createBlock(false);
2151*67e74705SXin Li Block->setTerminator(DS);
2152*67e74705SXin Li addSuccessor(Block, blockAfterStaticInit);
2153*67e74705SXin Li addSuccessor(Block, B);
2154*67e74705SXin Li B = Block;
2155*67e74705SXin Li }
2156*67e74705SXin Li
2157*67e74705SXin Li return B;
2158*67e74705SXin Li }
2159*67e74705SXin Li
VisitIfStmt(IfStmt * I)2160*67e74705SXin Li CFGBlock *CFGBuilder::VisitIfStmt(IfStmt *I) {
2161*67e74705SXin Li // We may see an if statement in the middle of a basic block, or it may be the
2162*67e74705SXin Li // first statement we are processing. In either case, we create a new basic
2163*67e74705SXin Li // block. First, we create the blocks for the then...else statements, and
2164*67e74705SXin Li // then we create the block containing the if statement. If we were in the
2165*67e74705SXin Li // middle of a block, we stop processing that block. That block is then the
2166*67e74705SXin Li // implicit successor for the "then" and "else" clauses.
2167*67e74705SXin Li
2168*67e74705SXin Li // Save local scope position because in case of condition variable ScopePos
2169*67e74705SXin Li // won't be restored when traversing AST.
2170*67e74705SXin Li SaveAndRestore<LocalScope::const_iterator> save_scope_pos(ScopePos);
2171*67e74705SXin Li
2172*67e74705SXin Li // Create local scope for C++17 if init-stmt if one exists.
2173*67e74705SXin Li if (Stmt *Init = I->getInit()) {
2174*67e74705SXin Li LocalScope::const_iterator BeginScopePos = ScopePos;
2175*67e74705SXin Li addLocalScopeForStmt(Init);
2176*67e74705SXin Li addAutomaticObjDtors(ScopePos, BeginScopePos, I);
2177*67e74705SXin Li }
2178*67e74705SXin Li
2179*67e74705SXin Li // Create local scope for possible condition variable.
2180*67e74705SXin Li // Store scope position. Add implicit destructor.
2181*67e74705SXin Li if (VarDecl *VD = I->getConditionVariable()) {
2182*67e74705SXin Li LocalScope::const_iterator BeginScopePos = ScopePos;
2183*67e74705SXin Li addLocalScopeForVarDecl(VD);
2184*67e74705SXin Li addAutomaticObjDtors(ScopePos, BeginScopePos, I);
2185*67e74705SXin Li }
2186*67e74705SXin Li
2187*67e74705SXin Li // The block we were processing is now finished. Make it the successor
2188*67e74705SXin Li // block.
2189*67e74705SXin Li if (Block) {
2190*67e74705SXin Li Succ = Block;
2191*67e74705SXin Li if (badCFG)
2192*67e74705SXin Li return nullptr;
2193*67e74705SXin Li }
2194*67e74705SXin Li
2195*67e74705SXin Li // Process the false branch.
2196*67e74705SXin Li CFGBlock *ElseBlock = Succ;
2197*67e74705SXin Li
2198*67e74705SXin Li if (Stmt *Else = I->getElse()) {
2199*67e74705SXin Li SaveAndRestore<CFGBlock*> sv(Succ);
2200*67e74705SXin Li
2201*67e74705SXin Li // NULL out Block so that the recursive call to Visit will
2202*67e74705SXin Li // create a new basic block.
2203*67e74705SXin Li Block = nullptr;
2204*67e74705SXin Li
2205*67e74705SXin Li // If branch is not a compound statement create implicit scope
2206*67e74705SXin Li // and add destructors.
2207*67e74705SXin Li if (!isa<CompoundStmt>(Else))
2208*67e74705SXin Li addLocalScopeAndDtors(Else);
2209*67e74705SXin Li
2210*67e74705SXin Li ElseBlock = addStmt(Else);
2211*67e74705SXin Li
2212*67e74705SXin Li if (!ElseBlock) // Can occur when the Else body has all NullStmts.
2213*67e74705SXin Li ElseBlock = sv.get();
2214*67e74705SXin Li else if (Block) {
2215*67e74705SXin Li if (badCFG)
2216*67e74705SXin Li return nullptr;
2217*67e74705SXin Li }
2218*67e74705SXin Li }
2219*67e74705SXin Li
2220*67e74705SXin Li // Process the true branch.
2221*67e74705SXin Li CFGBlock *ThenBlock;
2222*67e74705SXin Li {
2223*67e74705SXin Li Stmt *Then = I->getThen();
2224*67e74705SXin Li assert(Then);
2225*67e74705SXin Li SaveAndRestore<CFGBlock*> sv(Succ);
2226*67e74705SXin Li Block = nullptr;
2227*67e74705SXin Li
2228*67e74705SXin Li // If branch is not a compound statement create implicit scope
2229*67e74705SXin Li // and add destructors.
2230*67e74705SXin Li if (!isa<CompoundStmt>(Then))
2231*67e74705SXin Li addLocalScopeAndDtors(Then);
2232*67e74705SXin Li
2233*67e74705SXin Li ThenBlock = addStmt(Then);
2234*67e74705SXin Li
2235*67e74705SXin Li if (!ThenBlock) {
2236*67e74705SXin Li // We can reach here if the "then" body has all NullStmts.
2237*67e74705SXin Li // Create an empty block so we can distinguish between true and false
2238*67e74705SXin Li // branches in path-sensitive analyses.
2239*67e74705SXin Li ThenBlock = createBlock(false);
2240*67e74705SXin Li addSuccessor(ThenBlock, sv.get());
2241*67e74705SXin Li } else if (Block) {
2242*67e74705SXin Li if (badCFG)
2243*67e74705SXin Li return nullptr;
2244*67e74705SXin Li }
2245*67e74705SXin Li }
2246*67e74705SXin Li
2247*67e74705SXin Li // Specially handle "if (expr1 || ...)" and "if (expr1 && ...)" by
2248*67e74705SXin Li // having these handle the actual control-flow jump. Note that
2249*67e74705SXin Li // if we introduce a condition variable, e.g. "if (int x = exp1 || exp2)"
2250*67e74705SXin Li // we resort to the old control-flow behavior. This special handling
2251*67e74705SXin Li // removes infeasible paths from the control-flow graph by having the
2252*67e74705SXin Li // control-flow transfer of '&&' or '||' go directly into the then/else
2253*67e74705SXin Li // blocks directly.
2254*67e74705SXin Li if (!I->getConditionVariable())
2255*67e74705SXin Li if (BinaryOperator *Cond =
2256*67e74705SXin Li dyn_cast<BinaryOperator>(I->getCond()->IgnoreParens()))
2257*67e74705SXin Li if (Cond->isLogicalOp())
2258*67e74705SXin Li return VisitLogicalOperator(Cond, I, ThenBlock, ElseBlock).first;
2259*67e74705SXin Li
2260*67e74705SXin Li // Now create a new block containing the if statement.
2261*67e74705SXin Li Block = createBlock(false);
2262*67e74705SXin Li
2263*67e74705SXin Li // Set the terminator of the new block to the If statement.
2264*67e74705SXin Li Block->setTerminator(I);
2265*67e74705SXin Li
2266*67e74705SXin Li // See if this is a known constant.
2267*67e74705SXin Li const TryResult &KnownVal = tryEvaluateBool(I->getCond());
2268*67e74705SXin Li
2269*67e74705SXin Li // Add the successors. If we know that specific branches are
2270*67e74705SXin Li // unreachable, inform addSuccessor() of that knowledge.
2271*67e74705SXin Li addSuccessor(Block, ThenBlock, /* isReachable = */ !KnownVal.isFalse());
2272*67e74705SXin Li addSuccessor(Block, ElseBlock, /* isReachable = */ !KnownVal.isTrue());
2273*67e74705SXin Li
2274*67e74705SXin Li // Add the condition as the last statement in the new block. This may create
2275*67e74705SXin Li // new blocks as the condition may contain control-flow. Any newly created
2276*67e74705SXin Li // blocks will be pointed to be "Block".
2277*67e74705SXin Li CFGBlock *LastBlock = addStmt(I->getCond());
2278*67e74705SXin Li
2279*67e74705SXin Li // If the IfStmt contains a condition variable, add it and its
2280*67e74705SXin Li // initializer to the CFG.
2281*67e74705SXin Li if (const DeclStmt* DS = I->getConditionVariableDeclStmt()) {
2282*67e74705SXin Li autoCreateBlock();
2283*67e74705SXin Li LastBlock = addStmt(const_cast<DeclStmt *>(DS));
2284*67e74705SXin Li }
2285*67e74705SXin Li
2286*67e74705SXin Li // Finally, if the IfStmt contains a C++17 init-stmt, add it to the CFG.
2287*67e74705SXin Li if (Stmt *Init = I->getInit()) {
2288*67e74705SXin Li autoCreateBlock();
2289*67e74705SXin Li LastBlock = addStmt(Init);
2290*67e74705SXin Li }
2291*67e74705SXin Li
2292*67e74705SXin Li return LastBlock;
2293*67e74705SXin Li }
2294*67e74705SXin Li
2295*67e74705SXin Li
VisitReturnStmt(ReturnStmt * R)2296*67e74705SXin Li CFGBlock *CFGBuilder::VisitReturnStmt(ReturnStmt *R) {
2297*67e74705SXin Li // If we were in the middle of a block we stop processing that block.
2298*67e74705SXin Li //
2299*67e74705SXin Li // NOTE: If a "return" appears in the middle of a block, this means that the
2300*67e74705SXin Li // code afterwards is DEAD (unreachable). We still keep a basic block
2301*67e74705SXin Li // for that code; a simple "mark-and-sweep" from the entry block will be
2302*67e74705SXin Li // able to report such dead blocks.
2303*67e74705SXin Li
2304*67e74705SXin Li // Create the new block.
2305*67e74705SXin Li Block = createBlock(false);
2306*67e74705SXin Li
2307*67e74705SXin Li addAutomaticObjDtors(ScopePos, LocalScope::const_iterator(), R);
2308*67e74705SXin Li
2309*67e74705SXin Li // If the one of the destructors does not return, we already have the Exit
2310*67e74705SXin Li // block as a successor.
2311*67e74705SXin Li if (!Block->hasNoReturnElement())
2312*67e74705SXin Li addSuccessor(Block, &cfg->getExit());
2313*67e74705SXin Li
2314*67e74705SXin Li // Add the return statement to the block. This may create new blocks if R
2315*67e74705SXin Li // contains control-flow (short-circuit operations).
2316*67e74705SXin Li return VisitStmt(R, AddStmtChoice::AlwaysAdd);
2317*67e74705SXin Li }
2318*67e74705SXin Li
VisitLabelStmt(LabelStmt * L)2319*67e74705SXin Li CFGBlock *CFGBuilder::VisitLabelStmt(LabelStmt *L) {
2320*67e74705SXin Li // Get the block of the labeled statement. Add it to our map.
2321*67e74705SXin Li addStmt(L->getSubStmt());
2322*67e74705SXin Li CFGBlock *LabelBlock = Block;
2323*67e74705SXin Li
2324*67e74705SXin Li if (!LabelBlock) // This can happen when the body is empty, i.e.
2325*67e74705SXin Li LabelBlock = createBlock(); // scopes that only contains NullStmts.
2326*67e74705SXin Li
2327*67e74705SXin Li assert(LabelMap.find(L->getDecl()) == LabelMap.end() &&
2328*67e74705SXin Li "label already in map");
2329*67e74705SXin Li LabelMap[L->getDecl()] = JumpTarget(LabelBlock, ScopePos);
2330*67e74705SXin Li
2331*67e74705SXin Li // Labels partition blocks, so this is the end of the basic block we were
2332*67e74705SXin Li // processing (L is the block's label). Because this is label (and we have
2333*67e74705SXin Li // already processed the substatement) there is no extra control-flow to worry
2334*67e74705SXin Li // about.
2335*67e74705SXin Li LabelBlock->setLabel(L);
2336*67e74705SXin Li if (badCFG)
2337*67e74705SXin Li return nullptr;
2338*67e74705SXin Li
2339*67e74705SXin Li // We set Block to NULL to allow lazy creation of a new block (if necessary);
2340*67e74705SXin Li Block = nullptr;
2341*67e74705SXin Li
2342*67e74705SXin Li // This block is now the implicit successor of other blocks.
2343*67e74705SXin Li Succ = LabelBlock;
2344*67e74705SXin Li
2345*67e74705SXin Li return LabelBlock;
2346*67e74705SXin Li }
2347*67e74705SXin Li
VisitBlockExpr(BlockExpr * E,AddStmtChoice asc)2348*67e74705SXin Li CFGBlock *CFGBuilder::VisitBlockExpr(BlockExpr *E, AddStmtChoice asc) {
2349*67e74705SXin Li CFGBlock *LastBlock = VisitNoRecurse(E, asc);
2350*67e74705SXin Li for (const BlockDecl::Capture &CI : E->getBlockDecl()->captures()) {
2351*67e74705SXin Li if (Expr *CopyExpr = CI.getCopyExpr()) {
2352*67e74705SXin Li CFGBlock *Tmp = Visit(CopyExpr);
2353*67e74705SXin Li if (Tmp)
2354*67e74705SXin Li LastBlock = Tmp;
2355*67e74705SXin Li }
2356*67e74705SXin Li }
2357*67e74705SXin Li return LastBlock;
2358*67e74705SXin Li }
2359*67e74705SXin Li
VisitLambdaExpr(LambdaExpr * E,AddStmtChoice asc)2360*67e74705SXin Li CFGBlock *CFGBuilder::VisitLambdaExpr(LambdaExpr *E, AddStmtChoice asc) {
2361*67e74705SXin Li CFGBlock *LastBlock = VisitNoRecurse(E, asc);
2362*67e74705SXin Li for (LambdaExpr::capture_init_iterator it = E->capture_init_begin(),
2363*67e74705SXin Li et = E->capture_init_end(); it != et; ++it) {
2364*67e74705SXin Li if (Expr *Init = *it) {
2365*67e74705SXin Li CFGBlock *Tmp = Visit(Init);
2366*67e74705SXin Li if (Tmp)
2367*67e74705SXin Li LastBlock = Tmp;
2368*67e74705SXin Li }
2369*67e74705SXin Li }
2370*67e74705SXin Li return LastBlock;
2371*67e74705SXin Li }
2372*67e74705SXin Li
VisitGotoStmt(GotoStmt * G)2373*67e74705SXin Li CFGBlock *CFGBuilder::VisitGotoStmt(GotoStmt *G) {
2374*67e74705SXin Li // Goto is a control-flow statement. Thus we stop processing the current
2375*67e74705SXin Li // block and create a new one.
2376*67e74705SXin Li
2377*67e74705SXin Li Block = createBlock(false);
2378*67e74705SXin Li Block->setTerminator(G);
2379*67e74705SXin Li
2380*67e74705SXin Li // If we already know the mapping to the label block add the successor now.
2381*67e74705SXin Li LabelMapTy::iterator I = LabelMap.find(G->getLabel());
2382*67e74705SXin Li
2383*67e74705SXin Li if (I == LabelMap.end())
2384*67e74705SXin Li // We will need to backpatch this block later.
2385*67e74705SXin Li BackpatchBlocks.push_back(JumpSource(Block, ScopePos));
2386*67e74705SXin Li else {
2387*67e74705SXin Li JumpTarget JT = I->second;
2388*67e74705SXin Li addAutomaticObjDtors(ScopePos, JT.scopePosition, G);
2389*67e74705SXin Li addSuccessor(Block, JT.block);
2390*67e74705SXin Li }
2391*67e74705SXin Li
2392*67e74705SXin Li return Block;
2393*67e74705SXin Li }
2394*67e74705SXin Li
VisitForStmt(ForStmt * F)2395*67e74705SXin Li CFGBlock *CFGBuilder::VisitForStmt(ForStmt *F) {
2396*67e74705SXin Li CFGBlock *LoopSuccessor = nullptr;
2397*67e74705SXin Li
2398*67e74705SXin Li // Save local scope position because in case of condition variable ScopePos
2399*67e74705SXin Li // won't be restored when traversing AST.
2400*67e74705SXin Li SaveAndRestore<LocalScope::const_iterator> save_scope_pos(ScopePos);
2401*67e74705SXin Li
2402*67e74705SXin Li // Create local scope for init statement and possible condition variable.
2403*67e74705SXin Li // Add destructor for init statement and condition variable.
2404*67e74705SXin Li // Store scope position for continue statement.
2405*67e74705SXin Li if (Stmt *Init = F->getInit())
2406*67e74705SXin Li addLocalScopeForStmt(Init);
2407*67e74705SXin Li LocalScope::const_iterator LoopBeginScopePos = ScopePos;
2408*67e74705SXin Li
2409*67e74705SXin Li if (VarDecl *VD = F->getConditionVariable())
2410*67e74705SXin Li addLocalScopeForVarDecl(VD);
2411*67e74705SXin Li LocalScope::const_iterator ContinueScopePos = ScopePos;
2412*67e74705SXin Li
2413*67e74705SXin Li addAutomaticObjDtors(ScopePos, save_scope_pos.get(), F);
2414*67e74705SXin Li
2415*67e74705SXin Li // "for" is a control-flow statement. Thus we stop processing the current
2416*67e74705SXin Li // block.
2417*67e74705SXin Li if (Block) {
2418*67e74705SXin Li if (badCFG)
2419*67e74705SXin Li return nullptr;
2420*67e74705SXin Li LoopSuccessor = Block;
2421*67e74705SXin Li } else
2422*67e74705SXin Li LoopSuccessor = Succ;
2423*67e74705SXin Li
2424*67e74705SXin Li // Save the current value for the break targets.
2425*67e74705SXin Li // All breaks should go to the code following the loop.
2426*67e74705SXin Li SaveAndRestore<JumpTarget> save_break(BreakJumpTarget);
2427*67e74705SXin Li BreakJumpTarget = JumpTarget(LoopSuccessor, ScopePos);
2428*67e74705SXin Li
2429*67e74705SXin Li CFGBlock *BodyBlock = nullptr, *TransitionBlock = nullptr;
2430*67e74705SXin Li
2431*67e74705SXin Li // Now create the loop body.
2432*67e74705SXin Li {
2433*67e74705SXin Li assert(F->getBody());
2434*67e74705SXin Li
2435*67e74705SXin Li // Save the current values for Block, Succ, continue and break targets.
2436*67e74705SXin Li SaveAndRestore<CFGBlock*> save_Block(Block), save_Succ(Succ);
2437*67e74705SXin Li SaveAndRestore<JumpTarget> save_continue(ContinueJumpTarget);
2438*67e74705SXin Li
2439*67e74705SXin Li // Create an empty block to represent the transition block for looping back
2440*67e74705SXin Li // to the head of the loop. If we have increment code, it will
2441*67e74705SXin Li // go in this block as well.
2442*67e74705SXin Li Block = Succ = TransitionBlock = createBlock(false);
2443*67e74705SXin Li TransitionBlock->setLoopTarget(F);
2444*67e74705SXin Li
2445*67e74705SXin Li if (Stmt *I = F->getInc()) {
2446*67e74705SXin Li // Generate increment code in its own basic block. This is the target of
2447*67e74705SXin Li // continue statements.
2448*67e74705SXin Li Succ = addStmt(I);
2449*67e74705SXin Li }
2450*67e74705SXin Li
2451*67e74705SXin Li // Finish up the increment (or empty) block if it hasn't been already.
2452*67e74705SXin Li if (Block) {
2453*67e74705SXin Li assert(Block == Succ);
2454*67e74705SXin Li if (badCFG)
2455*67e74705SXin Li return nullptr;
2456*67e74705SXin Li Block = nullptr;
2457*67e74705SXin Li }
2458*67e74705SXin Li
2459*67e74705SXin Li // The starting block for the loop increment is the block that should
2460*67e74705SXin Li // represent the 'loop target' for looping back to the start of the loop.
2461*67e74705SXin Li ContinueJumpTarget = JumpTarget(Succ, ContinueScopePos);
2462*67e74705SXin Li ContinueJumpTarget.block->setLoopTarget(F);
2463*67e74705SXin Li
2464*67e74705SXin Li // Loop body should end with destructor of Condition variable (if any).
2465*67e74705SXin Li addAutomaticObjDtors(ScopePos, LoopBeginScopePos, F);
2466*67e74705SXin Li
2467*67e74705SXin Li // If body is not a compound statement create implicit scope
2468*67e74705SXin Li // and add destructors.
2469*67e74705SXin Li if (!isa<CompoundStmt>(F->getBody()))
2470*67e74705SXin Li addLocalScopeAndDtors(F->getBody());
2471*67e74705SXin Li
2472*67e74705SXin Li // Now populate the body block, and in the process create new blocks as we
2473*67e74705SXin Li // walk the body of the loop.
2474*67e74705SXin Li BodyBlock = addStmt(F->getBody());
2475*67e74705SXin Li
2476*67e74705SXin Li if (!BodyBlock) {
2477*67e74705SXin Li // In the case of "for (...;...;...);" we can have a null BodyBlock.
2478*67e74705SXin Li // Use the continue jump target as the proxy for the body.
2479*67e74705SXin Li BodyBlock = ContinueJumpTarget.block;
2480*67e74705SXin Li }
2481*67e74705SXin Li else if (badCFG)
2482*67e74705SXin Li return nullptr;
2483*67e74705SXin Li }
2484*67e74705SXin Li
2485*67e74705SXin Li // Because of short-circuit evaluation, the condition of the loop can span
2486*67e74705SXin Li // multiple basic blocks. Thus we need the "Entry" and "Exit" blocks that
2487*67e74705SXin Li // evaluate the condition.
2488*67e74705SXin Li CFGBlock *EntryConditionBlock = nullptr, *ExitConditionBlock = nullptr;
2489*67e74705SXin Li
2490*67e74705SXin Li do {
2491*67e74705SXin Li Expr *C = F->getCond();
2492*67e74705SXin Li
2493*67e74705SXin Li // Specially handle logical operators, which have a slightly
2494*67e74705SXin Li // more optimal CFG representation.
2495*67e74705SXin Li if (BinaryOperator *Cond =
2496*67e74705SXin Li dyn_cast_or_null<BinaryOperator>(C ? C->IgnoreParens() : nullptr))
2497*67e74705SXin Li if (Cond->isLogicalOp()) {
2498*67e74705SXin Li std::tie(EntryConditionBlock, ExitConditionBlock) =
2499*67e74705SXin Li VisitLogicalOperator(Cond, F, BodyBlock, LoopSuccessor);
2500*67e74705SXin Li break;
2501*67e74705SXin Li }
2502*67e74705SXin Li
2503*67e74705SXin Li // The default case when not handling logical operators.
2504*67e74705SXin Li EntryConditionBlock = ExitConditionBlock = createBlock(false);
2505*67e74705SXin Li ExitConditionBlock->setTerminator(F);
2506*67e74705SXin Li
2507*67e74705SXin Li // See if this is a known constant.
2508*67e74705SXin Li TryResult KnownVal(true);
2509*67e74705SXin Li
2510*67e74705SXin Li if (C) {
2511*67e74705SXin Li // Now add the actual condition to the condition block.
2512*67e74705SXin Li // Because the condition itself may contain control-flow, new blocks may
2513*67e74705SXin Li // be created. Thus we update "Succ" after adding the condition.
2514*67e74705SXin Li Block = ExitConditionBlock;
2515*67e74705SXin Li EntryConditionBlock = addStmt(C);
2516*67e74705SXin Li
2517*67e74705SXin Li // If this block contains a condition variable, add both the condition
2518*67e74705SXin Li // variable and initializer to the CFG.
2519*67e74705SXin Li if (VarDecl *VD = F->getConditionVariable()) {
2520*67e74705SXin Li if (Expr *Init = VD->getInit()) {
2521*67e74705SXin Li autoCreateBlock();
2522*67e74705SXin Li appendStmt(Block, F->getConditionVariableDeclStmt());
2523*67e74705SXin Li EntryConditionBlock = addStmt(Init);
2524*67e74705SXin Li assert(Block == EntryConditionBlock);
2525*67e74705SXin Li }
2526*67e74705SXin Li }
2527*67e74705SXin Li
2528*67e74705SXin Li if (Block && badCFG)
2529*67e74705SXin Li return nullptr;
2530*67e74705SXin Li
2531*67e74705SXin Li KnownVal = tryEvaluateBool(C);
2532*67e74705SXin Li }
2533*67e74705SXin Li
2534*67e74705SXin Li // Add the loop body entry as a successor to the condition.
2535*67e74705SXin Li addSuccessor(ExitConditionBlock, KnownVal.isFalse() ? nullptr : BodyBlock);
2536*67e74705SXin Li // Link up the condition block with the code that follows the loop. (the
2537*67e74705SXin Li // false branch).
2538*67e74705SXin Li addSuccessor(ExitConditionBlock,
2539*67e74705SXin Li KnownVal.isTrue() ? nullptr : LoopSuccessor);
2540*67e74705SXin Li
2541*67e74705SXin Li } while (false);
2542*67e74705SXin Li
2543*67e74705SXin Li // Link up the loop-back block to the entry condition block.
2544*67e74705SXin Li addSuccessor(TransitionBlock, EntryConditionBlock);
2545*67e74705SXin Li
2546*67e74705SXin Li // The condition block is the implicit successor for any code above the loop.
2547*67e74705SXin Li Succ = EntryConditionBlock;
2548*67e74705SXin Li
2549*67e74705SXin Li // If the loop contains initialization, create a new block for those
2550*67e74705SXin Li // statements. This block can also contain statements that precede the loop.
2551*67e74705SXin Li if (Stmt *I = F->getInit()) {
2552*67e74705SXin Li Block = createBlock();
2553*67e74705SXin Li return addStmt(I);
2554*67e74705SXin Li }
2555*67e74705SXin Li
2556*67e74705SXin Li // There is no loop initialization. We are thus basically a while loop.
2557*67e74705SXin Li // NULL out Block to force lazy block construction.
2558*67e74705SXin Li Block = nullptr;
2559*67e74705SXin Li Succ = EntryConditionBlock;
2560*67e74705SXin Li return EntryConditionBlock;
2561*67e74705SXin Li }
2562*67e74705SXin Li
VisitMemberExpr(MemberExpr * M,AddStmtChoice asc)2563*67e74705SXin Li CFGBlock *CFGBuilder::VisitMemberExpr(MemberExpr *M, AddStmtChoice asc) {
2564*67e74705SXin Li if (asc.alwaysAdd(*this, M)) {
2565*67e74705SXin Li autoCreateBlock();
2566*67e74705SXin Li appendStmt(Block, M);
2567*67e74705SXin Li }
2568*67e74705SXin Li return Visit(M->getBase());
2569*67e74705SXin Li }
2570*67e74705SXin Li
VisitObjCForCollectionStmt(ObjCForCollectionStmt * S)2571*67e74705SXin Li CFGBlock *CFGBuilder::VisitObjCForCollectionStmt(ObjCForCollectionStmt *S) {
2572*67e74705SXin Li // Objective-C fast enumeration 'for' statements:
2573*67e74705SXin Li // http://developer.apple.com/documentation/Cocoa/Conceptual/ObjectiveC
2574*67e74705SXin Li //
2575*67e74705SXin Li // for ( Type newVariable in collection_expression ) { statements }
2576*67e74705SXin Li //
2577*67e74705SXin Li // becomes:
2578*67e74705SXin Li //
2579*67e74705SXin Li // prologue:
2580*67e74705SXin Li // 1. collection_expression
2581*67e74705SXin Li // T. jump to loop_entry
2582*67e74705SXin Li // loop_entry:
2583*67e74705SXin Li // 1. side-effects of element expression
2584*67e74705SXin Li // 1. ObjCForCollectionStmt [performs binding to newVariable]
2585*67e74705SXin Li // T. ObjCForCollectionStmt TB, FB [jumps to TB if newVariable != nil]
2586*67e74705SXin Li // TB:
2587*67e74705SXin Li // statements
2588*67e74705SXin Li // T. jump to loop_entry
2589*67e74705SXin Li // FB:
2590*67e74705SXin Li // what comes after
2591*67e74705SXin Li //
2592*67e74705SXin Li // and
2593*67e74705SXin Li //
2594*67e74705SXin Li // Type existingItem;
2595*67e74705SXin Li // for ( existingItem in expression ) { statements }
2596*67e74705SXin Li //
2597*67e74705SXin Li // becomes:
2598*67e74705SXin Li //
2599*67e74705SXin Li // the same with newVariable replaced with existingItem; the binding works
2600*67e74705SXin Li // the same except that for one ObjCForCollectionStmt::getElement() returns
2601*67e74705SXin Li // a DeclStmt and the other returns a DeclRefExpr.
2602*67e74705SXin Li //
2603*67e74705SXin Li
2604*67e74705SXin Li CFGBlock *LoopSuccessor = nullptr;
2605*67e74705SXin Li
2606*67e74705SXin Li if (Block) {
2607*67e74705SXin Li if (badCFG)
2608*67e74705SXin Li return nullptr;
2609*67e74705SXin Li LoopSuccessor = Block;
2610*67e74705SXin Li Block = nullptr;
2611*67e74705SXin Li } else
2612*67e74705SXin Li LoopSuccessor = Succ;
2613*67e74705SXin Li
2614*67e74705SXin Li // Build the condition blocks.
2615*67e74705SXin Li CFGBlock *ExitConditionBlock = createBlock(false);
2616*67e74705SXin Li
2617*67e74705SXin Li // Set the terminator for the "exit" condition block.
2618*67e74705SXin Li ExitConditionBlock->setTerminator(S);
2619*67e74705SXin Li
2620*67e74705SXin Li // The last statement in the block should be the ObjCForCollectionStmt, which
2621*67e74705SXin Li // performs the actual binding to 'element' and determines if there are any
2622*67e74705SXin Li // more items in the collection.
2623*67e74705SXin Li appendStmt(ExitConditionBlock, S);
2624*67e74705SXin Li Block = ExitConditionBlock;
2625*67e74705SXin Li
2626*67e74705SXin Li // Walk the 'element' expression to see if there are any side-effects. We
2627*67e74705SXin Li // generate new blocks as necessary. We DON'T add the statement by default to
2628*67e74705SXin Li // the CFG unless it contains control-flow.
2629*67e74705SXin Li CFGBlock *EntryConditionBlock = Visit(S->getElement(),
2630*67e74705SXin Li AddStmtChoice::NotAlwaysAdd);
2631*67e74705SXin Li if (Block) {
2632*67e74705SXin Li if (badCFG)
2633*67e74705SXin Li return nullptr;
2634*67e74705SXin Li Block = nullptr;
2635*67e74705SXin Li }
2636*67e74705SXin Li
2637*67e74705SXin Li // The condition block is the implicit successor for the loop body as well as
2638*67e74705SXin Li // any code above the loop.
2639*67e74705SXin Li Succ = EntryConditionBlock;
2640*67e74705SXin Li
2641*67e74705SXin Li // Now create the true branch.
2642*67e74705SXin Li {
2643*67e74705SXin Li // Save the current values for Succ, continue and break targets.
2644*67e74705SXin Li SaveAndRestore<CFGBlock*> save_Block(Block), save_Succ(Succ);
2645*67e74705SXin Li SaveAndRestore<JumpTarget> save_continue(ContinueJumpTarget),
2646*67e74705SXin Li save_break(BreakJumpTarget);
2647*67e74705SXin Li
2648*67e74705SXin Li // Add an intermediate block between the BodyBlock and the
2649*67e74705SXin Li // EntryConditionBlock to represent the "loop back" transition, for looping
2650*67e74705SXin Li // back to the head of the loop.
2651*67e74705SXin Li CFGBlock *LoopBackBlock = nullptr;
2652*67e74705SXin Li Succ = LoopBackBlock = createBlock();
2653*67e74705SXin Li LoopBackBlock->setLoopTarget(S);
2654*67e74705SXin Li
2655*67e74705SXin Li BreakJumpTarget = JumpTarget(LoopSuccessor, ScopePos);
2656*67e74705SXin Li ContinueJumpTarget = JumpTarget(Succ, ScopePos);
2657*67e74705SXin Li
2658*67e74705SXin Li CFGBlock *BodyBlock = addStmt(S->getBody());
2659*67e74705SXin Li
2660*67e74705SXin Li if (!BodyBlock)
2661*67e74705SXin Li BodyBlock = ContinueJumpTarget.block; // can happen for "for (X in Y) ;"
2662*67e74705SXin Li else if (Block) {
2663*67e74705SXin Li if (badCFG)
2664*67e74705SXin Li return nullptr;
2665*67e74705SXin Li }
2666*67e74705SXin Li
2667*67e74705SXin Li // This new body block is a successor to our "exit" condition block.
2668*67e74705SXin Li addSuccessor(ExitConditionBlock, BodyBlock);
2669*67e74705SXin Li }
2670*67e74705SXin Li
2671*67e74705SXin Li // Link up the condition block with the code that follows the loop.
2672*67e74705SXin Li // (the false branch).
2673*67e74705SXin Li addSuccessor(ExitConditionBlock, LoopSuccessor);
2674*67e74705SXin Li
2675*67e74705SXin Li // Now create a prologue block to contain the collection expression.
2676*67e74705SXin Li Block = createBlock();
2677*67e74705SXin Li return addStmt(S->getCollection());
2678*67e74705SXin Li }
2679*67e74705SXin Li
VisitObjCAutoreleasePoolStmt(ObjCAutoreleasePoolStmt * S)2680*67e74705SXin Li CFGBlock *CFGBuilder::VisitObjCAutoreleasePoolStmt(ObjCAutoreleasePoolStmt *S) {
2681*67e74705SXin Li // Inline the body.
2682*67e74705SXin Li return addStmt(S->getSubStmt());
2683*67e74705SXin Li // TODO: consider adding cleanups for the end of @autoreleasepool scope.
2684*67e74705SXin Li }
2685*67e74705SXin Li
VisitObjCAtSynchronizedStmt(ObjCAtSynchronizedStmt * S)2686*67e74705SXin Li CFGBlock *CFGBuilder::VisitObjCAtSynchronizedStmt(ObjCAtSynchronizedStmt *S) {
2687*67e74705SXin Li // FIXME: Add locking 'primitives' to CFG for @synchronized.
2688*67e74705SXin Li
2689*67e74705SXin Li // Inline the body.
2690*67e74705SXin Li CFGBlock *SyncBlock = addStmt(S->getSynchBody());
2691*67e74705SXin Li
2692*67e74705SXin Li // The sync body starts its own basic block. This makes it a little easier
2693*67e74705SXin Li // for diagnostic clients.
2694*67e74705SXin Li if (SyncBlock) {
2695*67e74705SXin Li if (badCFG)
2696*67e74705SXin Li return nullptr;
2697*67e74705SXin Li
2698*67e74705SXin Li Block = nullptr;
2699*67e74705SXin Li Succ = SyncBlock;
2700*67e74705SXin Li }
2701*67e74705SXin Li
2702*67e74705SXin Li // Add the @synchronized to the CFG.
2703*67e74705SXin Li autoCreateBlock();
2704*67e74705SXin Li appendStmt(Block, S);
2705*67e74705SXin Li
2706*67e74705SXin Li // Inline the sync expression.
2707*67e74705SXin Li return addStmt(S->getSynchExpr());
2708*67e74705SXin Li }
2709*67e74705SXin Li
VisitObjCAtTryStmt(ObjCAtTryStmt * S)2710*67e74705SXin Li CFGBlock *CFGBuilder::VisitObjCAtTryStmt(ObjCAtTryStmt *S) {
2711*67e74705SXin Li // FIXME
2712*67e74705SXin Li return NYS();
2713*67e74705SXin Li }
2714*67e74705SXin Li
VisitPseudoObjectExpr(PseudoObjectExpr * E)2715*67e74705SXin Li CFGBlock *CFGBuilder::VisitPseudoObjectExpr(PseudoObjectExpr *E) {
2716*67e74705SXin Li autoCreateBlock();
2717*67e74705SXin Li
2718*67e74705SXin Li // Add the PseudoObject as the last thing.
2719*67e74705SXin Li appendStmt(Block, E);
2720*67e74705SXin Li
2721*67e74705SXin Li CFGBlock *lastBlock = Block;
2722*67e74705SXin Li
2723*67e74705SXin Li // Before that, evaluate all of the semantics in order. In
2724*67e74705SXin Li // CFG-land, that means appending them in reverse order.
2725*67e74705SXin Li for (unsigned i = E->getNumSemanticExprs(); i != 0; ) {
2726*67e74705SXin Li Expr *Semantic = E->getSemanticExpr(--i);
2727*67e74705SXin Li
2728*67e74705SXin Li // If the semantic is an opaque value, we're being asked to bind
2729*67e74705SXin Li // it to its source expression.
2730*67e74705SXin Li if (OpaqueValueExpr *OVE = dyn_cast<OpaqueValueExpr>(Semantic))
2731*67e74705SXin Li Semantic = OVE->getSourceExpr();
2732*67e74705SXin Li
2733*67e74705SXin Li if (CFGBlock *B = Visit(Semantic))
2734*67e74705SXin Li lastBlock = B;
2735*67e74705SXin Li }
2736*67e74705SXin Li
2737*67e74705SXin Li return lastBlock;
2738*67e74705SXin Li }
2739*67e74705SXin Li
VisitWhileStmt(WhileStmt * W)2740*67e74705SXin Li CFGBlock *CFGBuilder::VisitWhileStmt(WhileStmt *W) {
2741*67e74705SXin Li CFGBlock *LoopSuccessor = nullptr;
2742*67e74705SXin Li
2743*67e74705SXin Li // Save local scope position because in case of condition variable ScopePos
2744*67e74705SXin Li // won't be restored when traversing AST.
2745*67e74705SXin Li SaveAndRestore<LocalScope::const_iterator> save_scope_pos(ScopePos);
2746*67e74705SXin Li
2747*67e74705SXin Li // Create local scope for possible condition variable.
2748*67e74705SXin Li // Store scope position for continue statement.
2749*67e74705SXin Li LocalScope::const_iterator LoopBeginScopePos = ScopePos;
2750*67e74705SXin Li if (VarDecl *VD = W->getConditionVariable()) {
2751*67e74705SXin Li addLocalScopeForVarDecl(VD);
2752*67e74705SXin Li addAutomaticObjDtors(ScopePos, LoopBeginScopePos, W);
2753*67e74705SXin Li }
2754*67e74705SXin Li
2755*67e74705SXin Li // "while" is a control-flow statement. Thus we stop processing the current
2756*67e74705SXin Li // block.
2757*67e74705SXin Li if (Block) {
2758*67e74705SXin Li if (badCFG)
2759*67e74705SXin Li return nullptr;
2760*67e74705SXin Li LoopSuccessor = Block;
2761*67e74705SXin Li Block = nullptr;
2762*67e74705SXin Li } else {
2763*67e74705SXin Li LoopSuccessor = Succ;
2764*67e74705SXin Li }
2765*67e74705SXin Li
2766*67e74705SXin Li CFGBlock *BodyBlock = nullptr, *TransitionBlock = nullptr;
2767*67e74705SXin Li
2768*67e74705SXin Li // Process the loop body.
2769*67e74705SXin Li {
2770*67e74705SXin Li assert(W->getBody());
2771*67e74705SXin Li
2772*67e74705SXin Li // Save the current values for Block, Succ, continue and break targets.
2773*67e74705SXin Li SaveAndRestore<CFGBlock*> save_Block(Block), save_Succ(Succ);
2774*67e74705SXin Li SaveAndRestore<JumpTarget> save_continue(ContinueJumpTarget),
2775*67e74705SXin Li save_break(BreakJumpTarget);
2776*67e74705SXin Li
2777*67e74705SXin Li // Create an empty block to represent the transition block for looping back
2778*67e74705SXin Li // to the head of the loop.
2779*67e74705SXin Li Succ = TransitionBlock = createBlock(false);
2780*67e74705SXin Li TransitionBlock->setLoopTarget(W);
2781*67e74705SXin Li ContinueJumpTarget = JumpTarget(Succ, LoopBeginScopePos);
2782*67e74705SXin Li
2783*67e74705SXin Li // All breaks should go to the code following the loop.
2784*67e74705SXin Li BreakJumpTarget = JumpTarget(LoopSuccessor, ScopePos);
2785*67e74705SXin Li
2786*67e74705SXin Li // Loop body should end with destructor of Condition variable (if any).
2787*67e74705SXin Li addAutomaticObjDtors(ScopePos, LoopBeginScopePos, W);
2788*67e74705SXin Li
2789*67e74705SXin Li // If body is not a compound statement create implicit scope
2790*67e74705SXin Li // and add destructors.
2791*67e74705SXin Li if (!isa<CompoundStmt>(W->getBody()))
2792*67e74705SXin Li addLocalScopeAndDtors(W->getBody());
2793*67e74705SXin Li
2794*67e74705SXin Li // Create the body. The returned block is the entry to the loop body.
2795*67e74705SXin Li BodyBlock = addStmt(W->getBody());
2796*67e74705SXin Li
2797*67e74705SXin Li if (!BodyBlock)
2798*67e74705SXin Li BodyBlock = ContinueJumpTarget.block; // can happen for "while(...) ;"
2799*67e74705SXin Li else if (Block && badCFG)
2800*67e74705SXin Li return nullptr;
2801*67e74705SXin Li }
2802*67e74705SXin Li
2803*67e74705SXin Li // Because of short-circuit evaluation, the condition of the loop can span
2804*67e74705SXin Li // multiple basic blocks. Thus we need the "Entry" and "Exit" blocks that
2805*67e74705SXin Li // evaluate the condition.
2806*67e74705SXin Li CFGBlock *EntryConditionBlock = nullptr, *ExitConditionBlock = nullptr;
2807*67e74705SXin Li
2808*67e74705SXin Li do {
2809*67e74705SXin Li Expr *C = W->getCond();
2810*67e74705SXin Li
2811*67e74705SXin Li // Specially handle logical operators, which have a slightly
2812*67e74705SXin Li // more optimal CFG representation.
2813*67e74705SXin Li if (BinaryOperator *Cond = dyn_cast<BinaryOperator>(C->IgnoreParens()))
2814*67e74705SXin Li if (Cond->isLogicalOp()) {
2815*67e74705SXin Li std::tie(EntryConditionBlock, ExitConditionBlock) =
2816*67e74705SXin Li VisitLogicalOperator(Cond, W, BodyBlock, LoopSuccessor);
2817*67e74705SXin Li break;
2818*67e74705SXin Li }
2819*67e74705SXin Li
2820*67e74705SXin Li // The default case when not handling logical operators.
2821*67e74705SXin Li ExitConditionBlock = createBlock(false);
2822*67e74705SXin Li ExitConditionBlock->setTerminator(W);
2823*67e74705SXin Li
2824*67e74705SXin Li // Now add the actual condition to the condition block.
2825*67e74705SXin Li // Because the condition itself may contain control-flow, new blocks may
2826*67e74705SXin Li // be created. Thus we update "Succ" after adding the condition.
2827*67e74705SXin Li Block = ExitConditionBlock;
2828*67e74705SXin Li Block = EntryConditionBlock = addStmt(C);
2829*67e74705SXin Li
2830*67e74705SXin Li // If this block contains a condition variable, add both the condition
2831*67e74705SXin Li // variable and initializer to the CFG.
2832*67e74705SXin Li if (VarDecl *VD = W->getConditionVariable()) {
2833*67e74705SXin Li if (Expr *Init = VD->getInit()) {
2834*67e74705SXin Li autoCreateBlock();
2835*67e74705SXin Li appendStmt(Block, W->getConditionVariableDeclStmt());
2836*67e74705SXin Li EntryConditionBlock = addStmt(Init);
2837*67e74705SXin Li assert(Block == EntryConditionBlock);
2838*67e74705SXin Li }
2839*67e74705SXin Li }
2840*67e74705SXin Li
2841*67e74705SXin Li if (Block && badCFG)
2842*67e74705SXin Li return nullptr;
2843*67e74705SXin Li
2844*67e74705SXin Li // See if this is a known constant.
2845*67e74705SXin Li const TryResult& KnownVal = tryEvaluateBool(C);
2846*67e74705SXin Li
2847*67e74705SXin Li // Add the loop body entry as a successor to the condition.
2848*67e74705SXin Li addSuccessor(ExitConditionBlock, KnownVal.isFalse() ? nullptr : BodyBlock);
2849*67e74705SXin Li // Link up the condition block with the code that follows the loop. (the
2850*67e74705SXin Li // false branch).
2851*67e74705SXin Li addSuccessor(ExitConditionBlock,
2852*67e74705SXin Li KnownVal.isTrue() ? nullptr : LoopSuccessor);
2853*67e74705SXin Li
2854*67e74705SXin Li } while(false);
2855*67e74705SXin Li
2856*67e74705SXin Li // Link up the loop-back block to the entry condition block.
2857*67e74705SXin Li addSuccessor(TransitionBlock, EntryConditionBlock);
2858*67e74705SXin Li
2859*67e74705SXin Li // There can be no more statements in the condition block since we loop back
2860*67e74705SXin Li // to this block. NULL out Block to force lazy creation of another block.
2861*67e74705SXin Li Block = nullptr;
2862*67e74705SXin Li
2863*67e74705SXin Li // Return the condition block, which is the dominating block for the loop.
2864*67e74705SXin Li Succ = EntryConditionBlock;
2865*67e74705SXin Li return EntryConditionBlock;
2866*67e74705SXin Li }
2867*67e74705SXin Li
2868*67e74705SXin Li
VisitObjCAtCatchStmt(ObjCAtCatchStmt * S)2869*67e74705SXin Li CFGBlock *CFGBuilder::VisitObjCAtCatchStmt(ObjCAtCatchStmt *S) {
2870*67e74705SXin Li // FIXME: For now we pretend that @catch and the code it contains does not
2871*67e74705SXin Li // exit.
2872*67e74705SXin Li return Block;
2873*67e74705SXin Li }
2874*67e74705SXin Li
VisitObjCAtThrowStmt(ObjCAtThrowStmt * S)2875*67e74705SXin Li CFGBlock *CFGBuilder::VisitObjCAtThrowStmt(ObjCAtThrowStmt *S) {
2876*67e74705SXin Li // FIXME: This isn't complete. We basically treat @throw like a return
2877*67e74705SXin Li // statement.
2878*67e74705SXin Li
2879*67e74705SXin Li // If we were in the middle of a block we stop processing that block.
2880*67e74705SXin Li if (badCFG)
2881*67e74705SXin Li return nullptr;
2882*67e74705SXin Li
2883*67e74705SXin Li // Create the new block.
2884*67e74705SXin Li Block = createBlock(false);
2885*67e74705SXin Li
2886*67e74705SXin Li // The Exit block is the only successor.
2887*67e74705SXin Li addSuccessor(Block, &cfg->getExit());
2888*67e74705SXin Li
2889*67e74705SXin Li // Add the statement to the block. This may create new blocks if S contains
2890*67e74705SXin Li // control-flow (short-circuit operations).
2891*67e74705SXin Li return VisitStmt(S, AddStmtChoice::AlwaysAdd);
2892*67e74705SXin Li }
2893*67e74705SXin Li
VisitCXXThrowExpr(CXXThrowExpr * T)2894*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXThrowExpr(CXXThrowExpr *T) {
2895*67e74705SXin Li // If we were in the middle of a block we stop processing that block.
2896*67e74705SXin Li if (badCFG)
2897*67e74705SXin Li return nullptr;
2898*67e74705SXin Li
2899*67e74705SXin Li // Create the new block.
2900*67e74705SXin Li Block = createBlock(false);
2901*67e74705SXin Li
2902*67e74705SXin Li if (TryTerminatedBlock)
2903*67e74705SXin Li // The current try statement is the only successor.
2904*67e74705SXin Li addSuccessor(Block, TryTerminatedBlock);
2905*67e74705SXin Li else
2906*67e74705SXin Li // otherwise the Exit block is the only successor.
2907*67e74705SXin Li addSuccessor(Block, &cfg->getExit());
2908*67e74705SXin Li
2909*67e74705SXin Li // Add the statement to the block. This may create new blocks if S contains
2910*67e74705SXin Li // control-flow (short-circuit operations).
2911*67e74705SXin Li return VisitStmt(T, AddStmtChoice::AlwaysAdd);
2912*67e74705SXin Li }
2913*67e74705SXin Li
VisitDoStmt(DoStmt * D)2914*67e74705SXin Li CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
2915*67e74705SXin Li CFGBlock *LoopSuccessor = nullptr;
2916*67e74705SXin Li
2917*67e74705SXin Li // "do...while" is a control-flow statement. Thus we stop processing the
2918*67e74705SXin Li // current block.
2919*67e74705SXin Li if (Block) {
2920*67e74705SXin Li if (badCFG)
2921*67e74705SXin Li return nullptr;
2922*67e74705SXin Li LoopSuccessor = Block;
2923*67e74705SXin Li } else
2924*67e74705SXin Li LoopSuccessor = Succ;
2925*67e74705SXin Li
2926*67e74705SXin Li // Because of short-circuit evaluation, the condition of the loop can span
2927*67e74705SXin Li // multiple basic blocks. Thus we need the "Entry" and "Exit" blocks that
2928*67e74705SXin Li // evaluate the condition.
2929*67e74705SXin Li CFGBlock *ExitConditionBlock = createBlock(false);
2930*67e74705SXin Li CFGBlock *EntryConditionBlock = ExitConditionBlock;
2931*67e74705SXin Li
2932*67e74705SXin Li // Set the terminator for the "exit" condition block.
2933*67e74705SXin Li ExitConditionBlock->setTerminator(D);
2934*67e74705SXin Li
2935*67e74705SXin Li // Now add the actual condition to the condition block. Because the condition
2936*67e74705SXin Li // itself may contain control-flow, new blocks may be created.
2937*67e74705SXin Li if (Stmt *C = D->getCond()) {
2938*67e74705SXin Li Block = ExitConditionBlock;
2939*67e74705SXin Li EntryConditionBlock = addStmt(C);
2940*67e74705SXin Li if (Block) {
2941*67e74705SXin Li if (badCFG)
2942*67e74705SXin Li return nullptr;
2943*67e74705SXin Li }
2944*67e74705SXin Li }
2945*67e74705SXin Li
2946*67e74705SXin Li // The condition block is the implicit successor for the loop body.
2947*67e74705SXin Li Succ = EntryConditionBlock;
2948*67e74705SXin Li
2949*67e74705SXin Li // See if this is a known constant.
2950*67e74705SXin Li const TryResult &KnownVal = tryEvaluateBool(D->getCond());
2951*67e74705SXin Li
2952*67e74705SXin Li // Process the loop body.
2953*67e74705SXin Li CFGBlock *BodyBlock = nullptr;
2954*67e74705SXin Li {
2955*67e74705SXin Li assert(D->getBody());
2956*67e74705SXin Li
2957*67e74705SXin Li // Save the current values for Block, Succ, and continue and break targets
2958*67e74705SXin Li SaveAndRestore<CFGBlock*> save_Block(Block), save_Succ(Succ);
2959*67e74705SXin Li SaveAndRestore<JumpTarget> save_continue(ContinueJumpTarget),
2960*67e74705SXin Li save_break(BreakJumpTarget);
2961*67e74705SXin Li
2962*67e74705SXin Li // All continues within this loop should go to the condition block
2963*67e74705SXin Li ContinueJumpTarget = JumpTarget(EntryConditionBlock, ScopePos);
2964*67e74705SXin Li
2965*67e74705SXin Li // All breaks should go to the code following the loop.
2966*67e74705SXin Li BreakJumpTarget = JumpTarget(LoopSuccessor, ScopePos);
2967*67e74705SXin Li
2968*67e74705SXin Li // NULL out Block to force lazy instantiation of blocks for the body.
2969*67e74705SXin Li Block = nullptr;
2970*67e74705SXin Li
2971*67e74705SXin Li // If body is not a compound statement create implicit scope
2972*67e74705SXin Li // and add destructors.
2973*67e74705SXin Li if (!isa<CompoundStmt>(D->getBody()))
2974*67e74705SXin Li addLocalScopeAndDtors(D->getBody());
2975*67e74705SXin Li
2976*67e74705SXin Li // Create the body. The returned block is the entry to the loop body.
2977*67e74705SXin Li BodyBlock = addStmt(D->getBody());
2978*67e74705SXin Li
2979*67e74705SXin Li if (!BodyBlock)
2980*67e74705SXin Li BodyBlock = EntryConditionBlock; // can happen for "do ; while(...)"
2981*67e74705SXin Li else if (Block) {
2982*67e74705SXin Li if (badCFG)
2983*67e74705SXin Li return nullptr;
2984*67e74705SXin Li }
2985*67e74705SXin Li
2986*67e74705SXin Li if (!KnownVal.isFalse()) {
2987*67e74705SXin Li // Add an intermediate block between the BodyBlock and the
2988*67e74705SXin Li // ExitConditionBlock to represent the "loop back" transition. Create an
2989*67e74705SXin Li // empty block to represent the transition block for looping back to the
2990*67e74705SXin Li // head of the loop.
2991*67e74705SXin Li // FIXME: Can we do this more efficiently without adding another block?
2992*67e74705SXin Li Block = nullptr;
2993*67e74705SXin Li Succ = BodyBlock;
2994*67e74705SXin Li CFGBlock *LoopBackBlock = createBlock();
2995*67e74705SXin Li LoopBackBlock->setLoopTarget(D);
2996*67e74705SXin Li
2997*67e74705SXin Li // Add the loop body entry as a successor to the condition.
2998*67e74705SXin Li addSuccessor(ExitConditionBlock, LoopBackBlock);
2999*67e74705SXin Li }
3000*67e74705SXin Li else
3001*67e74705SXin Li addSuccessor(ExitConditionBlock, nullptr);
3002*67e74705SXin Li }
3003*67e74705SXin Li
3004*67e74705SXin Li // Link up the condition block with the code that follows the loop.
3005*67e74705SXin Li // (the false branch).
3006*67e74705SXin Li addSuccessor(ExitConditionBlock, KnownVal.isTrue() ? nullptr : LoopSuccessor);
3007*67e74705SXin Li
3008*67e74705SXin Li // There can be no more statements in the body block(s) since we loop back to
3009*67e74705SXin Li // the body. NULL out Block to force lazy creation of another block.
3010*67e74705SXin Li Block = nullptr;
3011*67e74705SXin Li
3012*67e74705SXin Li // Return the loop body, which is the dominating block for the loop.
3013*67e74705SXin Li Succ = BodyBlock;
3014*67e74705SXin Li return BodyBlock;
3015*67e74705SXin Li }
3016*67e74705SXin Li
VisitContinueStmt(ContinueStmt * C)3017*67e74705SXin Li CFGBlock *CFGBuilder::VisitContinueStmt(ContinueStmt *C) {
3018*67e74705SXin Li // "continue" is a control-flow statement. Thus we stop processing the
3019*67e74705SXin Li // current block.
3020*67e74705SXin Li if (badCFG)
3021*67e74705SXin Li return nullptr;
3022*67e74705SXin Li
3023*67e74705SXin Li // Now create a new block that ends with the continue statement.
3024*67e74705SXin Li Block = createBlock(false);
3025*67e74705SXin Li Block->setTerminator(C);
3026*67e74705SXin Li
3027*67e74705SXin Li // If there is no target for the continue, then we are looking at an
3028*67e74705SXin Li // incomplete AST. This means the CFG cannot be constructed.
3029*67e74705SXin Li if (ContinueJumpTarget.block) {
3030*67e74705SXin Li addAutomaticObjDtors(ScopePos, ContinueJumpTarget.scopePosition, C);
3031*67e74705SXin Li addSuccessor(Block, ContinueJumpTarget.block);
3032*67e74705SXin Li } else
3033*67e74705SXin Li badCFG = true;
3034*67e74705SXin Li
3035*67e74705SXin Li return Block;
3036*67e74705SXin Li }
3037*67e74705SXin Li
VisitUnaryExprOrTypeTraitExpr(UnaryExprOrTypeTraitExpr * E,AddStmtChoice asc)3038*67e74705SXin Li CFGBlock *CFGBuilder::VisitUnaryExprOrTypeTraitExpr(UnaryExprOrTypeTraitExpr *E,
3039*67e74705SXin Li AddStmtChoice asc) {
3040*67e74705SXin Li
3041*67e74705SXin Li if (asc.alwaysAdd(*this, E)) {
3042*67e74705SXin Li autoCreateBlock();
3043*67e74705SXin Li appendStmt(Block, E);
3044*67e74705SXin Li }
3045*67e74705SXin Li
3046*67e74705SXin Li // VLA types have expressions that must be evaluated.
3047*67e74705SXin Li CFGBlock *lastBlock = Block;
3048*67e74705SXin Li
3049*67e74705SXin Li if (E->isArgumentType()) {
3050*67e74705SXin Li for (const VariableArrayType *VA =FindVA(E->getArgumentType().getTypePtr());
3051*67e74705SXin Li VA != nullptr; VA = FindVA(VA->getElementType().getTypePtr()))
3052*67e74705SXin Li lastBlock = addStmt(VA->getSizeExpr());
3053*67e74705SXin Li }
3054*67e74705SXin Li return lastBlock;
3055*67e74705SXin Li }
3056*67e74705SXin Li
3057*67e74705SXin Li /// VisitStmtExpr - Utility method to handle (nested) statement
3058*67e74705SXin Li /// expressions (a GCC extension).
VisitStmtExpr(StmtExpr * SE,AddStmtChoice asc)3059*67e74705SXin Li CFGBlock *CFGBuilder::VisitStmtExpr(StmtExpr *SE, AddStmtChoice asc) {
3060*67e74705SXin Li if (asc.alwaysAdd(*this, SE)) {
3061*67e74705SXin Li autoCreateBlock();
3062*67e74705SXin Li appendStmt(Block, SE);
3063*67e74705SXin Li }
3064*67e74705SXin Li return VisitCompoundStmt(SE->getSubStmt());
3065*67e74705SXin Li }
3066*67e74705SXin Li
VisitSwitchStmt(SwitchStmt * Terminator)3067*67e74705SXin Li CFGBlock *CFGBuilder::VisitSwitchStmt(SwitchStmt *Terminator) {
3068*67e74705SXin Li // "switch" is a control-flow statement. Thus we stop processing the current
3069*67e74705SXin Li // block.
3070*67e74705SXin Li CFGBlock *SwitchSuccessor = nullptr;
3071*67e74705SXin Li
3072*67e74705SXin Li // Save local scope position because in case of condition variable ScopePos
3073*67e74705SXin Li // won't be restored when traversing AST.
3074*67e74705SXin Li SaveAndRestore<LocalScope::const_iterator> save_scope_pos(ScopePos);
3075*67e74705SXin Li
3076*67e74705SXin Li // Create local scope for C++17 switch init-stmt if one exists.
3077*67e74705SXin Li if (Stmt *Init = Terminator->getInit()) {
3078*67e74705SXin Li LocalScope::const_iterator BeginScopePos = ScopePos;
3079*67e74705SXin Li addLocalScopeForStmt(Init);
3080*67e74705SXin Li addAutomaticObjDtors(ScopePos, BeginScopePos, Terminator);
3081*67e74705SXin Li }
3082*67e74705SXin Li
3083*67e74705SXin Li // Create local scope for possible condition variable.
3084*67e74705SXin Li // Store scope position. Add implicit destructor.
3085*67e74705SXin Li if (VarDecl *VD = Terminator->getConditionVariable()) {
3086*67e74705SXin Li LocalScope::const_iterator SwitchBeginScopePos = ScopePos;
3087*67e74705SXin Li addLocalScopeForVarDecl(VD);
3088*67e74705SXin Li addAutomaticObjDtors(ScopePos, SwitchBeginScopePos, Terminator);
3089*67e74705SXin Li }
3090*67e74705SXin Li
3091*67e74705SXin Li if (Block) {
3092*67e74705SXin Li if (badCFG)
3093*67e74705SXin Li return nullptr;
3094*67e74705SXin Li SwitchSuccessor = Block;
3095*67e74705SXin Li } else SwitchSuccessor = Succ;
3096*67e74705SXin Li
3097*67e74705SXin Li // Save the current "switch" context.
3098*67e74705SXin Li SaveAndRestore<CFGBlock*> save_switch(SwitchTerminatedBlock),
3099*67e74705SXin Li save_default(DefaultCaseBlock);
3100*67e74705SXin Li SaveAndRestore<JumpTarget> save_break(BreakJumpTarget);
3101*67e74705SXin Li
3102*67e74705SXin Li // Set the "default" case to be the block after the switch statement. If the
3103*67e74705SXin Li // switch statement contains a "default:", this value will be overwritten with
3104*67e74705SXin Li // the block for that code.
3105*67e74705SXin Li DefaultCaseBlock = SwitchSuccessor;
3106*67e74705SXin Li
3107*67e74705SXin Li // Create a new block that will contain the switch statement.
3108*67e74705SXin Li SwitchTerminatedBlock = createBlock(false);
3109*67e74705SXin Li
3110*67e74705SXin Li // Now process the switch body. The code after the switch is the implicit
3111*67e74705SXin Li // successor.
3112*67e74705SXin Li Succ = SwitchSuccessor;
3113*67e74705SXin Li BreakJumpTarget = JumpTarget(SwitchSuccessor, ScopePos);
3114*67e74705SXin Li
3115*67e74705SXin Li // When visiting the body, the case statements should automatically get linked
3116*67e74705SXin Li // up to the switch. We also don't keep a pointer to the body, since all
3117*67e74705SXin Li // control-flow from the switch goes to case/default statements.
3118*67e74705SXin Li assert(Terminator->getBody() && "switch must contain a non-NULL body");
3119*67e74705SXin Li Block = nullptr;
3120*67e74705SXin Li
3121*67e74705SXin Li // For pruning unreachable case statements, save the current state
3122*67e74705SXin Li // for tracking the condition value.
3123*67e74705SXin Li SaveAndRestore<bool> save_switchExclusivelyCovered(switchExclusivelyCovered,
3124*67e74705SXin Li false);
3125*67e74705SXin Li
3126*67e74705SXin Li // Determine if the switch condition can be explicitly evaluated.
3127*67e74705SXin Li assert(Terminator->getCond() && "switch condition must be non-NULL");
3128*67e74705SXin Li Expr::EvalResult result;
3129*67e74705SXin Li bool b = tryEvaluate(Terminator->getCond(), result);
3130*67e74705SXin Li SaveAndRestore<Expr::EvalResult*> save_switchCond(switchCond,
3131*67e74705SXin Li b ? &result : nullptr);
3132*67e74705SXin Li
3133*67e74705SXin Li // If body is not a compound statement create implicit scope
3134*67e74705SXin Li // and add destructors.
3135*67e74705SXin Li if (!isa<CompoundStmt>(Terminator->getBody()))
3136*67e74705SXin Li addLocalScopeAndDtors(Terminator->getBody());
3137*67e74705SXin Li
3138*67e74705SXin Li addStmt(Terminator->getBody());
3139*67e74705SXin Li if (Block) {
3140*67e74705SXin Li if (badCFG)
3141*67e74705SXin Li return nullptr;
3142*67e74705SXin Li }
3143*67e74705SXin Li
3144*67e74705SXin Li // If we have no "default:" case, the default transition is to the code
3145*67e74705SXin Li // following the switch body. Moreover, take into account if all the
3146*67e74705SXin Li // cases of a switch are covered (e.g., switching on an enum value).
3147*67e74705SXin Li //
3148*67e74705SXin Li // Note: We add a successor to a switch that is considered covered yet has no
3149*67e74705SXin Li // case statements if the enumeration has no enumerators.
3150*67e74705SXin Li bool SwitchAlwaysHasSuccessor = false;
3151*67e74705SXin Li SwitchAlwaysHasSuccessor |= switchExclusivelyCovered;
3152*67e74705SXin Li SwitchAlwaysHasSuccessor |= Terminator->isAllEnumCasesCovered() &&
3153*67e74705SXin Li Terminator->getSwitchCaseList();
3154*67e74705SXin Li addSuccessor(SwitchTerminatedBlock, DefaultCaseBlock,
3155*67e74705SXin Li !SwitchAlwaysHasSuccessor);
3156*67e74705SXin Li
3157*67e74705SXin Li // Add the terminator and condition in the switch block.
3158*67e74705SXin Li SwitchTerminatedBlock->setTerminator(Terminator);
3159*67e74705SXin Li Block = SwitchTerminatedBlock;
3160*67e74705SXin Li CFGBlock *LastBlock = addStmt(Terminator->getCond());
3161*67e74705SXin Li
3162*67e74705SXin Li // If the SwitchStmt contains a condition variable, add both the
3163*67e74705SXin Li // SwitchStmt and the condition variable initialization to the CFG.
3164*67e74705SXin Li if (VarDecl *VD = Terminator->getConditionVariable()) {
3165*67e74705SXin Li if (Expr *Init = VD->getInit()) {
3166*67e74705SXin Li autoCreateBlock();
3167*67e74705SXin Li appendStmt(Block, Terminator->getConditionVariableDeclStmt());
3168*67e74705SXin Li LastBlock = addStmt(Init);
3169*67e74705SXin Li }
3170*67e74705SXin Li }
3171*67e74705SXin Li
3172*67e74705SXin Li // Finally, if the SwitchStmt contains a C++17 init-stmt, add it to the CFG.
3173*67e74705SXin Li if (Stmt *Init = Terminator->getInit()) {
3174*67e74705SXin Li autoCreateBlock();
3175*67e74705SXin Li LastBlock = addStmt(Init);
3176*67e74705SXin Li }
3177*67e74705SXin Li
3178*67e74705SXin Li return LastBlock;
3179*67e74705SXin Li }
3180*67e74705SXin Li
shouldAddCase(bool & switchExclusivelyCovered,const Expr::EvalResult * switchCond,const CaseStmt * CS,ASTContext & Ctx)3181*67e74705SXin Li static bool shouldAddCase(bool &switchExclusivelyCovered,
3182*67e74705SXin Li const Expr::EvalResult *switchCond,
3183*67e74705SXin Li const CaseStmt *CS,
3184*67e74705SXin Li ASTContext &Ctx) {
3185*67e74705SXin Li if (!switchCond)
3186*67e74705SXin Li return true;
3187*67e74705SXin Li
3188*67e74705SXin Li bool addCase = false;
3189*67e74705SXin Li
3190*67e74705SXin Li if (!switchExclusivelyCovered) {
3191*67e74705SXin Li if (switchCond->Val.isInt()) {
3192*67e74705SXin Li // Evaluate the LHS of the case value.
3193*67e74705SXin Li const llvm::APSInt &lhsInt = CS->getLHS()->EvaluateKnownConstInt(Ctx);
3194*67e74705SXin Li const llvm::APSInt &condInt = switchCond->Val.getInt();
3195*67e74705SXin Li
3196*67e74705SXin Li if (condInt == lhsInt) {
3197*67e74705SXin Li addCase = true;
3198*67e74705SXin Li switchExclusivelyCovered = true;
3199*67e74705SXin Li }
3200*67e74705SXin Li else if (condInt > lhsInt) {
3201*67e74705SXin Li if (const Expr *RHS = CS->getRHS()) {
3202*67e74705SXin Li // Evaluate the RHS of the case value.
3203*67e74705SXin Li const llvm::APSInt &V2 = RHS->EvaluateKnownConstInt(Ctx);
3204*67e74705SXin Li if (V2 >= condInt) {
3205*67e74705SXin Li addCase = true;
3206*67e74705SXin Li switchExclusivelyCovered = true;
3207*67e74705SXin Li }
3208*67e74705SXin Li }
3209*67e74705SXin Li }
3210*67e74705SXin Li }
3211*67e74705SXin Li else
3212*67e74705SXin Li addCase = true;
3213*67e74705SXin Li }
3214*67e74705SXin Li return addCase;
3215*67e74705SXin Li }
3216*67e74705SXin Li
VisitCaseStmt(CaseStmt * CS)3217*67e74705SXin Li CFGBlock *CFGBuilder::VisitCaseStmt(CaseStmt *CS) {
3218*67e74705SXin Li // CaseStmts are essentially labels, so they are the first statement in a
3219*67e74705SXin Li // block.
3220*67e74705SXin Li CFGBlock *TopBlock = nullptr, *LastBlock = nullptr;
3221*67e74705SXin Li
3222*67e74705SXin Li if (Stmt *Sub = CS->getSubStmt()) {
3223*67e74705SXin Li // For deeply nested chains of CaseStmts, instead of doing a recursion
3224*67e74705SXin Li // (which can blow out the stack), manually unroll and create blocks
3225*67e74705SXin Li // along the way.
3226*67e74705SXin Li while (isa<CaseStmt>(Sub)) {
3227*67e74705SXin Li CFGBlock *currentBlock = createBlock(false);
3228*67e74705SXin Li currentBlock->setLabel(CS);
3229*67e74705SXin Li
3230*67e74705SXin Li if (TopBlock)
3231*67e74705SXin Li addSuccessor(LastBlock, currentBlock);
3232*67e74705SXin Li else
3233*67e74705SXin Li TopBlock = currentBlock;
3234*67e74705SXin Li
3235*67e74705SXin Li addSuccessor(SwitchTerminatedBlock,
3236*67e74705SXin Li shouldAddCase(switchExclusivelyCovered, switchCond,
3237*67e74705SXin Li CS, *Context)
3238*67e74705SXin Li ? currentBlock : nullptr);
3239*67e74705SXin Li
3240*67e74705SXin Li LastBlock = currentBlock;
3241*67e74705SXin Li CS = cast<CaseStmt>(Sub);
3242*67e74705SXin Li Sub = CS->getSubStmt();
3243*67e74705SXin Li }
3244*67e74705SXin Li
3245*67e74705SXin Li addStmt(Sub);
3246*67e74705SXin Li }
3247*67e74705SXin Li
3248*67e74705SXin Li CFGBlock *CaseBlock = Block;
3249*67e74705SXin Li if (!CaseBlock)
3250*67e74705SXin Li CaseBlock = createBlock();
3251*67e74705SXin Li
3252*67e74705SXin Li // Cases statements partition blocks, so this is the top of the basic block we
3253*67e74705SXin Li // were processing (the "case XXX:" is the label).
3254*67e74705SXin Li CaseBlock->setLabel(CS);
3255*67e74705SXin Li
3256*67e74705SXin Li if (badCFG)
3257*67e74705SXin Li return nullptr;
3258*67e74705SXin Li
3259*67e74705SXin Li // Add this block to the list of successors for the block with the switch
3260*67e74705SXin Li // statement.
3261*67e74705SXin Li assert(SwitchTerminatedBlock);
3262*67e74705SXin Li addSuccessor(SwitchTerminatedBlock, CaseBlock,
3263*67e74705SXin Li shouldAddCase(switchExclusivelyCovered, switchCond,
3264*67e74705SXin Li CS, *Context));
3265*67e74705SXin Li
3266*67e74705SXin Li // We set Block to NULL to allow lazy creation of a new block (if necessary)
3267*67e74705SXin Li Block = nullptr;
3268*67e74705SXin Li
3269*67e74705SXin Li if (TopBlock) {
3270*67e74705SXin Li addSuccessor(LastBlock, CaseBlock);
3271*67e74705SXin Li Succ = TopBlock;
3272*67e74705SXin Li } else {
3273*67e74705SXin Li // This block is now the implicit successor of other blocks.
3274*67e74705SXin Li Succ = CaseBlock;
3275*67e74705SXin Li }
3276*67e74705SXin Li
3277*67e74705SXin Li return Succ;
3278*67e74705SXin Li }
3279*67e74705SXin Li
VisitDefaultStmt(DefaultStmt * Terminator)3280*67e74705SXin Li CFGBlock *CFGBuilder::VisitDefaultStmt(DefaultStmt *Terminator) {
3281*67e74705SXin Li if (Terminator->getSubStmt())
3282*67e74705SXin Li addStmt(Terminator->getSubStmt());
3283*67e74705SXin Li
3284*67e74705SXin Li DefaultCaseBlock = Block;
3285*67e74705SXin Li
3286*67e74705SXin Li if (!DefaultCaseBlock)
3287*67e74705SXin Li DefaultCaseBlock = createBlock();
3288*67e74705SXin Li
3289*67e74705SXin Li // Default statements partition blocks, so this is the top of the basic block
3290*67e74705SXin Li // we were processing (the "default:" is the label).
3291*67e74705SXin Li DefaultCaseBlock->setLabel(Terminator);
3292*67e74705SXin Li
3293*67e74705SXin Li if (badCFG)
3294*67e74705SXin Li return nullptr;
3295*67e74705SXin Li
3296*67e74705SXin Li // Unlike case statements, we don't add the default block to the successors
3297*67e74705SXin Li // for the switch statement immediately. This is done when we finish
3298*67e74705SXin Li // processing the switch statement. This allows for the default case
3299*67e74705SXin Li // (including a fall-through to the code after the switch statement) to always
3300*67e74705SXin Li // be the last successor of a switch-terminated block.
3301*67e74705SXin Li
3302*67e74705SXin Li // We set Block to NULL to allow lazy creation of a new block (if necessary)
3303*67e74705SXin Li Block = nullptr;
3304*67e74705SXin Li
3305*67e74705SXin Li // This block is now the implicit successor of other blocks.
3306*67e74705SXin Li Succ = DefaultCaseBlock;
3307*67e74705SXin Li
3308*67e74705SXin Li return DefaultCaseBlock;
3309*67e74705SXin Li }
3310*67e74705SXin Li
VisitCXXTryStmt(CXXTryStmt * Terminator)3311*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXTryStmt(CXXTryStmt *Terminator) {
3312*67e74705SXin Li // "try"/"catch" is a control-flow statement. Thus we stop processing the
3313*67e74705SXin Li // current block.
3314*67e74705SXin Li CFGBlock *TrySuccessor = nullptr;
3315*67e74705SXin Li
3316*67e74705SXin Li if (Block) {
3317*67e74705SXin Li if (badCFG)
3318*67e74705SXin Li return nullptr;
3319*67e74705SXin Li TrySuccessor = Block;
3320*67e74705SXin Li } else TrySuccessor = Succ;
3321*67e74705SXin Li
3322*67e74705SXin Li CFGBlock *PrevTryTerminatedBlock = TryTerminatedBlock;
3323*67e74705SXin Li
3324*67e74705SXin Li // Create a new block that will contain the try statement.
3325*67e74705SXin Li CFGBlock *NewTryTerminatedBlock = createBlock(false);
3326*67e74705SXin Li // Add the terminator in the try block.
3327*67e74705SXin Li NewTryTerminatedBlock->setTerminator(Terminator);
3328*67e74705SXin Li
3329*67e74705SXin Li bool HasCatchAll = false;
3330*67e74705SXin Li for (unsigned h = 0; h <Terminator->getNumHandlers(); ++h) {
3331*67e74705SXin Li // The code after the try is the implicit successor.
3332*67e74705SXin Li Succ = TrySuccessor;
3333*67e74705SXin Li CXXCatchStmt *CS = Terminator->getHandler(h);
3334*67e74705SXin Li if (CS->getExceptionDecl() == nullptr) {
3335*67e74705SXin Li HasCatchAll = true;
3336*67e74705SXin Li }
3337*67e74705SXin Li Block = nullptr;
3338*67e74705SXin Li CFGBlock *CatchBlock = VisitCXXCatchStmt(CS);
3339*67e74705SXin Li if (!CatchBlock)
3340*67e74705SXin Li return nullptr;
3341*67e74705SXin Li // Add this block to the list of successors for the block with the try
3342*67e74705SXin Li // statement.
3343*67e74705SXin Li addSuccessor(NewTryTerminatedBlock, CatchBlock);
3344*67e74705SXin Li }
3345*67e74705SXin Li if (!HasCatchAll) {
3346*67e74705SXin Li if (PrevTryTerminatedBlock)
3347*67e74705SXin Li addSuccessor(NewTryTerminatedBlock, PrevTryTerminatedBlock);
3348*67e74705SXin Li else
3349*67e74705SXin Li addSuccessor(NewTryTerminatedBlock, &cfg->getExit());
3350*67e74705SXin Li }
3351*67e74705SXin Li
3352*67e74705SXin Li // The code after the try is the implicit successor.
3353*67e74705SXin Li Succ = TrySuccessor;
3354*67e74705SXin Li
3355*67e74705SXin Li // Save the current "try" context.
3356*67e74705SXin Li SaveAndRestore<CFGBlock*> save_try(TryTerminatedBlock, NewTryTerminatedBlock);
3357*67e74705SXin Li cfg->addTryDispatchBlock(TryTerminatedBlock);
3358*67e74705SXin Li
3359*67e74705SXin Li assert(Terminator->getTryBlock() && "try must contain a non-NULL body");
3360*67e74705SXin Li Block = nullptr;
3361*67e74705SXin Li return addStmt(Terminator->getTryBlock());
3362*67e74705SXin Li }
3363*67e74705SXin Li
VisitCXXCatchStmt(CXXCatchStmt * CS)3364*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXCatchStmt(CXXCatchStmt *CS) {
3365*67e74705SXin Li // CXXCatchStmt are treated like labels, so they are the first statement in a
3366*67e74705SXin Li // block.
3367*67e74705SXin Li
3368*67e74705SXin Li // Save local scope position because in case of exception variable ScopePos
3369*67e74705SXin Li // won't be restored when traversing AST.
3370*67e74705SXin Li SaveAndRestore<LocalScope::const_iterator> save_scope_pos(ScopePos);
3371*67e74705SXin Li
3372*67e74705SXin Li // Create local scope for possible exception variable.
3373*67e74705SXin Li // Store scope position. Add implicit destructor.
3374*67e74705SXin Li if (VarDecl *VD = CS->getExceptionDecl()) {
3375*67e74705SXin Li LocalScope::const_iterator BeginScopePos = ScopePos;
3376*67e74705SXin Li addLocalScopeForVarDecl(VD);
3377*67e74705SXin Li addAutomaticObjDtors(ScopePos, BeginScopePos, CS);
3378*67e74705SXin Li }
3379*67e74705SXin Li
3380*67e74705SXin Li if (CS->getHandlerBlock())
3381*67e74705SXin Li addStmt(CS->getHandlerBlock());
3382*67e74705SXin Li
3383*67e74705SXin Li CFGBlock *CatchBlock = Block;
3384*67e74705SXin Li if (!CatchBlock)
3385*67e74705SXin Li CatchBlock = createBlock();
3386*67e74705SXin Li
3387*67e74705SXin Li // CXXCatchStmt is more than just a label. They have semantic meaning
3388*67e74705SXin Li // as well, as they implicitly "initialize" the catch variable. Add
3389*67e74705SXin Li // it to the CFG as a CFGElement so that the control-flow of these
3390*67e74705SXin Li // semantics gets captured.
3391*67e74705SXin Li appendStmt(CatchBlock, CS);
3392*67e74705SXin Li
3393*67e74705SXin Li // Also add the CXXCatchStmt as a label, to mirror handling of regular
3394*67e74705SXin Li // labels.
3395*67e74705SXin Li CatchBlock->setLabel(CS);
3396*67e74705SXin Li
3397*67e74705SXin Li // Bail out if the CFG is bad.
3398*67e74705SXin Li if (badCFG)
3399*67e74705SXin Li return nullptr;
3400*67e74705SXin Li
3401*67e74705SXin Li // We set Block to NULL to allow lazy creation of a new block (if necessary)
3402*67e74705SXin Li Block = nullptr;
3403*67e74705SXin Li
3404*67e74705SXin Li return CatchBlock;
3405*67e74705SXin Li }
3406*67e74705SXin Li
VisitCXXForRangeStmt(CXXForRangeStmt * S)3407*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXForRangeStmt(CXXForRangeStmt *S) {
3408*67e74705SXin Li // C++0x for-range statements are specified as [stmt.ranged]:
3409*67e74705SXin Li //
3410*67e74705SXin Li // {
3411*67e74705SXin Li // auto && __range = range-init;
3412*67e74705SXin Li // for ( auto __begin = begin-expr,
3413*67e74705SXin Li // __end = end-expr;
3414*67e74705SXin Li // __begin != __end;
3415*67e74705SXin Li // ++__begin ) {
3416*67e74705SXin Li // for-range-declaration = *__begin;
3417*67e74705SXin Li // statement
3418*67e74705SXin Li // }
3419*67e74705SXin Li // }
3420*67e74705SXin Li
3421*67e74705SXin Li // Save local scope position before the addition of the implicit variables.
3422*67e74705SXin Li SaveAndRestore<LocalScope::const_iterator> save_scope_pos(ScopePos);
3423*67e74705SXin Li
3424*67e74705SXin Li // Create local scopes and destructors for range, begin and end variables.
3425*67e74705SXin Li if (Stmt *Range = S->getRangeStmt())
3426*67e74705SXin Li addLocalScopeForStmt(Range);
3427*67e74705SXin Li if (Stmt *Begin = S->getBeginStmt())
3428*67e74705SXin Li addLocalScopeForStmt(Begin);
3429*67e74705SXin Li if (Stmt *End = S->getEndStmt())
3430*67e74705SXin Li addLocalScopeForStmt(End);
3431*67e74705SXin Li addAutomaticObjDtors(ScopePos, save_scope_pos.get(), S);
3432*67e74705SXin Li
3433*67e74705SXin Li LocalScope::const_iterator ContinueScopePos = ScopePos;
3434*67e74705SXin Li
3435*67e74705SXin Li // "for" is a control-flow statement. Thus we stop processing the current
3436*67e74705SXin Li // block.
3437*67e74705SXin Li CFGBlock *LoopSuccessor = nullptr;
3438*67e74705SXin Li if (Block) {
3439*67e74705SXin Li if (badCFG)
3440*67e74705SXin Li return nullptr;
3441*67e74705SXin Li LoopSuccessor = Block;
3442*67e74705SXin Li } else
3443*67e74705SXin Li LoopSuccessor = Succ;
3444*67e74705SXin Li
3445*67e74705SXin Li // Save the current value for the break targets.
3446*67e74705SXin Li // All breaks should go to the code following the loop.
3447*67e74705SXin Li SaveAndRestore<JumpTarget> save_break(BreakJumpTarget);
3448*67e74705SXin Li BreakJumpTarget = JumpTarget(LoopSuccessor, ScopePos);
3449*67e74705SXin Li
3450*67e74705SXin Li // The block for the __begin != __end expression.
3451*67e74705SXin Li CFGBlock *ConditionBlock = createBlock(false);
3452*67e74705SXin Li ConditionBlock->setTerminator(S);
3453*67e74705SXin Li
3454*67e74705SXin Li // Now add the actual condition to the condition block.
3455*67e74705SXin Li if (Expr *C = S->getCond()) {
3456*67e74705SXin Li Block = ConditionBlock;
3457*67e74705SXin Li CFGBlock *BeginConditionBlock = addStmt(C);
3458*67e74705SXin Li if (badCFG)
3459*67e74705SXin Li return nullptr;
3460*67e74705SXin Li assert(BeginConditionBlock == ConditionBlock &&
3461*67e74705SXin Li "condition block in for-range was unexpectedly complex");
3462*67e74705SXin Li (void)BeginConditionBlock;
3463*67e74705SXin Li }
3464*67e74705SXin Li
3465*67e74705SXin Li // The condition block is the implicit successor for the loop body as well as
3466*67e74705SXin Li // any code above the loop.
3467*67e74705SXin Li Succ = ConditionBlock;
3468*67e74705SXin Li
3469*67e74705SXin Li // See if this is a known constant.
3470*67e74705SXin Li TryResult KnownVal(true);
3471*67e74705SXin Li
3472*67e74705SXin Li if (S->getCond())
3473*67e74705SXin Li KnownVal = tryEvaluateBool(S->getCond());
3474*67e74705SXin Li
3475*67e74705SXin Li // Now create the loop body.
3476*67e74705SXin Li {
3477*67e74705SXin Li assert(S->getBody());
3478*67e74705SXin Li
3479*67e74705SXin Li // Save the current values for Block, Succ, and continue targets.
3480*67e74705SXin Li SaveAndRestore<CFGBlock*> save_Block(Block), save_Succ(Succ);
3481*67e74705SXin Li SaveAndRestore<JumpTarget> save_continue(ContinueJumpTarget);
3482*67e74705SXin Li
3483*67e74705SXin Li // Generate increment code in its own basic block. This is the target of
3484*67e74705SXin Li // continue statements.
3485*67e74705SXin Li Block = nullptr;
3486*67e74705SXin Li Succ = addStmt(S->getInc());
3487*67e74705SXin Li if (badCFG)
3488*67e74705SXin Li return nullptr;
3489*67e74705SXin Li ContinueJumpTarget = JumpTarget(Succ, ContinueScopePos);
3490*67e74705SXin Li
3491*67e74705SXin Li // The starting block for the loop increment is the block that should
3492*67e74705SXin Li // represent the 'loop target' for looping back to the start of the loop.
3493*67e74705SXin Li ContinueJumpTarget.block->setLoopTarget(S);
3494*67e74705SXin Li
3495*67e74705SXin Li // Finish up the increment block and prepare to start the loop body.
3496*67e74705SXin Li assert(Block);
3497*67e74705SXin Li if (badCFG)
3498*67e74705SXin Li return nullptr;
3499*67e74705SXin Li Block = nullptr;
3500*67e74705SXin Li
3501*67e74705SXin Li // Add implicit scope and dtors for loop variable.
3502*67e74705SXin Li addLocalScopeAndDtors(S->getLoopVarStmt());
3503*67e74705SXin Li
3504*67e74705SXin Li // Populate a new block to contain the loop body and loop variable.
3505*67e74705SXin Li addStmt(S->getBody());
3506*67e74705SXin Li if (badCFG)
3507*67e74705SXin Li return nullptr;
3508*67e74705SXin Li CFGBlock *LoopVarStmtBlock = addStmt(S->getLoopVarStmt());
3509*67e74705SXin Li if (badCFG)
3510*67e74705SXin Li return nullptr;
3511*67e74705SXin Li
3512*67e74705SXin Li // This new body block is a successor to our condition block.
3513*67e74705SXin Li addSuccessor(ConditionBlock,
3514*67e74705SXin Li KnownVal.isFalse() ? nullptr : LoopVarStmtBlock);
3515*67e74705SXin Li }
3516*67e74705SXin Li
3517*67e74705SXin Li // Link up the condition block with the code that follows the loop (the
3518*67e74705SXin Li // false branch).
3519*67e74705SXin Li addSuccessor(ConditionBlock, KnownVal.isTrue() ? nullptr : LoopSuccessor);
3520*67e74705SXin Li
3521*67e74705SXin Li // Add the initialization statements.
3522*67e74705SXin Li Block = createBlock();
3523*67e74705SXin Li addStmt(S->getBeginStmt());
3524*67e74705SXin Li addStmt(S->getEndStmt());
3525*67e74705SXin Li return addStmt(S->getRangeStmt());
3526*67e74705SXin Li }
3527*67e74705SXin Li
VisitExprWithCleanups(ExprWithCleanups * E,AddStmtChoice asc)3528*67e74705SXin Li CFGBlock *CFGBuilder::VisitExprWithCleanups(ExprWithCleanups *E,
3529*67e74705SXin Li AddStmtChoice asc) {
3530*67e74705SXin Li if (BuildOpts.AddTemporaryDtors) {
3531*67e74705SXin Li // If adding implicit destructors visit the full expression for adding
3532*67e74705SXin Li // destructors of temporaries.
3533*67e74705SXin Li TempDtorContext Context;
3534*67e74705SXin Li VisitForTemporaryDtors(E->getSubExpr(), false, Context);
3535*67e74705SXin Li
3536*67e74705SXin Li // Full expression has to be added as CFGStmt so it will be sequenced
3537*67e74705SXin Li // before destructors of it's temporaries.
3538*67e74705SXin Li asc = asc.withAlwaysAdd(true);
3539*67e74705SXin Li }
3540*67e74705SXin Li return Visit(E->getSubExpr(), asc);
3541*67e74705SXin Li }
3542*67e74705SXin Li
VisitCXXBindTemporaryExpr(CXXBindTemporaryExpr * E,AddStmtChoice asc)3543*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXBindTemporaryExpr(CXXBindTemporaryExpr *E,
3544*67e74705SXin Li AddStmtChoice asc) {
3545*67e74705SXin Li if (asc.alwaysAdd(*this, E)) {
3546*67e74705SXin Li autoCreateBlock();
3547*67e74705SXin Li appendStmt(Block, E);
3548*67e74705SXin Li
3549*67e74705SXin Li // We do not want to propagate the AlwaysAdd property.
3550*67e74705SXin Li asc = asc.withAlwaysAdd(false);
3551*67e74705SXin Li }
3552*67e74705SXin Li return Visit(E->getSubExpr(), asc);
3553*67e74705SXin Li }
3554*67e74705SXin Li
VisitCXXConstructExpr(CXXConstructExpr * C,AddStmtChoice asc)3555*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXConstructExpr(CXXConstructExpr *C,
3556*67e74705SXin Li AddStmtChoice asc) {
3557*67e74705SXin Li autoCreateBlock();
3558*67e74705SXin Li appendStmt(Block, C);
3559*67e74705SXin Li
3560*67e74705SXin Li return VisitChildren(C);
3561*67e74705SXin Li }
3562*67e74705SXin Li
VisitCXXNewExpr(CXXNewExpr * NE,AddStmtChoice asc)3563*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXNewExpr(CXXNewExpr *NE,
3564*67e74705SXin Li AddStmtChoice asc) {
3565*67e74705SXin Li
3566*67e74705SXin Li autoCreateBlock();
3567*67e74705SXin Li appendStmt(Block, NE);
3568*67e74705SXin Li
3569*67e74705SXin Li if (NE->getInitializer())
3570*67e74705SXin Li Block = Visit(NE->getInitializer());
3571*67e74705SXin Li if (BuildOpts.AddCXXNewAllocator)
3572*67e74705SXin Li appendNewAllocator(Block, NE);
3573*67e74705SXin Li if (NE->isArray())
3574*67e74705SXin Li Block = Visit(NE->getArraySize());
3575*67e74705SXin Li for (CXXNewExpr::arg_iterator I = NE->placement_arg_begin(),
3576*67e74705SXin Li E = NE->placement_arg_end(); I != E; ++I)
3577*67e74705SXin Li Block = Visit(*I);
3578*67e74705SXin Li return Block;
3579*67e74705SXin Li }
3580*67e74705SXin Li
VisitCXXDeleteExpr(CXXDeleteExpr * DE,AddStmtChoice asc)3581*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXDeleteExpr(CXXDeleteExpr *DE,
3582*67e74705SXin Li AddStmtChoice asc) {
3583*67e74705SXin Li autoCreateBlock();
3584*67e74705SXin Li appendStmt(Block, DE);
3585*67e74705SXin Li QualType DTy = DE->getDestroyedType();
3586*67e74705SXin Li DTy = DTy.getNonReferenceType();
3587*67e74705SXin Li CXXRecordDecl *RD = Context->getBaseElementType(DTy)->getAsCXXRecordDecl();
3588*67e74705SXin Li if (RD) {
3589*67e74705SXin Li if (RD->isCompleteDefinition() && !RD->hasTrivialDestructor())
3590*67e74705SXin Li appendDeleteDtor(Block, RD, DE);
3591*67e74705SXin Li }
3592*67e74705SXin Li
3593*67e74705SXin Li return VisitChildren(DE);
3594*67e74705SXin Li }
3595*67e74705SXin Li
VisitCXXFunctionalCastExpr(CXXFunctionalCastExpr * E,AddStmtChoice asc)3596*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXFunctionalCastExpr(CXXFunctionalCastExpr *E,
3597*67e74705SXin Li AddStmtChoice asc) {
3598*67e74705SXin Li if (asc.alwaysAdd(*this, E)) {
3599*67e74705SXin Li autoCreateBlock();
3600*67e74705SXin Li appendStmt(Block, E);
3601*67e74705SXin Li // We do not want to propagate the AlwaysAdd property.
3602*67e74705SXin Li asc = asc.withAlwaysAdd(false);
3603*67e74705SXin Li }
3604*67e74705SXin Li return Visit(E->getSubExpr(), asc);
3605*67e74705SXin Li }
3606*67e74705SXin Li
VisitCXXTemporaryObjectExpr(CXXTemporaryObjectExpr * C,AddStmtChoice asc)3607*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXTemporaryObjectExpr(CXXTemporaryObjectExpr *C,
3608*67e74705SXin Li AddStmtChoice asc) {
3609*67e74705SXin Li autoCreateBlock();
3610*67e74705SXin Li appendStmt(Block, C);
3611*67e74705SXin Li return VisitChildren(C);
3612*67e74705SXin Li }
3613*67e74705SXin Li
VisitImplicitCastExpr(ImplicitCastExpr * E,AddStmtChoice asc)3614*67e74705SXin Li CFGBlock *CFGBuilder::VisitImplicitCastExpr(ImplicitCastExpr *E,
3615*67e74705SXin Li AddStmtChoice asc) {
3616*67e74705SXin Li if (asc.alwaysAdd(*this, E)) {
3617*67e74705SXin Li autoCreateBlock();
3618*67e74705SXin Li appendStmt(Block, E);
3619*67e74705SXin Li }
3620*67e74705SXin Li return Visit(E->getSubExpr(), AddStmtChoice());
3621*67e74705SXin Li }
3622*67e74705SXin Li
VisitIndirectGotoStmt(IndirectGotoStmt * I)3623*67e74705SXin Li CFGBlock *CFGBuilder::VisitIndirectGotoStmt(IndirectGotoStmt *I) {
3624*67e74705SXin Li // Lazily create the indirect-goto dispatch block if there isn't one already.
3625*67e74705SXin Li CFGBlock *IBlock = cfg->getIndirectGotoBlock();
3626*67e74705SXin Li
3627*67e74705SXin Li if (!IBlock) {
3628*67e74705SXin Li IBlock = createBlock(false);
3629*67e74705SXin Li cfg->setIndirectGotoBlock(IBlock);
3630*67e74705SXin Li }
3631*67e74705SXin Li
3632*67e74705SXin Li // IndirectGoto is a control-flow statement. Thus we stop processing the
3633*67e74705SXin Li // current block and create a new one.
3634*67e74705SXin Li if (badCFG)
3635*67e74705SXin Li return nullptr;
3636*67e74705SXin Li
3637*67e74705SXin Li Block = createBlock(false);
3638*67e74705SXin Li Block->setTerminator(I);
3639*67e74705SXin Li addSuccessor(Block, IBlock);
3640*67e74705SXin Li return addStmt(I->getTarget());
3641*67e74705SXin Li }
3642*67e74705SXin Li
VisitForTemporaryDtors(Stmt * E,bool BindToTemporary,TempDtorContext & Context)3643*67e74705SXin Li CFGBlock *CFGBuilder::VisitForTemporaryDtors(Stmt *E, bool BindToTemporary,
3644*67e74705SXin Li TempDtorContext &Context) {
3645*67e74705SXin Li assert(BuildOpts.AddImplicitDtors && BuildOpts.AddTemporaryDtors);
3646*67e74705SXin Li
3647*67e74705SXin Li tryAgain:
3648*67e74705SXin Li if (!E) {
3649*67e74705SXin Li badCFG = true;
3650*67e74705SXin Li return nullptr;
3651*67e74705SXin Li }
3652*67e74705SXin Li switch (E->getStmtClass()) {
3653*67e74705SXin Li default:
3654*67e74705SXin Li return VisitChildrenForTemporaryDtors(E, Context);
3655*67e74705SXin Li
3656*67e74705SXin Li case Stmt::BinaryOperatorClass:
3657*67e74705SXin Li return VisitBinaryOperatorForTemporaryDtors(cast<BinaryOperator>(E),
3658*67e74705SXin Li Context);
3659*67e74705SXin Li
3660*67e74705SXin Li case Stmt::CXXBindTemporaryExprClass:
3661*67e74705SXin Li return VisitCXXBindTemporaryExprForTemporaryDtors(
3662*67e74705SXin Li cast<CXXBindTemporaryExpr>(E), BindToTemporary, Context);
3663*67e74705SXin Li
3664*67e74705SXin Li case Stmt::BinaryConditionalOperatorClass:
3665*67e74705SXin Li case Stmt::ConditionalOperatorClass:
3666*67e74705SXin Li return VisitConditionalOperatorForTemporaryDtors(
3667*67e74705SXin Li cast<AbstractConditionalOperator>(E), BindToTemporary, Context);
3668*67e74705SXin Li
3669*67e74705SXin Li case Stmt::ImplicitCastExprClass:
3670*67e74705SXin Li // For implicit cast we want BindToTemporary to be passed further.
3671*67e74705SXin Li E = cast<CastExpr>(E)->getSubExpr();
3672*67e74705SXin Li goto tryAgain;
3673*67e74705SXin Li
3674*67e74705SXin Li case Stmt::CXXFunctionalCastExprClass:
3675*67e74705SXin Li // For functional cast we want BindToTemporary to be passed further.
3676*67e74705SXin Li E = cast<CXXFunctionalCastExpr>(E)->getSubExpr();
3677*67e74705SXin Li goto tryAgain;
3678*67e74705SXin Li
3679*67e74705SXin Li case Stmt::ParenExprClass:
3680*67e74705SXin Li E = cast<ParenExpr>(E)->getSubExpr();
3681*67e74705SXin Li goto tryAgain;
3682*67e74705SXin Li
3683*67e74705SXin Li case Stmt::MaterializeTemporaryExprClass: {
3684*67e74705SXin Li const MaterializeTemporaryExpr* MTE = cast<MaterializeTemporaryExpr>(E);
3685*67e74705SXin Li BindToTemporary = (MTE->getStorageDuration() != SD_FullExpression);
3686*67e74705SXin Li SmallVector<const Expr *, 2> CommaLHSs;
3687*67e74705SXin Li SmallVector<SubobjectAdjustment, 2> Adjustments;
3688*67e74705SXin Li // Find the expression whose lifetime needs to be extended.
3689*67e74705SXin Li E = const_cast<Expr *>(
3690*67e74705SXin Li cast<MaterializeTemporaryExpr>(E)
3691*67e74705SXin Li ->GetTemporaryExpr()
3692*67e74705SXin Li ->skipRValueSubobjectAdjustments(CommaLHSs, Adjustments));
3693*67e74705SXin Li // Visit the skipped comma operator left-hand sides for other temporaries.
3694*67e74705SXin Li for (const Expr *CommaLHS : CommaLHSs) {
3695*67e74705SXin Li VisitForTemporaryDtors(const_cast<Expr *>(CommaLHS),
3696*67e74705SXin Li /*BindToTemporary=*/false, Context);
3697*67e74705SXin Li }
3698*67e74705SXin Li goto tryAgain;
3699*67e74705SXin Li }
3700*67e74705SXin Li
3701*67e74705SXin Li case Stmt::BlockExprClass:
3702*67e74705SXin Li // Don't recurse into blocks; their subexpressions don't get evaluated
3703*67e74705SXin Li // here.
3704*67e74705SXin Li return Block;
3705*67e74705SXin Li
3706*67e74705SXin Li case Stmt::LambdaExprClass: {
3707*67e74705SXin Li // For lambda expressions, only recurse into the capture initializers,
3708*67e74705SXin Li // and not the body.
3709*67e74705SXin Li auto *LE = cast<LambdaExpr>(E);
3710*67e74705SXin Li CFGBlock *B = Block;
3711*67e74705SXin Li for (Expr *Init : LE->capture_inits()) {
3712*67e74705SXin Li if (CFGBlock *R = VisitForTemporaryDtors(
3713*67e74705SXin Li Init, /*BindToTemporary=*/false, Context))
3714*67e74705SXin Li B = R;
3715*67e74705SXin Li }
3716*67e74705SXin Li return B;
3717*67e74705SXin Li }
3718*67e74705SXin Li
3719*67e74705SXin Li case Stmt::CXXDefaultArgExprClass:
3720*67e74705SXin Li E = cast<CXXDefaultArgExpr>(E)->getExpr();
3721*67e74705SXin Li goto tryAgain;
3722*67e74705SXin Li
3723*67e74705SXin Li case Stmt::CXXDefaultInitExprClass:
3724*67e74705SXin Li E = cast<CXXDefaultInitExpr>(E)->getExpr();
3725*67e74705SXin Li goto tryAgain;
3726*67e74705SXin Li }
3727*67e74705SXin Li }
3728*67e74705SXin Li
VisitChildrenForTemporaryDtors(Stmt * E,TempDtorContext & Context)3729*67e74705SXin Li CFGBlock *CFGBuilder::VisitChildrenForTemporaryDtors(Stmt *E,
3730*67e74705SXin Li TempDtorContext &Context) {
3731*67e74705SXin Li if (isa<LambdaExpr>(E)) {
3732*67e74705SXin Li // Do not visit the children of lambdas; they have their own CFGs.
3733*67e74705SXin Li return Block;
3734*67e74705SXin Li }
3735*67e74705SXin Li
3736*67e74705SXin Li // When visiting children for destructors we want to visit them in reverse
3737*67e74705SXin Li // order that they will appear in the CFG. Because the CFG is built
3738*67e74705SXin Li // bottom-up, this means we visit them in their natural order, which
3739*67e74705SXin Li // reverses them in the CFG.
3740*67e74705SXin Li CFGBlock *B = Block;
3741*67e74705SXin Li for (Stmt *Child : E->children())
3742*67e74705SXin Li if (Child)
3743*67e74705SXin Li if (CFGBlock *R = VisitForTemporaryDtors(Child, false, Context))
3744*67e74705SXin Li B = R;
3745*67e74705SXin Li
3746*67e74705SXin Li return B;
3747*67e74705SXin Li }
3748*67e74705SXin Li
VisitBinaryOperatorForTemporaryDtors(BinaryOperator * E,TempDtorContext & Context)3749*67e74705SXin Li CFGBlock *CFGBuilder::VisitBinaryOperatorForTemporaryDtors(
3750*67e74705SXin Li BinaryOperator *E, TempDtorContext &Context) {
3751*67e74705SXin Li if (E->isLogicalOp()) {
3752*67e74705SXin Li VisitForTemporaryDtors(E->getLHS(), false, Context);
3753*67e74705SXin Li TryResult RHSExecuted = tryEvaluateBool(E->getLHS());
3754*67e74705SXin Li if (RHSExecuted.isKnown() && E->getOpcode() == BO_LOr)
3755*67e74705SXin Li RHSExecuted.negate();
3756*67e74705SXin Li
3757*67e74705SXin Li // We do not know at CFG-construction time whether the right-hand-side was
3758*67e74705SXin Li // executed, thus we add a branch node that depends on the temporary
3759*67e74705SXin Li // constructor call.
3760*67e74705SXin Li TempDtorContext RHSContext(
3761*67e74705SXin Li bothKnownTrue(Context.KnownExecuted, RHSExecuted));
3762*67e74705SXin Li VisitForTemporaryDtors(E->getRHS(), false, RHSContext);
3763*67e74705SXin Li InsertTempDtorDecisionBlock(RHSContext);
3764*67e74705SXin Li
3765*67e74705SXin Li return Block;
3766*67e74705SXin Li }
3767*67e74705SXin Li
3768*67e74705SXin Li if (E->isAssignmentOp()) {
3769*67e74705SXin Li // For assignment operator (=) LHS expression is visited
3770*67e74705SXin Li // before RHS expression. For destructors visit them in reverse order.
3771*67e74705SXin Li CFGBlock *RHSBlock = VisitForTemporaryDtors(E->getRHS(), false, Context);
3772*67e74705SXin Li CFGBlock *LHSBlock = VisitForTemporaryDtors(E->getLHS(), false, Context);
3773*67e74705SXin Li return LHSBlock ? LHSBlock : RHSBlock;
3774*67e74705SXin Li }
3775*67e74705SXin Li
3776*67e74705SXin Li // For any other binary operator RHS expression is visited before
3777*67e74705SXin Li // LHS expression (order of children). For destructors visit them in reverse
3778*67e74705SXin Li // order.
3779*67e74705SXin Li CFGBlock *LHSBlock = VisitForTemporaryDtors(E->getLHS(), false, Context);
3780*67e74705SXin Li CFGBlock *RHSBlock = VisitForTemporaryDtors(E->getRHS(), false, Context);
3781*67e74705SXin Li return RHSBlock ? RHSBlock : LHSBlock;
3782*67e74705SXin Li }
3783*67e74705SXin Li
VisitCXXBindTemporaryExprForTemporaryDtors(CXXBindTemporaryExpr * E,bool BindToTemporary,TempDtorContext & Context)3784*67e74705SXin Li CFGBlock *CFGBuilder::VisitCXXBindTemporaryExprForTemporaryDtors(
3785*67e74705SXin Li CXXBindTemporaryExpr *E, bool BindToTemporary, TempDtorContext &Context) {
3786*67e74705SXin Li // First add destructors for temporaries in subexpression.
3787*67e74705SXin Li CFGBlock *B = VisitForTemporaryDtors(E->getSubExpr(), false, Context);
3788*67e74705SXin Li if (!BindToTemporary) {
3789*67e74705SXin Li // If lifetime of temporary is not prolonged (by assigning to constant
3790*67e74705SXin Li // reference) add destructor for it.
3791*67e74705SXin Li
3792*67e74705SXin Li const CXXDestructorDecl *Dtor = E->getTemporary()->getDestructor();
3793*67e74705SXin Li
3794*67e74705SXin Li if (Dtor->getParent()->isAnyDestructorNoReturn()) {
3795*67e74705SXin Li // If the destructor is marked as a no-return destructor, we need to
3796*67e74705SXin Li // create a new block for the destructor which does not have as a
3797*67e74705SXin Li // successor anything built thus far. Control won't flow out of this
3798*67e74705SXin Li // block.
3799*67e74705SXin Li if (B) Succ = B;
3800*67e74705SXin Li Block = createNoReturnBlock();
3801*67e74705SXin Li } else if (Context.needsTempDtorBranch()) {
3802*67e74705SXin Li // If we need to introduce a branch, we add a new block that we will hook
3803*67e74705SXin Li // up to a decision block later.
3804*67e74705SXin Li if (B) Succ = B;
3805*67e74705SXin Li Block = createBlock();
3806*67e74705SXin Li } else {
3807*67e74705SXin Li autoCreateBlock();
3808*67e74705SXin Li }
3809*67e74705SXin Li if (Context.needsTempDtorBranch()) {
3810*67e74705SXin Li Context.setDecisionPoint(Succ, E);
3811*67e74705SXin Li }
3812*67e74705SXin Li appendTemporaryDtor(Block, E);
3813*67e74705SXin Li
3814*67e74705SXin Li B = Block;
3815*67e74705SXin Li }
3816*67e74705SXin Li return B;
3817*67e74705SXin Li }
3818*67e74705SXin Li
InsertTempDtorDecisionBlock(const TempDtorContext & Context,CFGBlock * FalseSucc)3819*67e74705SXin Li void CFGBuilder::InsertTempDtorDecisionBlock(const TempDtorContext &Context,
3820*67e74705SXin Li CFGBlock *FalseSucc) {
3821*67e74705SXin Li if (!Context.TerminatorExpr) {
3822*67e74705SXin Li // If no temporary was found, we do not need to insert a decision point.
3823*67e74705SXin Li return;
3824*67e74705SXin Li }
3825*67e74705SXin Li assert(Context.TerminatorExpr);
3826*67e74705SXin Li CFGBlock *Decision = createBlock(false);
3827*67e74705SXin Li Decision->setTerminator(CFGTerminator(Context.TerminatorExpr, true));
3828*67e74705SXin Li addSuccessor(Decision, Block, !Context.KnownExecuted.isFalse());
3829*67e74705SXin Li addSuccessor(Decision, FalseSucc ? FalseSucc : Context.Succ,
3830*67e74705SXin Li !Context.KnownExecuted.isTrue());
3831*67e74705SXin Li Block = Decision;
3832*67e74705SXin Li }
3833*67e74705SXin Li
VisitConditionalOperatorForTemporaryDtors(AbstractConditionalOperator * E,bool BindToTemporary,TempDtorContext & Context)3834*67e74705SXin Li CFGBlock *CFGBuilder::VisitConditionalOperatorForTemporaryDtors(
3835*67e74705SXin Li AbstractConditionalOperator *E, bool BindToTemporary,
3836*67e74705SXin Li TempDtorContext &Context) {
3837*67e74705SXin Li VisitForTemporaryDtors(E->getCond(), false, Context);
3838*67e74705SXin Li CFGBlock *ConditionBlock = Block;
3839*67e74705SXin Li CFGBlock *ConditionSucc = Succ;
3840*67e74705SXin Li TryResult ConditionVal = tryEvaluateBool(E->getCond());
3841*67e74705SXin Li TryResult NegatedVal = ConditionVal;
3842*67e74705SXin Li if (NegatedVal.isKnown()) NegatedVal.negate();
3843*67e74705SXin Li
3844*67e74705SXin Li TempDtorContext TrueContext(
3845*67e74705SXin Li bothKnownTrue(Context.KnownExecuted, ConditionVal));
3846*67e74705SXin Li VisitForTemporaryDtors(E->getTrueExpr(), BindToTemporary, TrueContext);
3847*67e74705SXin Li CFGBlock *TrueBlock = Block;
3848*67e74705SXin Li
3849*67e74705SXin Li Block = ConditionBlock;
3850*67e74705SXin Li Succ = ConditionSucc;
3851*67e74705SXin Li TempDtorContext FalseContext(
3852*67e74705SXin Li bothKnownTrue(Context.KnownExecuted, NegatedVal));
3853*67e74705SXin Li VisitForTemporaryDtors(E->getFalseExpr(), BindToTemporary, FalseContext);
3854*67e74705SXin Li
3855*67e74705SXin Li if (TrueContext.TerminatorExpr && FalseContext.TerminatorExpr) {
3856*67e74705SXin Li InsertTempDtorDecisionBlock(FalseContext, TrueBlock);
3857*67e74705SXin Li } else if (TrueContext.TerminatorExpr) {
3858*67e74705SXin Li Block = TrueBlock;
3859*67e74705SXin Li InsertTempDtorDecisionBlock(TrueContext);
3860*67e74705SXin Li } else {
3861*67e74705SXin Li InsertTempDtorDecisionBlock(FalseContext);
3862*67e74705SXin Li }
3863*67e74705SXin Li return Block;
3864*67e74705SXin Li }
3865*67e74705SXin Li
3866*67e74705SXin Li } // end anonymous namespace
3867*67e74705SXin Li
3868*67e74705SXin Li /// createBlock - Constructs and adds a new CFGBlock to the CFG. The block has
3869*67e74705SXin Li /// no successors or predecessors. If this is the first block created in the
3870*67e74705SXin Li /// CFG, it is automatically set to be the Entry and Exit of the CFG.
createBlock()3871*67e74705SXin Li CFGBlock *CFG::createBlock() {
3872*67e74705SXin Li bool first_block = begin() == end();
3873*67e74705SXin Li
3874*67e74705SXin Li // Create the block.
3875*67e74705SXin Li CFGBlock *Mem = getAllocator().Allocate<CFGBlock>();
3876*67e74705SXin Li new (Mem) CFGBlock(NumBlockIDs++, BlkBVC, this);
3877*67e74705SXin Li Blocks.push_back(Mem, BlkBVC);
3878*67e74705SXin Li
3879*67e74705SXin Li // If this is the first block, set it as the Entry and Exit.
3880*67e74705SXin Li if (first_block)
3881*67e74705SXin Li Entry = Exit = &back();
3882*67e74705SXin Li
3883*67e74705SXin Li // Return the block.
3884*67e74705SXin Li return &back();
3885*67e74705SXin Li }
3886*67e74705SXin Li
3887*67e74705SXin Li /// buildCFG - Constructs a CFG from an AST.
buildCFG(const Decl * D,Stmt * Statement,ASTContext * C,const BuildOptions & BO)3888*67e74705SXin Li std::unique_ptr<CFG> CFG::buildCFG(const Decl *D, Stmt *Statement,
3889*67e74705SXin Li ASTContext *C, const BuildOptions &BO) {
3890*67e74705SXin Li CFGBuilder Builder(C, BO);
3891*67e74705SXin Li return Builder.buildCFG(D, Statement);
3892*67e74705SXin Li }
3893*67e74705SXin Li
3894*67e74705SXin Li const CXXDestructorDecl *
getDestructorDecl(ASTContext & astContext) const3895*67e74705SXin Li CFGImplicitDtor::getDestructorDecl(ASTContext &astContext) const {
3896*67e74705SXin Li switch (getKind()) {
3897*67e74705SXin Li case CFGElement::Statement:
3898*67e74705SXin Li case CFGElement::Initializer:
3899*67e74705SXin Li case CFGElement::NewAllocator:
3900*67e74705SXin Li llvm_unreachable("getDestructorDecl should only be used with "
3901*67e74705SXin Li "ImplicitDtors");
3902*67e74705SXin Li case CFGElement::AutomaticObjectDtor: {
3903*67e74705SXin Li const VarDecl *var = castAs<CFGAutomaticObjDtor>().getVarDecl();
3904*67e74705SXin Li QualType ty = var->getType();
3905*67e74705SXin Li ty = ty.getNonReferenceType();
3906*67e74705SXin Li while (const ArrayType *arrayType = astContext.getAsArrayType(ty)) {
3907*67e74705SXin Li ty = arrayType->getElementType();
3908*67e74705SXin Li }
3909*67e74705SXin Li const RecordType *recordType = ty->getAs<RecordType>();
3910*67e74705SXin Li const CXXRecordDecl *classDecl =
3911*67e74705SXin Li cast<CXXRecordDecl>(recordType->getDecl());
3912*67e74705SXin Li return classDecl->getDestructor();
3913*67e74705SXin Li }
3914*67e74705SXin Li case CFGElement::DeleteDtor: {
3915*67e74705SXin Li const CXXDeleteExpr *DE = castAs<CFGDeleteDtor>().getDeleteExpr();
3916*67e74705SXin Li QualType DTy = DE->getDestroyedType();
3917*67e74705SXin Li DTy = DTy.getNonReferenceType();
3918*67e74705SXin Li const CXXRecordDecl *classDecl =
3919*67e74705SXin Li astContext.getBaseElementType(DTy)->getAsCXXRecordDecl();
3920*67e74705SXin Li return classDecl->getDestructor();
3921*67e74705SXin Li }
3922*67e74705SXin Li case CFGElement::TemporaryDtor: {
3923*67e74705SXin Li const CXXBindTemporaryExpr *bindExpr =
3924*67e74705SXin Li castAs<CFGTemporaryDtor>().getBindTemporaryExpr();
3925*67e74705SXin Li const CXXTemporary *temp = bindExpr->getTemporary();
3926*67e74705SXin Li return temp->getDestructor();
3927*67e74705SXin Li }
3928*67e74705SXin Li case CFGElement::BaseDtor:
3929*67e74705SXin Li case CFGElement::MemberDtor:
3930*67e74705SXin Li
3931*67e74705SXin Li // Not yet supported.
3932*67e74705SXin Li return nullptr;
3933*67e74705SXin Li }
3934*67e74705SXin Li llvm_unreachable("getKind() returned bogus value");
3935*67e74705SXin Li }
3936*67e74705SXin Li
isNoReturn(ASTContext & astContext) const3937*67e74705SXin Li bool CFGImplicitDtor::isNoReturn(ASTContext &astContext) const {
3938*67e74705SXin Li if (const CXXDestructorDecl *DD = getDestructorDecl(astContext))
3939*67e74705SXin Li return DD->isNoReturn();
3940*67e74705SXin Li return false;
3941*67e74705SXin Li }
3942*67e74705SXin Li
3943*67e74705SXin Li //===----------------------------------------------------------------------===//
3944*67e74705SXin Li // CFGBlock operations.
3945*67e74705SXin Li //===----------------------------------------------------------------------===//
3946*67e74705SXin Li
AdjacentBlock(CFGBlock * B,bool IsReachable)3947*67e74705SXin Li CFGBlock::AdjacentBlock::AdjacentBlock(CFGBlock *B, bool IsReachable)
3948*67e74705SXin Li : ReachableBlock(IsReachable ? B : nullptr),
3949*67e74705SXin Li UnreachableBlock(!IsReachable ? B : nullptr,
3950*67e74705SXin Li B && IsReachable ? AB_Normal : AB_Unreachable) {}
3951*67e74705SXin Li
AdjacentBlock(CFGBlock * B,CFGBlock * AlternateBlock)3952*67e74705SXin Li CFGBlock::AdjacentBlock::AdjacentBlock(CFGBlock *B, CFGBlock *AlternateBlock)
3953*67e74705SXin Li : ReachableBlock(B),
3954*67e74705SXin Li UnreachableBlock(B == AlternateBlock ? nullptr : AlternateBlock,
3955*67e74705SXin Li B == AlternateBlock ? AB_Alternate : AB_Normal) {}
3956*67e74705SXin Li
addSuccessor(AdjacentBlock Succ,BumpVectorContext & C)3957*67e74705SXin Li void CFGBlock::addSuccessor(AdjacentBlock Succ,
3958*67e74705SXin Li BumpVectorContext &C) {
3959*67e74705SXin Li if (CFGBlock *B = Succ.getReachableBlock())
3960*67e74705SXin Li B->Preds.push_back(AdjacentBlock(this, Succ.isReachable()), C);
3961*67e74705SXin Li
3962*67e74705SXin Li if (CFGBlock *UnreachableB = Succ.getPossiblyUnreachableBlock())
3963*67e74705SXin Li UnreachableB->Preds.push_back(AdjacentBlock(this, false), C);
3964*67e74705SXin Li
3965*67e74705SXin Li Succs.push_back(Succ, C);
3966*67e74705SXin Li }
3967*67e74705SXin Li
FilterEdge(const CFGBlock::FilterOptions & F,const CFGBlock * From,const CFGBlock * To)3968*67e74705SXin Li bool CFGBlock::FilterEdge(const CFGBlock::FilterOptions &F,
3969*67e74705SXin Li const CFGBlock *From, const CFGBlock *To) {
3970*67e74705SXin Li
3971*67e74705SXin Li if (F.IgnoreNullPredecessors && !From)
3972*67e74705SXin Li return true;
3973*67e74705SXin Li
3974*67e74705SXin Li if (To && From && F.IgnoreDefaultsWithCoveredEnums) {
3975*67e74705SXin Li // If the 'To' has no label or is labeled but the label isn't a
3976*67e74705SXin Li // CaseStmt then filter this edge.
3977*67e74705SXin Li if (const SwitchStmt *S =
3978*67e74705SXin Li dyn_cast_or_null<SwitchStmt>(From->getTerminator().getStmt())) {
3979*67e74705SXin Li if (S->isAllEnumCasesCovered()) {
3980*67e74705SXin Li const Stmt *L = To->getLabel();
3981*67e74705SXin Li if (!L || !isa<CaseStmt>(L))
3982*67e74705SXin Li return true;
3983*67e74705SXin Li }
3984*67e74705SXin Li }
3985*67e74705SXin Li }
3986*67e74705SXin Li
3987*67e74705SXin Li return false;
3988*67e74705SXin Li }
3989*67e74705SXin Li
3990*67e74705SXin Li //===----------------------------------------------------------------------===//
3991*67e74705SXin Li // CFG pretty printing
3992*67e74705SXin Li //===----------------------------------------------------------------------===//
3993*67e74705SXin Li
3994*67e74705SXin Li namespace {
3995*67e74705SXin Li
3996*67e74705SXin Li class StmtPrinterHelper : public PrinterHelper {
3997*67e74705SXin Li typedef llvm::DenseMap<const Stmt*,std::pair<unsigned,unsigned> > StmtMapTy;
3998*67e74705SXin Li typedef llvm::DenseMap<const Decl*,std::pair<unsigned,unsigned> > DeclMapTy;
3999*67e74705SXin Li StmtMapTy StmtMap;
4000*67e74705SXin Li DeclMapTy DeclMap;
4001*67e74705SXin Li signed currentBlock;
4002*67e74705SXin Li unsigned currStmt;
4003*67e74705SXin Li const LangOptions &LangOpts;
4004*67e74705SXin Li public:
4005*67e74705SXin Li
StmtPrinterHelper(const CFG * cfg,const LangOptions & LO)4006*67e74705SXin Li StmtPrinterHelper(const CFG* cfg, const LangOptions &LO)
4007*67e74705SXin Li : currentBlock(0), currStmt(0), LangOpts(LO)
4008*67e74705SXin Li {
4009*67e74705SXin Li for (CFG::const_iterator I = cfg->begin(), E = cfg->end(); I != E; ++I ) {
4010*67e74705SXin Li unsigned j = 1;
4011*67e74705SXin Li for (CFGBlock::const_iterator BI = (*I)->begin(), BEnd = (*I)->end() ;
4012*67e74705SXin Li BI != BEnd; ++BI, ++j ) {
4013*67e74705SXin Li if (Optional<CFGStmt> SE = BI->getAs<CFGStmt>()) {
4014*67e74705SXin Li const Stmt *stmt= SE->getStmt();
4015*67e74705SXin Li std::pair<unsigned, unsigned> P((*I)->getBlockID(), j);
4016*67e74705SXin Li StmtMap[stmt] = P;
4017*67e74705SXin Li
4018*67e74705SXin Li switch (stmt->getStmtClass()) {
4019*67e74705SXin Li case Stmt::DeclStmtClass:
4020*67e74705SXin Li DeclMap[cast<DeclStmt>(stmt)->getSingleDecl()] = P;
4021*67e74705SXin Li break;
4022*67e74705SXin Li case Stmt::IfStmtClass: {
4023*67e74705SXin Li const VarDecl *var = cast<IfStmt>(stmt)->getConditionVariable();
4024*67e74705SXin Li if (var)
4025*67e74705SXin Li DeclMap[var] = P;
4026*67e74705SXin Li break;
4027*67e74705SXin Li }
4028*67e74705SXin Li case Stmt::ForStmtClass: {
4029*67e74705SXin Li const VarDecl *var = cast<ForStmt>(stmt)->getConditionVariable();
4030*67e74705SXin Li if (var)
4031*67e74705SXin Li DeclMap[var] = P;
4032*67e74705SXin Li break;
4033*67e74705SXin Li }
4034*67e74705SXin Li case Stmt::WhileStmtClass: {
4035*67e74705SXin Li const VarDecl *var =
4036*67e74705SXin Li cast<WhileStmt>(stmt)->getConditionVariable();
4037*67e74705SXin Li if (var)
4038*67e74705SXin Li DeclMap[var] = P;
4039*67e74705SXin Li break;
4040*67e74705SXin Li }
4041*67e74705SXin Li case Stmt::SwitchStmtClass: {
4042*67e74705SXin Li const VarDecl *var =
4043*67e74705SXin Li cast<SwitchStmt>(stmt)->getConditionVariable();
4044*67e74705SXin Li if (var)
4045*67e74705SXin Li DeclMap[var] = P;
4046*67e74705SXin Li break;
4047*67e74705SXin Li }
4048*67e74705SXin Li case Stmt::CXXCatchStmtClass: {
4049*67e74705SXin Li const VarDecl *var =
4050*67e74705SXin Li cast<CXXCatchStmt>(stmt)->getExceptionDecl();
4051*67e74705SXin Li if (var)
4052*67e74705SXin Li DeclMap[var] = P;
4053*67e74705SXin Li break;
4054*67e74705SXin Li }
4055*67e74705SXin Li default:
4056*67e74705SXin Li break;
4057*67e74705SXin Li }
4058*67e74705SXin Li }
4059*67e74705SXin Li }
4060*67e74705SXin Li }
4061*67e74705SXin Li }
4062*67e74705SXin Li
~StmtPrinterHelper()4063*67e74705SXin Li ~StmtPrinterHelper() override {}
4064*67e74705SXin Li
getLangOpts() const4065*67e74705SXin Li const LangOptions &getLangOpts() const { return LangOpts; }
setBlockID(signed i)4066*67e74705SXin Li void setBlockID(signed i) { currentBlock = i; }
setStmtID(unsigned i)4067*67e74705SXin Li void setStmtID(unsigned i) { currStmt = i; }
4068*67e74705SXin Li
handledStmt(Stmt * S,raw_ostream & OS)4069*67e74705SXin Li bool handledStmt(Stmt *S, raw_ostream &OS) override {
4070*67e74705SXin Li StmtMapTy::iterator I = StmtMap.find(S);
4071*67e74705SXin Li
4072*67e74705SXin Li if (I == StmtMap.end())
4073*67e74705SXin Li return false;
4074*67e74705SXin Li
4075*67e74705SXin Li if (currentBlock >= 0 && I->second.first == (unsigned) currentBlock
4076*67e74705SXin Li && I->second.second == currStmt) {
4077*67e74705SXin Li return false;
4078*67e74705SXin Li }
4079*67e74705SXin Li
4080*67e74705SXin Li OS << "[B" << I->second.first << "." << I->second.second << "]";
4081*67e74705SXin Li return true;
4082*67e74705SXin Li }
4083*67e74705SXin Li
handleDecl(const Decl * D,raw_ostream & OS)4084*67e74705SXin Li bool handleDecl(const Decl *D, raw_ostream &OS) {
4085*67e74705SXin Li DeclMapTy::iterator I = DeclMap.find(D);
4086*67e74705SXin Li
4087*67e74705SXin Li if (I == DeclMap.end())
4088*67e74705SXin Li return false;
4089*67e74705SXin Li
4090*67e74705SXin Li if (currentBlock >= 0 && I->second.first == (unsigned) currentBlock
4091*67e74705SXin Li && I->second.second == currStmt) {
4092*67e74705SXin Li return false;
4093*67e74705SXin Li }
4094*67e74705SXin Li
4095*67e74705SXin Li OS << "[B" << I->second.first << "." << I->second.second << "]";
4096*67e74705SXin Li return true;
4097*67e74705SXin Li }
4098*67e74705SXin Li };
4099*67e74705SXin Li } // end anonymous namespace
4100*67e74705SXin Li
4101*67e74705SXin Li
4102*67e74705SXin Li namespace {
4103*67e74705SXin Li class CFGBlockTerminatorPrint
4104*67e74705SXin Li : public StmtVisitor<CFGBlockTerminatorPrint,void> {
4105*67e74705SXin Li
4106*67e74705SXin Li raw_ostream &OS;
4107*67e74705SXin Li StmtPrinterHelper* Helper;
4108*67e74705SXin Li PrintingPolicy Policy;
4109*67e74705SXin Li public:
CFGBlockTerminatorPrint(raw_ostream & os,StmtPrinterHelper * helper,const PrintingPolicy & Policy)4110*67e74705SXin Li CFGBlockTerminatorPrint(raw_ostream &os, StmtPrinterHelper* helper,
4111*67e74705SXin Li const PrintingPolicy &Policy)
4112*67e74705SXin Li : OS(os), Helper(helper), Policy(Policy) {
4113*67e74705SXin Li this->Policy.IncludeNewlines = false;
4114*67e74705SXin Li }
4115*67e74705SXin Li
VisitIfStmt(IfStmt * I)4116*67e74705SXin Li void VisitIfStmt(IfStmt *I) {
4117*67e74705SXin Li OS << "if ";
4118*67e74705SXin Li if (Stmt *C = I->getCond())
4119*67e74705SXin Li C->printPretty(OS, Helper, Policy);
4120*67e74705SXin Li }
4121*67e74705SXin Li
4122*67e74705SXin Li // Default case.
VisitStmt(Stmt * Terminator)4123*67e74705SXin Li void VisitStmt(Stmt *Terminator) {
4124*67e74705SXin Li Terminator->printPretty(OS, Helper, Policy);
4125*67e74705SXin Li }
4126*67e74705SXin Li
VisitDeclStmt(DeclStmt * DS)4127*67e74705SXin Li void VisitDeclStmt(DeclStmt *DS) {
4128*67e74705SXin Li VarDecl *VD = cast<VarDecl>(DS->getSingleDecl());
4129*67e74705SXin Li OS << "static init " << VD->getName();
4130*67e74705SXin Li }
4131*67e74705SXin Li
VisitForStmt(ForStmt * F)4132*67e74705SXin Li void VisitForStmt(ForStmt *F) {
4133*67e74705SXin Li OS << "for (" ;
4134*67e74705SXin Li if (F->getInit())
4135*67e74705SXin Li OS << "...";
4136*67e74705SXin Li OS << "; ";
4137*67e74705SXin Li if (Stmt *C = F->getCond())
4138*67e74705SXin Li C->printPretty(OS, Helper, Policy);
4139*67e74705SXin Li OS << "; ";
4140*67e74705SXin Li if (F->getInc())
4141*67e74705SXin Li OS << "...";
4142*67e74705SXin Li OS << ")";
4143*67e74705SXin Li }
4144*67e74705SXin Li
VisitWhileStmt(WhileStmt * W)4145*67e74705SXin Li void VisitWhileStmt(WhileStmt *W) {
4146*67e74705SXin Li OS << "while " ;
4147*67e74705SXin Li if (Stmt *C = W->getCond())
4148*67e74705SXin Li C->printPretty(OS, Helper, Policy);
4149*67e74705SXin Li }
4150*67e74705SXin Li
VisitDoStmt(DoStmt * D)4151*67e74705SXin Li void VisitDoStmt(DoStmt *D) {
4152*67e74705SXin Li OS << "do ... while ";
4153*67e74705SXin Li if (Stmt *C = D->getCond())
4154*67e74705SXin Li C->printPretty(OS, Helper, Policy);
4155*67e74705SXin Li }
4156*67e74705SXin Li
VisitSwitchStmt(SwitchStmt * Terminator)4157*67e74705SXin Li void VisitSwitchStmt(SwitchStmt *Terminator) {
4158*67e74705SXin Li OS << "switch ";
4159*67e74705SXin Li Terminator->getCond()->printPretty(OS, Helper, Policy);
4160*67e74705SXin Li }
4161*67e74705SXin Li
VisitCXXTryStmt(CXXTryStmt * CS)4162*67e74705SXin Li void VisitCXXTryStmt(CXXTryStmt *CS) {
4163*67e74705SXin Li OS << "try ...";
4164*67e74705SXin Li }
4165*67e74705SXin Li
VisitAbstractConditionalOperator(AbstractConditionalOperator * C)4166*67e74705SXin Li void VisitAbstractConditionalOperator(AbstractConditionalOperator* C) {
4167*67e74705SXin Li if (Stmt *Cond = C->getCond())
4168*67e74705SXin Li Cond->printPretty(OS, Helper, Policy);
4169*67e74705SXin Li OS << " ? ... : ...";
4170*67e74705SXin Li }
4171*67e74705SXin Li
VisitChooseExpr(ChooseExpr * C)4172*67e74705SXin Li void VisitChooseExpr(ChooseExpr *C) {
4173*67e74705SXin Li OS << "__builtin_choose_expr( ";
4174*67e74705SXin Li if (Stmt *Cond = C->getCond())
4175*67e74705SXin Li Cond->printPretty(OS, Helper, Policy);
4176*67e74705SXin Li OS << " )";
4177*67e74705SXin Li }
4178*67e74705SXin Li
VisitIndirectGotoStmt(IndirectGotoStmt * I)4179*67e74705SXin Li void VisitIndirectGotoStmt(IndirectGotoStmt *I) {
4180*67e74705SXin Li OS << "goto *";
4181*67e74705SXin Li if (Stmt *T = I->getTarget())
4182*67e74705SXin Li T->printPretty(OS, Helper, Policy);
4183*67e74705SXin Li }
4184*67e74705SXin Li
VisitBinaryOperator(BinaryOperator * B)4185*67e74705SXin Li void VisitBinaryOperator(BinaryOperator* B) {
4186*67e74705SXin Li if (!B->isLogicalOp()) {
4187*67e74705SXin Li VisitExpr(B);
4188*67e74705SXin Li return;
4189*67e74705SXin Li }
4190*67e74705SXin Li
4191*67e74705SXin Li if (B->getLHS())
4192*67e74705SXin Li B->getLHS()->printPretty(OS, Helper, Policy);
4193*67e74705SXin Li
4194*67e74705SXin Li switch (B->getOpcode()) {
4195*67e74705SXin Li case BO_LOr:
4196*67e74705SXin Li OS << " || ...";
4197*67e74705SXin Li return;
4198*67e74705SXin Li case BO_LAnd:
4199*67e74705SXin Li OS << " && ...";
4200*67e74705SXin Li return;
4201*67e74705SXin Li default:
4202*67e74705SXin Li llvm_unreachable("Invalid logical operator.");
4203*67e74705SXin Li }
4204*67e74705SXin Li }
4205*67e74705SXin Li
VisitExpr(Expr * E)4206*67e74705SXin Li void VisitExpr(Expr *E) {
4207*67e74705SXin Li E->printPretty(OS, Helper, Policy);
4208*67e74705SXin Li }
4209*67e74705SXin Li
4210*67e74705SXin Li public:
print(CFGTerminator T)4211*67e74705SXin Li void print(CFGTerminator T) {
4212*67e74705SXin Li if (T.isTemporaryDtorsBranch())
4213*67e74705SXin Li OS << "(Temp Dtor) ";
4214*67e74705SXin Li Visit(T.getStmt());
4215*67e74705SXin Li }
4216*67e74705SXin Li };
4217*67e74705SXin Li } // end anonymous namespace
4218*67e74705SXin Li
print_elem(raw_ostream & OS,StmtPrinterHelper & Helper,const CFGElement & E)4219*67e74705SXin Li static void print_elem(raw_ostream &OS, StmtPrinterHelper &Helper,
4220*67e74705SXin Li const CFGElement &E) {
4221*67e74705SXin Li if (Optional<CFGStmt> CS = E.getAs<CFGStmt>()) {
4222*67e74705SXin Li const Stmt *S = CS->getStmt();
4223*67e74705SXin Li assert(S != nullptr && "Expecting non-null Stmt");
4224*67e74705SXin Li
4225*67e74705SXin Li // special printing for statement-expressions.
4226*67e74705SXin Li if (const StmtExpr *SE = dyn_cast<StmtExpr>(S)) {
4227*67e74705SXin Li const CompoundStmt *Sub = SE->getSubStmt();
4228*67e74705SXin Li
4229*67e74705SXin Li auto Children = Sub->children();
4230*67e74705SXin Li if (Children.begin() != Children.end()) {
4231*67e74705SXin Li OS << "({ ... ; ";
4232*67e74705SXin Li Helper.handledStmt(*SE->getSubStmt()->body_rbegin(),OS);
4233*67e74705SXin Li OS << " })\n";
4234*67e74705SXin Li return;
4235*67e74705SXin Li }
4236*67e74705SXin Li }
4237*67e74705SXin Li // special printing for comma expressions.
4238*67e74705SXin Li if (const BinaryOperator* B = dyn_cast<BinaryOperator>(S)) {
4239*67e74705SXin Li if (B->getOpcode() == BO_Comma) {
4240*67e74705SXin Li OS << "... , ";
4241*67e74705SXin Li Helper.handledStmt(B->getRHS(),OS);
4242*67e74705SXin Li OS << '\n';
4243*67e74705SXin Li return;
4244*67e74705SXin Li }
4245*67e74705SXin Li }
4246*67e74705SXin Li S->printPretty(OS, &Helper, PrintingPolicy(Helper.getLangOpts()));
4247*67e74705SXin Li
4248*67e74705SXin Li if (isa<CXXOperatorCallExpr>(S)) {
4249*67e74705SXin Li OS << " (OperatorCall)";
4250*67e74705SXin Li }
4251*67e74705SXin Li else if (isa<CXXBindTemporaryExpr>(S)) {
4252*67e74705SXin Li OS << " (BindTemporary)";
4253*67e74705SXin Li }
4254*67e74705SXin Li else if (const CXXConstructExpr *CCE = dyn_cast<CXXConstructExpr>(S)) {
4255*67e74705SXin Li OS << " (CXXConstructExpr, " << CCE->getType().getAsString() << ")";
4256*67e74705SXin Li }
4257*67e74705SXin Li else if (const CastExpr *CE = dyn_cast<CastExpr>(S)) {
4258*67e74705SXin Li OS << " (" << CE->getStmtClassName() << ", "
4259*67e74705SXin Li << CE->getCastKindName()
4260*67e74705SXin Li << ", " << CE->getType().getAsString()
4261*67e74705SXin Li << ")";
4262*67e74705SXin Li }
4263*67e74705SXin Li
4264*67e74705SXin Li // Expressions need a newline.
4265*67e74705SXin Li if (isa<Expr>(S))
4266*67e74705SXin Li OS << '\n';
4267*67e74705SXin Li
4268*67e74705SXin Li } else if (Optional<CFGInitializer> IE = E.getAs<CFGInitializer>()) {
4269*67e74705SXin Li const CXXCtorInitializer *I = IE->getInitializer();
4270*67e74705SXin Li if (I->isBaseInitializer())
4271*67e74705SXin Li OS << I->getBaseClass()->getAsCXXRecordDecl()->getName();
4272*67e74705SXin Li else if (I->isDelegatingInitializer())
4273*67e74705SXin Li OS << I->getTypeSourceInfo()->getType()->getAsCXXRecordDecl()->getName();
4274*67e74705SXin Li else OS << I->getAnyMember()->getName();
4275*67e74705SXin Li
4276*67e74705SXin Li OS << "(";
4277*67e74705SXin Li if (Expr *IE = I->getInit())
4278*67e74705SXin Li IE->printPretty(OS, &Helper, PrintingPolicy(Helper.getLangOpts()));
4279*67e74705SXin Li OS << ")";
4280*67e74705SXin Li
4281*67e74705SXin Li if (I->isBaseInitializer())
4282*67e74705SXin Li OS << " (Base initializer)\n";
4283*67e74705SXin Li else if (I->isDelegatingInitializer())
4284*67e74705SXin Li OS << " (Delegating initializer)\n";
4285*67e74705SXin Li else OS << " (Member initializer)\n";
4286*67e74705SXin Li
4287*67e74705SXin Li } else if (Optional<CFGAutomaticObjDtor> DE =
4288*67e74705SXin Li E.getAs<CFGAutomaticObjDtor>()) {
4289*67e74705SXin Li const VarDecl *VD = DE->getVarDecl();
4290*67e74705SXin Li Helper.handleDecl(VD, OS);
4291*67e74705SXin Li
4292*67e74705SXin Li const Type* T = VD->getType().getTypePtr();
4293*67e74705SXin Li if (const ReferenceType* RT = T->getAs<ReferenceType>())
4294*67e74705SXin Li T = RT->getPointeeType().getTypePtr();
4295*67e74705SXin Li T = T->getBaseElementTypeUnsafe();
4296*67e74705SXin Li
4297*67e74705SXin Li OS << ".~" << T->getAsCXXRecordDecl()->getName().str() << "()";
4298*67e74705SXin Li OS << " (Implicit destructor)\n";
4299*67e74705SXin Li
4300*67e74705SXin Li } else if (Optional<CFGNewAllocator> NE = E.getAs<CFGNewAllocator>()) {
4301*67e74705SXin Li OS << "CFGNewAllocator(";
4302*67e74705SXin Li if (const CXXNewExpr *AllocExpr = NE->getAllocatorExpr())
4303*67e74705SXin Li AllocExpr->getType().print(OS, PrintingPolicy(Helper.getLangOpts()));
4304*67e74705SXin Li OS << ")\n";
4305*67e74705SXin Li } else if (Optional<CFGDeleteDtor> DE = E.getAs<CFGDeleteDtor>()) {
4306*67e74705SXin Li const CXXRecordDecl *RD = DE->getCXXRecordDecl();
4307*67e74705SXin Li if (!RD)
4308*67e74705SXin Li return;
4309*67e74705SXin Li CXXDeleteExpr *DelExpr =
4310*67e74705SXin Li const_cast<CXXDeleteExpr*>(DE->getDeleteExpr());
4311*67e74705SXin Li Helper.handledStmt(cast<Stmt>(DelExpr->getArgument()), OS);
4312*67e74705SXin Li OS << "->~" << RD->getName().str() << "()";
4313*67e74705SXin Li OS << " (Implicit destructor)\n";
4314*67e74705SXin Li } else if (Optional<CFGBaseDtor> BE = E.getAs<CFGBaseDtor>()) {
4315*67e74705SXin Li const CXXBaseSpecifier *BS = BE->getBaseSpecifier();
4316*67e74705SXin Li OS << "~" << BS->getType()->getAsCXXRecordDecl()->getName() << "()";
4317*67e74705SXin Li OS << " (Base object destructor)\n";
4318*67e74705SXin Li
4319*67e74705SXin Li } else if (Optional<CFGMemberDtor> ME = E.getAs<CFGMemberDtor>()) {
4320*67e74705SXin Li const FieldDecl *FD = ME->getFieldDecl();
4321*67e74705SXin Li const Type *T = FD->getType()->getBaseElementTypeUnsafe();
4322*67e74705SXin Li OS << "this->" << FD->getName();
4323*67e74705SXin Li OS << ".~" << T->getAsCXXRecordDecl()->getName() << "()";
4324*67e74705SXin Li OS << " (Member object destructor)\n";
4325*67e74705SXin Li
4326*67e74705SXin Li } else if (Optional<CFGTemporaryDtor> TE = E.getAs<CFGTemporaryDtor>()) {
4327*67e74705SXin Li const CXXBindTemporaryExpr *BT = TE->getBindTemporaryExpr();
4328*67e74705SXin Li OS << "~";
4329*67e74705SXin Li BT->getType().print(OS, PrintingPolicy(Helper.getLangOpts()));
4330*67e74705SXin Li OS << "() (Temporary object destructor)\n";
4331*67e74705SXin Li }
4332*67e74705SXin Li }
4333*67e74705SXin Li
print_block(raw_ostream & OS,const CFG * cfg,const CFGBlock & B,StmtPrinterHelper & Helper,bool print_edges,bool ShowColors)4334*67e74705SXin Li static void print_block(raw_ostream &OS, const CFG* cfg,
4335*67e74705SXin Li const CFGBlock &B,
4336*67e74705SXin Li StmtPrinterHelper &Helper, bool print_edges,
4337*67e74705SXin Li bool ShowColors) {
4338*67e74705SXin Li
4339*67e74705SXin Li Helper.setBlockID(B.getBlockID());
4340*67e74705SXin Li
4341*67e74705SXin Li // Print the header.
4342*67e74705SXin Li if (ShowColors)
4343*67e74705SXin Li OS.changeColor(raw_ostream::YELLOW, true);
4344*67e74705SXin Li
4345*67e74705SXin Li OS << "\n [B" << B.getBlockID();
4346*67e74705SXin Li
4347*67e74705SXin Li if (&B == &cfg->getEntry())
4348*67e74705SXin Li OS << " (ENTRY)]\n";
4349*67e74705SXin Li else if (&B == &cfg->getExit())
4350*67e74705SXin Li OS << " (EXIT)]\n";
4351*67e74705SXin Li else if (&B == cfg->getIndirectGotoBlock())
4352*67e74705SXin Li OS << " (INDIRECT GOTO DISPATCH)]\n";
4353*67e74705SXin Li else if (B.hasNoReturnElement())
4354*67e74705SXin Li OS << " (NORETURN)]\n";
4355*67e74705SXin Li else
4356*67e74705SXin Li OS << "]\n";
4357*67e74705SXin Li
4358*67e74705SXin Li if (ShowColors)
4359*67e74705SXin Li OS.resetColor();
4360*67e74705SXin Li
4361*67e74705SXin Li // Print the label of this block.
4362*67e74705SXin Li if (Stmt *Label = const_cast<Stmt*>(B.getLabel())) {
4363*67e74705SXin Li
4364*67e74705SXin Li if (print_edges)
4365*67e74705SXin Li OS << " ";
4366*67e74705SXin Li
4367*67e74705SXin Li if (LabelStmt *L = dyn_cast<LabelStmt>(Label))
4368*67e74705SXin Li OS << L->getName();
4369*67e74705SXin Li else if (CaseStmt *C = dyn_cast<CaseStmt>(Label)) {
4370*67e74705SXin Li OS << "case ";
4371*67e74705SXin Li if (C->getLHS())
4372*67e74705SXin Li C->getLHS()->printPretty(OS, &Helper,
4373*67e74705SXin Li PrintingPolicy(Helper.getLangOpts()));
4374*67e74705SXin Li if (C->getRHS()) {
4375*67e74705SXin Li OS << " ... ";
4376*67e74705SXin Li C->getRHS()->printPretty(OS, &Helper,
4377*67e74705SXin Li PrintingPolicy(Helper.getLangOpts()));
4378*67e74705SXin Li }
4379*67e74705SXin Li } else if (isa<DefaultStmt>(Label))
4380*67e74705SXin Li OS << "default";
4381*67e74705SXin Li else if (CXXCatchStmt *CS = dyn_cast<CXXCatchStmt>(Label)) {
4382*67e74705SXin Li OS << "catch (";
4383*67e74705SXin Li if (CS->getExceptionDecl())
4384*67e74705SXin Li CS->getExceptionDecl()->print(OS, PrintingPolicy(Helper.getLangOpts()),
4385*67e74705SXin Li 0);
4386*67e74705SXin Li else
4387*67e74705SXin Li OS << "...";
4388*67e74705SXin Li OS << ")";
4389*67e74705SXin Li
4390*67e74705SXin Li } else
4391*67e74705SXin Li llvm_unreachable("Invalid label statement in CFGBlock.");
4392*67e74705SXin Li
4393*67e74705SXin Li OS << ":\n";
4394*67e74705SXin Li }
4395*67e74705SXin Li
4396*67e74705SXin Li // Iterate through the statements in the block and print them.
4397*67e74705SXin Li unsigned j = 1;
4398*67e74705SXin Li
4399*67e74705SXin Li for (CFGBlock::const_iterator I = B.begin(), E = B.end() ;
4400*67e74705SXin Li I != E ; ++I, ++j ) {
4401*67e74705SXin Li
4402*67e74705SXin Li // Print the statement # in the basic block and the statement itself.
4403*67e74705SXin Li if (print_edges)
4404*67e74705SXin Li OS << " ";
4405*67e74705SXin Li
4406*67e74705SXin Li OS << llvm::format("%3d", j) << ": ";
4407*67e74705SXin Li
4408*67e74705SXin Li Helper.setStmtID(j);
4409*67e74705SXin Li
4410*67e74705SXin Li print_elem(OS, Helper, *I);
4411*67e74705SXin Li }
4412*67e74705SXin Li
4413*67e74705SXin Li // Print the terminator of this block.
4414*67e74705SXin Li if (B.getTerminator()) {
4415*67e74705SXin Li if (ShowColors)
4416*67e74705SXin Li OS.changeColor(raw_ostream::GREEN);
4417*67e74705SXin Li
4418*67e74705SXin Li OS << " T: ";
4419*67e74705SXin Li
4420*67e74705SXin Li Helper.setBlockID(-1);
4421*67e74705SXin Li
4422*67e74705SXin Li PrintingPolicy PP(Helper.getLangOpts());
4423*67e74705SXin Li CFGBlockTerminatorPrint TPrinter(OS, &Helper, PP);
4424*67e74705SXin Li TPrinter.print(B.getTerminator());
4425*67e74705SXin Li OS << '\n';
4426*67e74705SXin Li
4427*67e74705SXin Li if (ShowColors)
4428*67e74705SXin Li OS.resetColor();
4429*67e74705SXin Li }
4430*67e74705SXin Li
4431*67e74705SXin Li if (print_edges) {
4432*67e74705SXin Li // Print the predecessors of this block.
4433*67e74705SXin Li if (!B.pred_empty()) {
4434*67e74705SXin Li const raw_ostream::Colors Color = raw_ostream::BLUE;
4435*67e74705SXin Li if (ShowColors)
4436*67e74705SXin Li OS.changeColor(Color);
4437*67e74705SXin Li OS << " Preds " ;
4438*67e74705SXin Li if (ShowColors)
4439*67e74705SXin Li OS.resetColor();
4440*67e74705SXin Li OS << '(' << B.pred_size() << "):";
4441*67e74705SXin Li unsigned i = 0;
4442*67e74705SXin Li
4443*67e74705SXin Li if (ShowColors)
4444*67e74705SXin Li OS.changeColor(Color);
4445*67e74705SXin Li
4446*67e74705SXin Li for (CFGBlock::const_pred_iterator I = B.pred_begin(), E = B.pred_end();
4447*67e74705SXin Li I != E; ++I, ++i) {
4448*67e74705SXin Li
4449*67e74705SXin Li if (i % 10 == 8)
4450*67e74705SXin Li OS << "\n ";
4451*67e74705SXin Li
4452*67e74705SXin Li CFGBlock *B = *I;
4453*67e74705SXin Li bool Reachable = true;
4454*67e74705SXin Li if (!B) {
4455*67e74705SXin Li Reachable = false;
4456*67e74705SXin Li B = I->getPossiblyUnreachableBlock();
4457*67e74705SXin Li }
4458*67e74705SXin Li
4459*67e74705SXin Li OS << " B" << B->getBlockID();
4460*67e74705SXin Li if (!Reachable)
4461*67e74705SXin Li OS << "(Unreachable)";
4462*67e74705SXin Li }
4463*67e74705SXin Li
4464*67e74705SXin Li if (ShowColors)
4465*67e74705SXin Li OS.resetColor();
4466*67e74705SXin Li
4467*67e74705SXin Li OS << '\n';
4468*67e74705SXin Li }
4469*67e74705SXin Li
4470*67e74705SXin Li // Print the successors of this block.
4471*67e74705SXin Li if (!B.succ_empty()) {
4472*67e74705SXin Li const raw_ostream::Colors Color = raw_ostream::MAGENTA;
4473*67e74705SXin Li if (ShowColors)
4474*67e74705SXin Li OS.changeColor(Color);
4475*67e74705SXin Li OS << " Succs ";
4476*67e74705SXin Li if (ShowColors)
4477*67e74705SXin Li OS.resetColor();
4478*67e74705SXin Li OS << '(' << B.succ_size() << "):";
4479*67e74705SXin Li unsigned i = 0;
4480*67e74705SXin Li
4481*67e74705SXin Li if (ShowColors)
4482*67e74705SXin Li OS.changeColor(Color);
4483*67e74705SXin Li
4484*67e74705SXin Li for (CFGBlock::const_succ_iterator I = B.succ_begin(), E = B.succ_end();
4485*67e74705SXin Li I != E; ++I, ++i) {
4486*67e74705SXin Li
4487*67e74705SXin Li if (i % 10 == 8)
4488*67e74705SXin Li OS << "\n ";
4489*67e74705SXin Li
4490*67e74705SXin Li CFGBlock *B = *I;
4491*67e74705SXin Li
4492*67e74705SXin Li bool Reachable = true;
4493*67e74705SXin Li if (!B) {
4494*67e74705SXin Li Reachable = false;
4495*67e74705SXin Li B = I->getPossiblyUnreachableBlock();
4496*67e74705SXin Li }
4497*67e74705SXin Li
4498*67e74705SXin Li if (B) {
4499*67e74705SXin Li OS << " B" << B->getBlockID();
4500*67e74705SXin Li if (!Reachable)
4501*67e74705SXin Li OS << "(Unreachable)";
4502*67e74705SXin Li }
4503*67e74705SXin Li else {
4504*67e74705SXin Li OS << " NULL";
4505*67e74705SXin Li }
4506*67e74705SXin Li }
4507*67e74705SXin Li
4508*67e74705SXin Li if (ShowColors)
4509*67e74705SXin Li OS.resetColor();
4510*67e74705SXin Li OS << '\n';
4511*67e74705SXin Li }
4512*67e74705SXin Li }
4513*67e74705SXin Li }
4514*67e74705SXin Li
4515*67e74705SXin Li
4516*67e74705SXin Li /// dump - A simple pretty printer of a CFG that outputs to stderr.
dump(const LangOptions & LO,bool ShowColors) const4517*67e74705SXin Li void CFG::dump(const LangOptions &LO, bool ShowColors) const {
4518*67e74705SXin Li print(llvm::errs(), LO, ShowColors);
4519*67e74705SXin Li }
4520*67e74705SXin Li
4521*67e74705SXin Li /// print - A simple pretty printer of a CFG that outputs to an ostream.
print(raw_ostream & OS,const LangOptions & LO,bool ShowColors) const4522*67e74705SXin Li void CFG::print(raw_ostream &OS, const LangOptions &LO, bool ShowColors) const {
4523*67e74705SXin Li StmtPrinterHelper Helper(this, LO);
4524*67e74705SXin Li
4525*67e74705SXin Li // Print the entry block.
4526*67e74705SXin Li print_block(OS, this, getEntry(), Helper, true, ShowColors);
4527*67e74705SXin Li
4528*67e74705SXin Li // Iterate through the CFGBlocks and print them one by one.
4529*67e74705SXin Li for (const_iterator I = Blocks.begin(), E = Blocks.end() ; I != E ; ++I) {
4530*67e74705SXin Li // Skip the entry block, because we already printed it.
4531*67e74705SXin Li if (&(**I) == &getEntry() || &(**I) == &getExit())
4532*67e74705SXin Li continue;
4533*67e74705SXin Li
4534*67e74705SXin Li print_block(OS, this, **I, Helper, true, ShowColors);
4535*67e74705SXin Li }
4536*67e74705SXin Li
4537*67e74705SXin Li // Print the exit block.
4538*67e74705SXin Li print_block(OS, this, getExit(), Helper, true, ShowColors);
4539*67e74705SXin Li OS << '\n';
4540*67e74705SXin Li OS.flush();
4541*67e74705SXin Li }
4542*67e74705SXin Li
4543*67e74705SXin Li /// dump - A simply pretty printer of a CFGBlock that outputs to stderr.
dump(const CFG * cfg,const LangOptions & LO,bool ShowColors) const4544*67e74705SXin Li void CFGBlock::dump(const CFG* cfg, const LangOptions &LO,
4545*67e74705SXin Li bool ShowColors) const {
4546*67e74705SXin Li print(llvm::errs(), cfg, LO, ShowColors);
4547*67e74705SXin Li }
4548*67e74705SXin Li
dump() const4549*67e74705SXin Li LLVM_DUMP_METHOD void CFGBlock::dump() const {
4550*67e74705SXin Li dump(getParent(), LangOptions(), false);
4551*67e74705SXin Li }
4552*67e74705SXin Li
4553*67e74705SXin Li /// print - A simple pretty printer of a CFGBlock that outputs to an ostream.
4554*67e74705SXin Li /// Generally this will only be called from CFG::print.
print(raw_ostream & OS,const CFG * cfg,const LangOptions & LO,bool ShowColors) const4555*67e74705SXin Li void CFGBlock::print(raw_ostream &OS, const CFG* cfg,
4556*67e74705SXin Li const LangOptions &LO, bool ShowColors) const {
4557*67e74705SXin Li StmtPrinterHelper Helper(cfg, LO);
4558*67e74705SXin Li print_block(OS, cfg, *this, Helper, true, ShowColors);
4559*67e74705SXin Li OS << '\n';
4560*67e74705SXin Li }
4561*67e74705SXin Li
4562*67e74705SXin Li /// printTerminator - A simple pretty printer of the terminator of a CFGBlock.
printTerminator(raw_ostream & OS,const LangOptions & LO) const4563*67e74705SXin Li void CFGBlock::printTerminator(raw_ostream &OS,
4564*67e74705SXin Li const LangOptions &LO) const {
4565*67e74705SXin Li CFGBlockTerminatorPrint TPrinter(OS, nullptr, PrintingPolicy(LO));
4566*67e74705SXin Li TPrinter.print(getTerminator());
4567*67e74705SXin Li }
4568*67e74705SXin Li
getTerminatorCondition(bool StripParens)4569*67e74705SXin Li Stmt *CFGBlock::getTerminatorCondition(bool StripParens) {
4570*67e74705SXin Li Stmt *Terminator = this->Terminator;
4571*67e74705SXin Li if (!Terminator)
4572*67e74705SXin Li return nullptr;
4573*67e74705SXin Li
4574*67e74705SXin Li Expr *E = nullptr;
4575*67e74705SXin Li
4576*67e74705SXin Li switch (Terminator->getStmtClass()) {
4577*67e74705SXin Li default:
4578*67e74705SXin Li break;
4579*67e74705SXin Li
4580*67e74705SXin Li case Stmt::CXXForRangeStmtClass:
4581*67e74705SXin Li E = cast<CXXForRangeStmt>(Terminator)->getCond();
4582*67e74705SXin Li break;
4583*67e74705SXin Li
4584*67e74705SXin Li case Stmt::ForStmtClass:
4585*67e74705SXin Li E = cast<ForStmt>(Terminator)->getCond();
4586*67e74705SXin Li break;
4587*67e74705SXin Li
4588*67e74705SXin Li case Stmt::WhileStmtClass:
4589*67e74705SXin Li E = cast<WhileStmt>(Terminator)->getCond();
4590*67e74705SXin Li break;
4591*67e74705SXin Li
4592*67e74705SXin Li case Stmt::DoStmtClass:
4593*67e74705SXin Li E = cast<DoStmt>(Terminator)->getCond();
4594*67e74705SXin Li break;
4595*67e74705SXin Li
4596*67e74705SXin Li case Stmt::IfStmtClass:
4597*67e74705SXin Li E = cast<IfStmt>(Terminator)->getCond();
4598*67e74705SXin Li break;
4599*67e74705SXin Li
4600*67e74705SXin Li case Stmt::ChooseExprClass:
4601*67e74705SXin Li E = cast<ChooseExpr>(Terminator)->getCond();
4602*67e74705SXin Li break;
4603*67e74705SXin Li
4604*67e74705SXin Li case Stmt::IndirectGotoStmtClass:
4605*67e74705SXin Li E = cast<IndirectGotoStmt>(Terminator)->getTarget();
4606*67e74705SXin Li break;
4607*67e74705SXin Li
4608*67e74705SXin Li case Stmt::SwitchStmtClass:
4609*67e74705SXin Li E = cast<SwitchStmt>(Terminator)->getCond();
4610*67e74705SXin Li break;
4611*67e74705SXin Li
4612*67e74705SXin Li case Stmt::BinaryConditionalOperatorClass:
4613*67e74705SXin Li E = cast<BinaryConditionalOperator>(Terminator)->getCond();
4614*67e74705SXin Li break;
4615*67e74705SXin Li
4616*67e74705SXin Li case Stmt::ConditionalOperatorClass:
4617*67e74705SXin Li E = cast<ConditionalOperator>(Terminator)->getCond();
4618*67e74705SXin Li break;
4619*67e74705SXin Li
4620*67e74705SXin Li case Stmt::BinaryOperatorClass: // '&&' and '||'
4621*67e74705SXin Li E = cast<BinaryOperator>(Terminator)->getLHS();
4622*67e74705SXin Li break;
4623*67e74705SXin Li
4624*67e74705SXin Li case Stmt::ObjCForCollectionStmtClass:
4625*67e74705SXin Li return Terminator;
4626*67e74705SXin Li }
4627*67e74705SXin Li
4628*67e74705SXin Li if (!StripParens)
4629*67e74705SXin Li return E;
4630*67e74705SXin Li
4631*67e74705SXin Li return E ? E->IgnoreParens() : nullptr;
4632*67e74705SXin Li }
4633*67e74705SXin Li
4634*67e74705SXin Li //===----------------------------------------------------------------------===//
4635*67e74705SXin Li // CFG Graphviz Visualization
4636*67e74705SXin Li //===----------------------------------------------------------------------===//
4637*67e74705SXin Li
4638*67e74705SXin Li
4639*67e74705SXin Li #ifndef NDEBUG
4640*67e74705SXin Li static StmtPrinterHelper* GraphHelper;
4641*67e74705SXin Li #endif
4642*67e74705SXin Li
viewCFG(const LangOptions & LO) const4643*67e74705SXin Li void CFG::viewCFG(const LangOptions &LO) const {
4644*67e74705SXin Li #ifndef NDEBUG
4645*67e74705SXin Li StmtPrinterHelper H(this, LO);
4646*67e74705SXin Li GraphHelper = &H;
4647*67e74705SXin Li llvm::ViewGraph(this,"CFG");
4648*67e74705SXin Li GraphHelper = nullptr;
4649*67e74705SXin Li #endif
4650*67e74705SXin Li }
4651*67e74705SXin Li
4652*67e74705SXin Li namespace llvm {
4653*67e74705SXin Li template<>
4654*67e74705SXin Li struct DOTGraphTraits<const CFG*> : public DefaultDOTGraphTraits {
4655*67e74705SXin Li
DOTGraphTraitsllvm::DOTGraphTraits4656*67e74705SXin Li DOTGraphTraits (bool isSimple=false) : DefaultDOTGraphTraits(isSimple) {}
4657*67e74705SXin Li
getNodeLabelllvm::DOTGraphTraits4658*67e74705SXin Li static std::string getNodeLabel(const CFGBlock *Node, const CFG* Graph) {
4659*67e74705SXin Li
4660*67e74705SXin Li #ifndef NDEBUG
4661*67e74705SXin Li std::string OutSStr;
4662*67e74705SXin Li llvm::raw_string_ostream Out(OutSStr);
4663*67e74705SXin Li print_block(Out,Graph, *Node, *GraphHelper, false, false);
4664*67e74705SXin Li std::string& OutStr = Out.str();
4665*67e74705SXin Li
4666*67e74705SXin Li if (OutStr[0] == '\n') OutStr.erase(OutStr.begin());
4667*67e74705SXin Li
4668*67e74705SXin Li // Process string output to make it nicer...
4669*67e74705SXin Li for (unsigned i = 0; i != OutStr.length(); ++i)
4670*67e74705SXin Li if (OutStr[i] == '\n') { // Left justify
4671*67e74705SXin Li OutStr[i] = '\\';
4672*67e74705SXin Li OutStr.insert(OutStr.begin()+i+1, 'l');
4673*67e74705SXin Li }
4674*67e74705SXin Li
4675*67e74705SXin Li return OutStr;
4676*67e74705SXin Li #else
4677*67e74705SXin Li return "";
4678*67e74705SXin Li #endif
4679*67e74705SXin Li }
4680*67e74705SXin Li };
4681*67e74705SXin Li } // end namespace llvm
4682