clang  9.0.0svn
ExprEngine.cpp
Go to the documentation of this file.
1 //===- ExprEngine.cpp - Path-Sensitive Expression-Level Dataflow ----------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file defines a meta-engine for path-sensitive dataflow analysis that
10 // is built on GREngine, but provides the boilerplate to execute transfer
11 // functions and build the ExplodedGraph at the expression level.
12 //
13 //===----------------------------------------------------------------------===//
14 
17 #include "clang/AST/ASTContext.h"
18 #include "clang/AST/Decl.h"
19 #include "clang/AST/DeclBase.h"
20 #include "clang/AST/DeclCXX.h"
21 #include "clang/AST/DeclObjC.h"
22 #include "clang/AST/Expr.h"
23 #include "clang/AST/ExprCXX.h"
24 #include "clang/AST/ExprObjC.h"
25 #include "clang/AST/ParentMap.h"
27 #include "clang/AST/Stmt.h"
28 #include "clang/AST/StmtCXX.h"
29 #include "clang/AST/StmtObjC.h"
30 #include "clang/AST/Type.h"
32 #include "clang/Analysis/CFG.h"
37 #include "clang/Basic/LLVM.h"
42 #include "clang/Basic/Specifiers.h"
63 #include "llvm/ADT/APSInt.h"
64 #include "llvm/ADT/DenseMap.h"
65 #include "llvm/ADT/ImmutableMap.h"
66 #include "llvm/ADT/ImmutableSet.h"
67 #include "llvm/ADT/Optional.h"
68 #include "llvm/ADT/SmallVector.h"
69 #include "llvm/ADT/Statistic.h"
70 #include "llvm/Support/Casting.h"
71 #include "llvm/Support/Compiler.h"
72 #include "llvm/Support/DOTGraphTraits.h"
73 #include "llvm/Support/ErrorHandling.h"
74 #include "llvm/Support/GraphWriter.h"
75 #include "llvm/Support/SaveAndRestore.h"
76 #include "llvm/Support/raw_ostream.h"
77 #include <cassert>
78 #include <cstdint>
79 #include <memory>
80 #include <string>
81 #include <tuple>
82 #include <utility>
83 #include <vector>
84 
85 using namespace clang;
86 using namespace ento;
87 
88 #define DEBUG_TYPE "ExprEngine"
89 
90 STATISTIC(NumRemoveDeadBindings,
91  "The # of times RemoveDeadBindings is called");
92 STATISTIC(NumMaxBlockCountReached,
93  "The # of aborted paths due to reaching the maximum block count in "
94  "a top level function");
95 STATISTIC(NumMaxBlockCountReachedInInlined,
96  "The # of aborted paths due to reaching the maximum block count in "
97  "an inlined function");
98 STATISTIC(NumTimesRetriedWithoutInlining,
99  "The # of times we re-evaluated a call without inlining");
100 
101 //===----------------------------------------------------------------------===//
102 // Internal program state traits.
103 //===----------------------------------------------------------------------===//
104 
105 namespace {
106 
107 // When modeling a C++ constructor, for a variety of reasons we need to track
108 // the location of the object for the duration of its ConstructionContext.
109 // ObjectsUnderConstruction maps statements within the construction context
110 // to the object's location, so that on every such statement the location
111 // could have been retrieved.
112 
113 /// ConstructedObjectKey is used for being able to find the path-sensitive
114 /// memory region of a freshly constructed object while modeling the AST node
115 /// that syntactically represents the object that is being constructed.
116 /// Semantics of such nodes may sometimes require access to the region that's
117 /// not otherwise present in the program state, or to the very fact that
118 /// the construction context was present and contained references to these
119 /// AST nodes.
120 class ConstructedObjectKey {
121  typedef std::pair<ConstructionContextItem, const LocationContext *>
122  ConstructedObjectKeyImpl;
123 
124  const ConstructedObjectKeyImpl Impl;
125 
126  const void *getAnyASTNodePtr() const {
127  if (const Stmt *S = getItem().getStmtOrNull())
128  return S;
129  else
130  return getItem().getCXXCtorInitializer();
131  }
132 
133 public:
134  explicit ConstructedObjectKey(const ConstructionContextItem &Item,
135  const LocationContext *LC)
136  : Impl(Item, LC) {}
137 
138  const ConstructionContextItem &getItem() const { return Impl.first; }
139  const LocationContext *getLocationContext() const { return Impl.second; }
140 
141  ASTContext &getASTContext() const {
142  return getLocationContext()->getDecl()->getASTContext();
143  }
144 
145  void printJson(llvm::raw_ostream &Out, PrinterHelper *Helper,
146  PrintingPolicy &PP) const {
147  const Stmt *S = getItem().getStmtOrNull();
148  const CXXCtorInitializer *I = nullptr;
149  if (!S)
150  I = getItem().getCXXCtorInitializer();
151 
152  // IDs
153  Out << "\"lctx_id\": " << getLocationContext()->getID() << ", ";
154 
155  if (S)
156  Out << "\"stmt_id\": " << S->getID(getASTContext());
157  else
158  Out << "\"init_id\": " << I->getID(getASTContext());
159 
160  // Kind
161  Out << ", \"kind\": \"" << getItem().getKindAsString()
162  << "\", \"argument_index\": ";
163 
165  Out << getItem().getIndex();
166  else
167  Out << "null";
168 
169  // Pretty-print
170  Out << ", \"pretty\": ";
171 
172  if (S) {
173  S->printJson(Out, Helper, PP, /*AddQuotes=*/true);
174  } else {
175  Out << '\"' << I->getAnyMember()->getNameAsString() << '\"';
176  }
177  }
178 
179  void Profile(llvm::FoldingSetNodeID &ID) const {
180  ID.Add(Impl.first);
181  ID.AddPointer(Impl.second);
182  }
183 
184  bool operator==(const ConstructedObjectKey &RHS) const {
185  return Impl == RHS.Impl;
186  }
187 
188  bool operator<(const ConstructedObjectKey &RHS) const {
189  return Impl < RHS.Impl;
190  }
191 };
192 } // namespace
193 
194 typedef llvm::ImmutableMap<ConstructedObjectKey, SVal>
196 REGISTER_TRAIT_WITH_PROGRAMSTATE(ObjectsUnderConstruction,
198 
199 //===----------------------------------------------------------------------===//
200 // Engine construction and deletion.
201 //===----------------------------------------------------------------------===//
202 
203 static const char* TagProviderName = "ExprEngine";
204 
206  AnalysisManager &mgr,
207  SetOfConstDecls *VisitedCalleesIn,
209  InliningModes HowToInlineIn)
210  : CTU(CTU), AMgr(mgr),
211  AnalysisDeclContexts(mgr.getAnalysisDeclContextManager()),
212  Engine(*this, FS, mgr.getAnalyzerOptions()), G(Engine.getGraph()),
213  StateMgr(getContext(), mgr.getStoreManagerCreator(),
214  mgr.getConstraintManagerCreator(), G.getAllocator(),
215  this),
216  SymMgr(StateMgr.getSymbolManager()),
217  MRMgr(StateMgr.getRegionManager()),
218  svalBuilder(StateMgr.getSValBuilder()),
219  ObjCNoRet(mgr.getASTContext()),
220  BR(mgr, *this),
221  VisitedCallees(VisitedCalleesIn),
222  HowToInline(HowToInlineIn)
223  {
224  unsigned TrimInterval = mgr.options.GraphTrimInterval;
225  if (TrimInterval != 0) {
226  // Enable eager node reclamation when constructing the ExplodedGraph.
227  G.enableNodeReclamation(TrimInterval);
228  }
229 }
230 
232  BR.FlushReports();
233 }
234 
235 //===----------------------------------------------------------------------===//
236 // Utility methods.
237 //===----------------------------------------------------------------------===//
238 
240  ProgramStateRef state = StateMgr.getInitialState(InitLoc);
241  const Decl *D = InitLoc->getDecl();
242 
243  // Preconditions.
244  // FIXME: It would be nice if we had a more general mechanism to add
245  // such preconditions. Some day.
246  do {
247  if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
248  // Precondition: the first argument of 'main' is an integer guaranteed
249  // to be > 0.
250  const IdentifierInfo *II = FD->getIdentifier();
251  if (!II || !(II->getName() == "main" && FD->getNumParams() > 0))
252  break;
253 
254  const ParmVarDecl *PD = FD->getParamDecl(0);
255  QualType T = PD->getType();
256  const auto *BT = dyn_cast<BuiltinType>(T);
257  if (!BT || !BT->isInteger())
258  break;
259 
260  const MemRegion *R = state->getRegion(PD, InitLoc);
261  if (!R)
262  break;
263 
264  SVal V = state->getSVal(loc::MemRegionVal(R));
265  SVal Constraint_untested = evalBinOp(state, BO_GT, V,
266  svalBuilder.makeZeroVal(T),
267  svalBuilder.getConditionType());
268 
269  Optional<DefinedOrUnknownSVal> Constraint =
270  Constraint_untested.getAs<DefinedOrUnknownSVal>();
271 
272  if (!Constraint)
273  break;
274 
275  if (ProgramStateRef newState = state->assume(*Constraint, true))
276  state = newState;
277  }
278  break;
279  }
280  while (false);
281 
282  if (const auto *MD = dyn_cast<ObjCMethodDecl>(D)) {
283  // Precondition: 'self' is always non-null upon entry to an Objective-C
284  // method.
285  const ImplicitParamDecl *SelfD = MD->getSelfDecl();
286  const MemRegion *R = state->getRegion(SelfD, InitLoc);
287  SVal V = state->getSVal(loc::MemRegionVal(R));
288 
289  if (Optional<Loc> LV = V.getAs<Loc>()) {
290  // Assume that the pointer value in 'self' is non-null.
291  state = state->assume(*LV, true);
292  assert(state && "'self' cannot be null");
293  }
294  }
295 
296  if (const auto *MD = dyn_cast<CXXMethodDecl>(D)) {
297  if (!MD->isStatic()) {
298  // Precondition: 'this' is always non-null upon entry to the
299  // top-level function. This is our starting assumption for
300  // analyzing an "open" program.
301  const StackFrameContext *SFC = InitLoc->getStackFrame();
302  if (SFC->getParent() == nullptr) {
303  loc::MemRegionVal L = svalBuilder.getCXXThis(MD, SFC);
304  SVal V = state->getSVal(L);
305  if (Optional<Loc> LV = V.getAs<Loc>()) {
306  state = state->assume(*LV, true);
307  assert(state && "'this' cannot be null");
308  }
309  }
310  }
311  }
312 
313  return state;
314 }
315 
316 ProgramStateRef ExprEngine::createTemporaryRegionIfNeeded(
318  const Expr *InitWithAdjustments, const Expr *Result,
319  const SubRegion **OutRegionWithAdjustments) {
320  // FIXME: This function is a hack that works around the quirky AST
321  // we're often having with respect to C++ temporaries. If only we modelled
322  // the actual execution order of statements properly in the CFG,
323  // all the hassle with adjustments would not be necessary,
324  // and perhaps the whole function would be removed.
325  SVal InitValWithAdjustments = State->getSVal(InitWithAdjustments, LC);
326  if (!Result) {
327  // If we don't have an explicit result expression, we're in "if needed"
328  // mode. Only create a region if the current value is a NonLoc.
329  if (!InitValWithAdjustments.getAs<NonLoc>()) {
330  if (OutRegionWithAdjustments)
331  *OutRegionWithAdjustments = nullptr;
332  return State;
333  }
334  Result = InitWithAdjustments;
335  } else {
336  // We need to create a region no matter what. For sanity, make sure we don't
337  // try to stuff a Loc into a non-pointer temporary region.
338  assert(!InitValWithAdjustments.getAs<Loc>() ||
339  Loc::isLocType(Result->getType()) ||
340  Result->getType()->isMemberPointerType());
341  }
342 
343  ProgramStateManager &StateMgr = State->getStateManager();
344  MemRegionManager &MRMgr = StateMgr.getRegionManager();
345  StoreManager &StoreMgr = StateMgr.getStoreManager();
346 
347  // MaterializeTemporaryExpr may appear out of place, after a few field and
348  // base-class accesses have been made to the object, even though semantically
349  // it is the whole object that gets materialized and lifetime-extended.
350  //
351  // For example:
352  //
353  // `-MaterializeTemporaryExpr
354  // `-MemberExpr
355  // `-CXXTemporaryObjectExpr
356  //
357  // instead of the more natural
358  //
359  // `-MemberExpr
360  // `-MaterializeTemporaryExpr
361  // `-CXXTemporaryObjectExpr
362  //
363  // Use the usual methods for obtaining the expression of the base object,
364  // and record the adjustments that we need to make to obtain the sub-object
365  // that the whole expression 'Ex' refers to. This trick is usual,
366  // in the sense that CodeGen takes a similar route.
367 
370 
371  const Expr *Init = InitWithAdjustments->skipRValueSubobjectAdjustments(
372  CommaLHSs, Adjustments);
373 
374  // Take the region for Init, i.e. for the whole object. If we do not remember
375  // the region in which the object originally was constructed, come up with
376  // a new temporary region out of thin air and copy the contents of the object
377  // (which are currently present in the Environment, because Init is an rvalue)
378  // into that region. This is not correct, but it is better than nothing.
379  const TypedValueRegion *TR = nullptr;
380  if (const auto *MT = dyn_cast<MaterializeTemporaryExpr>(Result)) {
381  if (Optional<SVal> V = getObjectUnderConstruction(State, MT, LC)) {
382  State = finishObjectConstruction(State, MT, LC);
383  State = State->BindExpr(Result, LC, *V);
384  return State;
385  } else {
386  StorageDuration SD = MT->getStorageDuration();
387  // If this object is bound to a reference with static storage duration, we
388  // put it in a different region to prevent "address leakage" warnings.
389  if (SD == SD_Static || SD == SD_Thread) {
390  TR = MRMgr.getCXXStaticTempObjectRegion(Init);
391  } else {
392  TR = MRMgr.getCXXTempObjectRegion(Init, LC);
393  }
394  }
395  } else {
396  TR = MRMgr.getCXXTempObjectRegion(Init, LC);
397  }
398 
399  SVal Reg = loc::MemRegionVal(TR);
400  SVal BaseReg = Reg;
401 
402  // Make the necessary adjustments to obtain the sub-object.
403  for (auto I = Adjustments.rbegin(), E = Adjustments.rend(); I != E; ++I) {
404  const SubobjectAdjustment &Adj = *I;
405  switch (Adj.Kind) {
407  Reg = StoreMgr.evalDerivedToBase(Reg, Adj.DerivedToBase.BasePath);
408  break;
410  Reg = StoreMgr.getLValueField(Adj.Field, Reg);
411  break;
413  // FIXME: Unimplemented.
414  State = State->invalidateRegions(Reg, InitWithAdjustments,
415  currBldrCtx->blockCount(), LC, true,
416  nullptr, nullptr, nullptr);
417  return State;
418  }
419  }
420 
421  // What remains is to copy the value of the object to the new region.
422  // FIXME: In other words, what we should always do is copy value of the
423  // Init expression (which corresponds to the bigger object) to the whole
424  // temporary region TR. However, this value is often no longer present
425  // in the Environment. If it has disappeared, we instead invalidate TR.
426  // Still, what we can do is assign the value of expression Ex (which
427  // corresponds to the sub-object) to the TR's sub-region Reg. At least,
428  // values inside Reg would be correct.
429  SVal InitVal = State->getSVal(Init, LC);
430  if (InitVal.isUnknown()) {
431  InitVal = getSValBuilder().conjureSymbolVal(Result, LC, Init->getType(),
432  currBldrCtx->blockCount());
433  State = State->bindLoc(BaseReg.castAs<Loc>(), InitVal, LC, false);
434 
435  // Then we'd need to take the value that certainly exists and bind it
436  // over.
437  if (InitValWithAdjustments.isUnknown()) {
438  // Try to recover some path sensitivity in case we couldn't
439  // compute the value.
440  InitValWithAdjustments = getSValBuilder().conjureSymbolVal(
441  Result, LC, InitWithAdjustments->getType(),
442  currBldrCtx->blockCount());
443  }
444  State =
445  State->bindLoc(Reg.castAs<Loc>(), InitValWithAdjustments, LC, false);
446  } else {
447  State = State->bindLoc(BaseReg.castAs<Loc>(), InitVal, LC, false);
448  }
449 
450  // The result expression would now point to the correct sub-region of the
451  // newly created temporary region. Do this last in order to getSVal of Init
452  // correctly in case (Result == Init).
453  if (Result->isGLValue()) {
454  State = State->BindExpr(Result, LC, Reg);
455  } else {
456  State = State->BindExpr(Result, LC, InitValWithAdjustments);
457  }
458 
459  // Notify checkers once for two bindLoc()s.
460  State = processRegionChange(State, TR, LC);
461 
462  if (OutRegionWithAdjustments)
463  *OutRegionWithAdjustments = cast<SubRegion>(Reg.getAsRegion());
464  return State;
465 }
466 
468 ExprEngine::addObjectUnderConstruction(ProgramStateRef State,
469  const ConstructionContextItem &Item,
470  const LocationContext *LC, SVal V) {
471  ConstructedObjectKey Key(Item, LC->getStackFrame());
472  // FIXME: Currently the state might already contain the marker due to
473  // incorrect handling of temporaries bound to default parameters.
474  assert(!State->get<ObjectsUnderConstruction>(Key) ||
475  Key.getItem().getKind() ==
477  return State->set<ObjectsUnderConstruction>(Key, V);
478 }
479 
482  const ConstructionContextItem &Item,
483  const LocationContext *LC) {
484  ConstructedObjectKey Key(Item, LC->getStackFrame());
485  return Optional<SVal>::create(State->get<ObjectsUnderConstruction>(Key));
486 }
487 
489 ExprEngine::finishObjectConstruction(ProgramStateRef State,
490  const ConstructionContextItem &Item,
491  const LocationContext *LC) {
492  ConstructedObjectKey Key(Item, LC->getStackFrame());
493  assert(State->contains<ObjectsUnderConstruction>(Key));
494  return State->remove<ObjectsUnderConstruction>(Key);
495 }
496 
497 ProgramStateRef ExprEngine::elideDestructor(ProgramStateRef State,
498  const CXXBindTemporaryExpr *BTE,
499  const LocationContext *LC) {
500  ConstructedObjectKey Key({BTE, /*IsElided=*/true}, LC);
501  // FIXME: Currently the state might already contain the marker due to
502  // incorrect handling of temporaries bound to default parameters.
503  return State->set<ObjectsUnderConstruction>(Key, UnknownVal());
504 }
505 
507 ExprEngine::cleanupElidedDestructor(ProgramStateRef State,
508  const CXXBindTemporaryExpr *BTE,
509  const LocationContext *LC) {
510  ConstructedObjectKey Key({BTE, /*IsElided=*/true}, LC);
511  assert(State->contains<ObjectsUnderConstruction>(Key));
512  return State->remove<ObjectsUnderConstruction>(Key);
513 }
514 
515 bool ExprEngine::isDestructorElided(ProgramStateRef State,
516  const CXXBindTemporaryExpr *BTE,
517  const LocationContext *LC) {
518  ConstructedObjectKey Key({BTE, /*IsElided=*/true}, LC);
519  return State->contains<ObjectsUnderConstruction>(Key);
520 }
521 
522 bool ExprEngine::areAllObjectsFullyConstructed(ProgramStateRef State,
523  const LocationContext *FromLC,
524  const LocationContext *ToLC) {
525  const LocationContext *LC = FromLC;
526  while (LC != ToLC) {
527  assert(LC && "ToLC must be a parent of FromLC!");
528  for (auto I : State->get<ObjectsUnderConstruction>())
529  if (I.first.getLocationContext() == LC)
530  return false;
531 
532  LC = LC->getParent();
533  }
534  return true;
535 }
536 
537 
538 //===----------------------------------------------------------------------===//
539 // Top-level transfer function logic (Dispatcher).
540 //===----------------------------------------------------------------------===//
541 
542 /// evalAssume - Called by ConstraintManager. Used to call checker-specific
543 /// logic for handling assumptions on symbolic values.
545  SVal cond, bool assumption) {
546  return getCheckerManager().runCheckersForEvalAssume(state, cond, assumption);
547 }
548 
551  const InvalidatedSymbols *invalidated,
552  ArrayRef<const MemRegion *> Explicits,
554  const LocationContext *LCtx,
555  const CallEvent *Call) {
556  return getCheckerManager().runCheckersForRegionChanges(state, invalidated,
557  Explicits, Regions,
558  LCtx, Call);
559 }
560 
561 static void
563  const char *NL, const LocationContext *LCtx,
564  unsigned int Space = 0, bool IsDot = false) {
565  PrintingPolicy PP =
567 
568  ++Space;
569  bool HasItem = false;
570 
571  // Store the last key.
572  const ConstructedObjectKey *LastKey = nullptr;
573  for (const auto &I : State->get<ObjectsUnderConstruction>()) {
574  const ConstructedObjectKey &Key = I.first;
575  if (Key.getLocationContext() != LCtx)
576  continue;
577 
578  if (!HasItem) {
579  Out << "[" << NL;
580  HasItem = true;
581  }
582 
583  LastKey = &Key;
584  }
585 
586  for (const auto &I : State->get<ObjectsUnderConstruction>()) {
587  const ConstructedObjectKey &Key = I.first;
588  SVal Value = I.second;
589  if (Key.getLocationContext() != LCtx)
590  continue;
591 
592  Indent(Out, Space, IsDot) << "{ ";
593  Key.printJson(Out, nullptr, PP);
594  Out << ", \"value\": \"" << Value << "\" }";
595 
596  if (&Key != LastKey)
597  Out << ',';
598  Out << NL;
599  }
600 
601  if (HasItem)
602  Indent(Out, --Space, IsDot) << ']'; // End of "location_context".
603  else {
604  Out << "null ";
605  }
606 }
607 
608 void ExprEngine::printJson(raw_ostream &Out, ProgramStateRef State,
609  const LocationContext *LCtx, const char *NL,
610  unsigned int Space, bool IsDot) const {
611  Indent(Out, Space, IsDot) << "\"constructing_objects\": ";
612 
613  if (LCtx && !State->get<ObjectsUnderConstruction>().isEmpty()) {
614  ++Space;
615  Out << '[' << NL;
616  LCtx->printJson(Out, NL, Space, IsDot, [&](const LocationContext *LC) {
617  printObjectsUnderConstructionJson(Out, State, NL, LC, Space, IsDot);
618  });
619 
620  --Space;
621  Indent(Out, Space, IsDot) << "]," << NL; // End of "constructing_objects".
622  } else {
623  Out << "null," << NL;
624  }
625 
626  getCheckerManager().runCheckersForPrintStateJson(Out, State, NL, Space,
627  IsDot);
628 }
629 
632 }
633 
635  unsigned StmtIdx, NodeBuilderContext *Ctx) {
637  currStmtIdx = StmtIdx;
638  currBldrCtx = Ctx;
639 
640  switch (E.getKind()) {
644  ProcessStmt(E.castAs<CFGStmt>().getStmt(), Pred);
645  return;
648  return;
651  Pred);
652  return;
659  return;
662  return;
666  return;
667  }
668 }
669 
670 static bool shouldRemoveDeadBindings(AnalysisManager &AMgr,
671  const Stmt *S,
672  const ExplodedNode *Pred,
673  const LocationContext *LC) {
674  // Are we never purging state values?
675  if (AMgr.options.AnalysisPurgeOpt == PurgeNone)
676  return false;
677 
678  // Is this the beginning of a basic block?
679  if (Pred->getLocation().getAs<BlockEntrance>())
680  return true;
681 
682  // Is this on a non-expression?
683  if (!isa<Expr>(S))
684  return true;
685 
686  // Run before processing a call.
687  if (CallEvent::isCallStmt(S))
688  return true;
689 
690  // Is this an expression that is consumed by another expression? If so,
691  // postpone cleaning out the state.
693  return !PM.isConsumedExpr(cast<Expr>(S));
694 }
695 
697  const Stmt *ReferenceStmt,
698  const LocationContext *LC,
699  const Stmt *DiagnosticStmt,
700  ProgramPoint::Kind K) {
702  ReferenceStmt == nullptr || isa<ReturnStmt>(ReferenceStmt))
703  && "PostStmt is not generally supported by the SymbolReaper yet");
704  assert(LC && "Must pass the current (or expiring) LocationContext");
705 
706  if (!DiagnosticStmt) {
707  DiagnosticStmt = ReferenceStmt;
708  assert(DiagnosticStmt && "Required for clearing a LocationContext");
709  }
710 
711  NumRemoveDeadBindings++;
712  ProgramStateRef CleanedState = Pred->getState();
713 
714  // LC is the location context being destroyed, but SymbolReaper wants a
715  // location context that is still live. (If this is the top-level stack
716  // frame, this will be null.)
717  if (!ReferenceStmt) {
719  "Use PostStmtPurgeDeadSymbolsKind for clearing a LocationContext");
720  LC = LC->getParent();
721  }
722 
723  const StackFrameContext *SFC = LC ? LC->getStackFrame() : nullptr;
724  SymbolReaper SymReaper(SFC, ReferenceStmt, SymMgr, getStoreManager());
725 
726  for (auto I : CleanedState->get<ObjectsUnderConstruction>()) {
727  if (SymbolRef Sym = I.second.getAsSymbol())
728  SymReaper.markLive(Sym);
729  if (const MemRegion *MR = I.second.getAsRegion())
730  SymReaper.markLive(MR);
731  }
732 
733  getCheckerManager().runCheckersForLiveSymbols(CleanedState, SymReaper);
734 
735  // Create a state in which dead bindings are removed from the environment
736  // and the store. TODO: The function should just return new env and store,
737  // not a new state.
738  CleanedState = StateMgr.removeDeadBindings(CleanedState, SFC, SymReaper);
739 
740  // Process any special transfer function for dead symbols.
741  // A tag to track convenience transitions, which can be removed at cleanup.
742  static SimpleProgramPointTag cleanupTag(TagProviderName, "Clean Node");
743  // Call checkers with the non-cleaned state so that they could query the
744  // values of the soon to be dead symbols.
745  ExplodedNodeSet CheckedSet;
746  getCheckerManager().runCheckersForDeadSymbols(CheckedSet, Pred, SymReaper,
747  DiagnosticStmt, *this, K);
748 
749  // For each node in CheckedSet, generate CleanedNodes that have the
750  // environment, the store, and the constraints cleaned up but have the
751  // user-supplied states as the predecessors.
752  StmtNodeBuilder Bldr(CheckedSet, Out, *currBldrCtx);
753  for (const auto I : CheckedSet) {
754  ProgramStateRef CheckerState = I->getState();
755 
756  // The constraint manager has not been cleaned up yet, so clean up now.
757  CheckerState =
758  getConstraintManager().removeDeadBindings(CheckerState, SymReaper);
759 
760  assert(StateMgr.haveEqualEnvironments(CheckerState, Pred->getState()) &&
761  "Checkers are not allowed to modify the Environment as a part of "
762  "checkDeadSymbols processing.");
763  assert(StateMgr.haveEqualStores(CheckerState, Pred->getState()) &&
764  "Checkers are not allowed to modify the Store as a part of "
765  "checkDeadSymbols processing.");
766 
767  // Create a state based on CleanedState with CheckerState GDM and
768  // generate a transition to that state.
769  ProgramStateRef CleanedCheckerSt =
770  StateMgr.getPersistentStateWithGDM(CleanedState, CheckerState);
771  Bldr.generateNode(DiagnosticStmt, I, CleanedCheckerSt, &cleanupTag, K);
772  }
773 }
774 
775 void ExprEngine::ProcessStmt(const Stmt *currStmt, ExplodedNode *Pred) {
776  // Reclaim any unnecessary nodes in the ExplodedGraph.
778 
779  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
780  currStmt->getBeginLoc(),
781  "Error evaluating statement");
782 
783  // Remove dead bindings and symbols.
784  ExplodedNodeSet CleanedStates;
785  if (shouldRemoveDeadBindings(AMgr, currStmt, Pred,
786  Pred->getLocationContext())) {
787  removeDead(Pred, CleanedStates, currStmt,
788  Pred->getLocationContext());
789  } else
790  CleanedStates.Add(Pred);
791 
792  // Visit the statement.
793  ExplodedNodeSet Dst;
794  for (const auto I : CleanedStates) {
795  ExplodedNodeSet DstI;
796  // Visit the statement.
797  Visit(currStmt, I, DstI);
798  Dst.insert(DstI);
799  }
800 
801  // Enqueue the new nodes onto the work list.
802  Engine.enqueue(Dst, currBldrCtx->getBlock(), currStmtIdx);
803 }
804 
806  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
807  S->getBeginLoc(),
808  "Error evaluating end of the loop");
809  ExplodedNodeSet Dst;
810  Dst.Add(Pred);
811  NodeBuilder Bldr(Pred, Dst, *currBldrCtx);
812  ProgramStateRef NewState = Pred->getState();
813 
814  if(AMgr.options.ShouldUnrollLoops)
815  NewState = processLoopEnd(S, NewState);
816 
817  LoopExit PP(S, Pred->getLocationContext());
818  Bldr.generateNode(PP, NewState, Pred);
819  // Enqueue the new nodes onto the work list.
820  Engine.enqueue(Dst, currBldrCtx->getBlock(), currStmtIdx);
821 }
822 
824  ExplodedNode *Pred) {
825  const CXXCtorInitializer *BMI = CFGInit.getInitializer();
826  const Expr *Init = BMI->getInit()->IgnoreImplicit();
827  const LocationContext *LC = Pred->getLocationContext();
828 
829  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
830  BMI->getSourceLocation(),
831  "Error evaluating initializer");
832 
833  // We don't clean up dead bindings here.
834  const auto *stackFrame = cast<StackFrameContext>(Pred->getLocationContext());
835  const auto *decl = cast<CXXConstructorDecl>(stackFrame->getDecl());
836 
837  ProgramStateRef State = Pred->getState();
838  SVal thisVal = State->getSVal(svalBuilder.getCXXThis(decl, stackFrame));
839 
840  ExplodedNodeSet Tmp;
841  SVal FieldLoc;
842 
843  // Evaluate the initializer, if necessary
844  if (BMI->isAnyMemberInitializer()) {
845  // Constructors build the object directly in the field,
846  // but non-objects must be copied in from the initializer.
847  if (getObjectUnderConstruction(State, BMI, LC)) {
848  // The field was directly constructed, so there is no need to bind.
849  // But we still need to stop tracking the object under construction.
850  State = finishObjectConstruction(State, BMI, LC);
851  NodeBuilder Bldr(Pred, Tmp, *currBldrCtx);
852  PostStore PS(Init, LC, /*Loc*/ nullptr, /*tag*/ nullptr);
853  Bldr.generateNode(PS, State, Pred);
854  } else {
855  const ValueDecl *Field;
856  if (BMI->isIndirectMemberInitializer()) {
857  Field = BMI->getIndirectMember();
858  FieldLoc = State->getLValue(BMI->getIndirectMember(), thisVal);
859  } else {
860  Field = BMI->getMember();
861  FieldLoc = State->getLValue(BMI->getMember(), thisVal);
862  }
863 
864  SVal InitVal;
865  if (Init->getType()->isArrayType()) {
866  // Handle arrays of trivial type. We can represent this with a
867  // primitive load/copy from the base array region.
868  const ArraySubscriptExpr *ASE;
869  while ((ASE = dyn_cast<ArraySubscriptExpr>(Init)))
870  Init = ASE->getBase()->IgnoreImplicit();
871 
872  SVal LValue = State->getSVal(Init, stackFrame);
873  if (!Field->getType()->isReferenceType())
874  if (Optional<Loc> LValueLoc = LValue.getAs<Loc>())
875  InitVal = State->getSVal(*LValueLoc);
876 
877  // If we fail to get the value for some reason, use a symbolic value.
878  if (InitVal.isUnknownOrUndef()) {
879  SValBuilder &SVB = getSValBuilder();
880  InitVal = SVB.conjureSymbolVal(BMI->getInit(), stackFrame,
881  Field->getType(),
882  currBldrCtx->blockCount());
883  }
884  } else {
885  InitVal = State->getSVal(BMI->getInit(), stackFrame);
886  }
887 
888  PostInitializer PP(BMI, FieldLoc.getAsRegion(), stackFrame);
889  evalBind(Tmp, Init, Pred, FieldLoc, InitVal, /*isInit=*/true, &PP);
890  }
891  } else {
892  assert(BMI->isBaseInitializer() || BMI->isDelegatingInitializer());
893  Tmp.insert(Pred);
894  // We already did all the work when visiting the CXXConstructExpr.
895  }
896 
897  // Construct PostInitializer nodes whether the state changed or not,
898  // so that the diagnostics don't get confused.
899  PostInitializer PP(BMI, FieldLoc.getAsRegion(), stackFrame);
900  ExplodedNodeSet Dst;
901  NodeBuilder Bldr(Tmp, Dst, *currBldrCtx);
902  for (const auto I : Tmp) {
903  ProgramStateRef State = I->getState();
904  Bldr.generateNode(PP, State, I);
905  }
906 
907  // Enqueue the new nodes onto the work list.
908  Engine.enqueue(Dst, currBldrCtx->getBlock(), currStmtIdx);
909 }
910 
912  ExplodedNode *Pred) {
913  ExplodedNodeSet Dst;
914  switch (D.getKind()) {
917  break;
919  ProcessBaseDtor(D.castAs<CFGBaseDtor>(), Pred, Dst);
920  break;
922  ProcessMemberDtor(D.castAs<CFGMemberDtor>(), Pred, Dst);
923  break;
926  break;
928  ProcessDeleteDtor(D.castAs<CFGDeleteDtor>(), Pred, Dst);
929  break;
930  default:
931  llvm_unreachable("Unexpected dtor kind.");
932  }
933 
934  // Enqueue the new nodes onto the work list.
935  Engine.enqueue(Dst, currBldrCtx->getBlock(), currStmtIdx);
936 }
937 
939  ExplodedNode *Pred) {
940  ExplodedNodeSet Dst;
942  AnalyzerOptions &Opts = AMgr.options;
943  // TODO: We're not evaluating allocators for all cases just yet as
944  // we're not handling the return value correctly, which causes false
945  // positives when the alpha.cplusplus.NewDeleteLeaks check is on.
946  if (Opts.MayInlineCXXAllocator)
947  VisitCXXNewAllocatorCall(NE, Pred, Dst);
948  else {
949  NodeBuilder Bldr(Pred, Dst, *currBldrCtx);
950  const LocationContext *LCtx = Pred->getLocationContext();
951  PostImplicitCall PP(NE->getOperatorNew(), NE->getBeginLoc(), LCtx);
952  Bldr.generateNode(PP, Pred->getState(), Pred);
953  }
954  Engine.enqueue(Dst, currBldrCtx->getBlock(), currStmtIdx);
955 }
956 
958  ExplodedNode *Pred,
959  ExplodedNodeSet &Dst) {
960  const VarDecl *varDecl = Dtor.getVarDecl();
961  QualType varType = varDecl->getType();
962 
963  ProgramStateRef state = Pred->getState();
964  SVal dest = state->getLValue(varDecl, Pred->getLocationContext());
965  const MemRegion *Region = dest.castAs<loc::MemRegionVal>().getRegion();
966 
967  if (varType->isReferenceType()) {
968  const MemRegion *ValueRegion = state->getSVal(Region).getAsRegion();
969  if (!ValueRegion) {
970  // FIXME: This should not happen. The language guarantees a presence
971  // of a valid initializer here, so the reference shall not be undefined.
972  // It seems that we're calling destructors over variables that
973  // were not initialized yet.
974  return;
975  }
976  Region = ValueRegion->getBaseRegion();
977  varType = cast<TypedValueRegion>(Region)->getValueType();
978  }
979 
980  // FIXME: We need to run the same destructor on every element of the array.
981  // This workaround will just run the first destructor (which will still
982  // invalidate the entire array).
983  EvalCallOptions CallOpts;
984  Region = makeZeroElementRegion(state, loc::MemRegionVal(Region), varType,
985  CallOpts.IsArrayCtorOrDtor).getAsRegion();
986 
987  VisitCXXDestructor(varType, Region, Dtor.getTriggerStmt(), /*IsBase=*/ false,
988  Pred, Dst, CallOpts);
989 }
990 
992  ExplodedNode *Pred,
993  ExplodedNodeSet &Dst) {
994  ProgramStateRef State = Pred->getState();
995  const LocationContext *LCtx = Pred->getLocationContext();
996  const CXXDeleteExpr *DE = Dtor.getDeleteExpr();
997  const Stmt *Arg = DE->getArgument();
998  QualType DTy = DE->getDestroyedType();
999  SVal ArgVal = State->getSVal(Arg, LCtx);
1000 
1001  // If the argument to delete is known to be a null value,
1002  // don't run destructor.
1003  if (State->isNull(ArgVal).isConstrainedTrue()) {
1004  QualType BTy = getContext().getBaseElementType(DTy);
1005  const CXXRecordDecl *RD = BTy->getAsCXXRecordDecl();
1006  const CXXDestructorDecl *Dtor = RD->getDestructor();
1007 
1008  PostImplicitCall PP(Dtor, DE->getBeginLoc(), LCtx);
1009  NodeBuilder Bldr(Pred, Dst, *currBldrCtx);
1010  Bldr.generateNode(PP, Pred->getState(), Pred);
1011  return;
1012  }
1013 
1014  EvalCallOptions CallOpts;
1015  const MemRegion *ArgR = ArgVal.getAsRegion();
1016  if (DE->isArrayForm()) {
1017  // FIXME: We need to run the same destructor on every element of the array.
1018  // This workaround will just run the first destructor (which will still
1019  // invalidate the entire array).
1020  CallOpts.IsArrayCtorOrDtor = true;
1021  // Yes, it may even be a multi-dimensional array.
1022  while (const auto *AT = getContext().getAsArrayType(DTy))
1023  DTy = AT->getElementType();
1024  if (ArgR)
1025  ArgR = getStoreManager().GetElementZeroRegion(cast<SubRegion>(ArgR), DTy);
1026  }
1027 
1028  VisitCXXDestructor(DTy, ArgR, DE, /*IsBase=*/false, Pred, Dst, CallOpts);
1029 }
1030 
1032  ExplodedNode *Pred, ExplodedNodeSet &Dst) {
1033  const LocationContext *LCtx = Pred->getLocationContext();
1034 
1035  const auto *CurDtor = cast<CXXDestructorDecl>(LCtx->getDecl());
1036  Loc ThisPtr = getSValBuilder().getCXXThis(CurDtor,
1037  LCtx->getStackFrame());
1038  SVal ThisVal = Pred->getState()->getSVal(ThisPtr);
1039 
1040  // Create the base object region.
1041  const CXXBaseSpecifier *Base = D.getBaseSpecifier();
1042  QualType BaseTy = Base->getType();
1043  SVal BaseVal = getStoreManager().evalDerivedToBase(ThisVal, BaseTy,
1044  Base->isVirtual());
1045 
1047  CurDtor->getBody(), /*IsBase=*/ true, Pred, Dst, {});
1048 }
1049 
1051  ExplodedNode *Pred, ExplodedNodeSet &Dst) {
1052  const FieldDecl *Member = D.getFieldDecl();
1053  QualType T = Member->getType();
1054  ProgramStateRef State = Pred->getState();
1055  const LocationContext *LCtx = Pred->getLocationContext();
1056 
1057  const auto *CurDtor = cast<CXXDestructorDecl>(LCtx->getDecl());
1058  Loc ThisVal = getSValBuilder().getCXXThis(CurDtor,
1059  LCtx->getStackFrame());
1060  SVal FieldVal =
1061  State->getLValue(Member, State->getSVal(ThisVal).castAs<Loc>());
1062 
1063  // FIXME: We need to run the same destructor on every element of the array.
1064  // This workaround will just run the first destructor (which will still
1065  // invalidate the entire array).
1066  EvalCallOptions CallOpts;
1067  FieldVal = makeZeroElementRegion(State, FieldVal, T,
1068  CallOpts.IsArrayCtorOrDtor);
1069 
1071  CurDtor->getBody(), /*IsBase=*/false, Pred, Dst, CallOpts);
1072 }
1073 
1075  ExplodedNode *Pred,
1076  ExplodedNodeSet &Dst) {
1077  const CXXBindTemporaryExpr *BTE = D.getBindTemporaryExpr();
1078  ProgramStateRef State = Pred->getState();
1079  const LocationContext *LC = Pred->getLocationContext();
1080  const MemRegion *MR = nullptr;
1081 
1082  if (Optional<SVal> V =
1084  Pred->getLocationContext())) {
1085  // FIXME: Currently we insert temporary destructors for default parameters,
1086  // but we don't insert the constructors, so the entry in
1087  // ObjectsUnderConstruction may be missing.
1088  State = finishObjectConstruction(State, D.getBindTemporaryExpr(),
1089  Pred->getLocationContext());
1090  MR = V->getAsRegion();
1091  }
1092 
1093  // If copy elision has occurred, and the constructor corresponding to the
1094  // destructor was elided, we need to skip the destructor as well.
1095  if (isDestructorElided(State, BTE, LC)) {
1096  State = cleanupElidedDestructor(State, BTE, LC);
1097  NodeBuilder Bldr(Pred, Dst, *currBldrCtx);
1100  Pred->getLocationContext());
1101  Bldr.generateNode(PP, State, Pred);
1102  return;
1103  }
1104 
1105  ExplodedNodeSet CleanDtorState;
1106  StmtNodeBuilder StmtBldr(Pred, CleanDtorState, *currBldrCtx);
1107  StmtBldr.generateNode(D.getBindTemporaryExpr(), Pred, State);
1108 
1110  // FIXME: Currently CleanDtorState can be empty here due to temporaries being
1111  // bound to default parameters.
1112  assert(CleanDtorState.size() <= 1);
1113  ExplodedNode *CleanPred =
1114  CleanDtorState.empty() ? Pred : *CleanDtorState.begin();
1115 
1116  EvalCallOptions CallOpts;
1117  CallOpts.IsTemporaryCtorOrDtor = true;
1118  if (!MR) {
1120 
1121  // If we have no MR, we still need to unwrap the array to avoid destroying
1122  // the whole array at once. Regardless, we'd eventually need to model array
1123  // destructors properly, element-by-element.
1124  while (const ArrayType *AT = getContext().getAsArrayType(T)) {
1125  T = AT->getElementType();
1126  CallOpts.IsArrayCtorOrDtor = true;
1127  }
1128  } else {
1129  // We'd eventually need to makeZeroElementRegion() trick here,
1130  // but for now we don't have the respective construction contexts,
1131  // so MR would always be null in this case. Do nothing for now.
1132  }
1134  /*IsBase=*/false, CleanPred, Dst, CallOpts);
1135 }
1136 
1138  NodeBuilderContext &BldCtx,
1139  ExplodedNode *Pred,
1140  ExplodedNodeSet &Dst,
1141  const CFGBlock *DstT,
1142  const CFGBlock *DstF) {
1143  BranchNodeBuilder TempDtorBuilder(Pred, Dst, BldCtx, DstT, DstF);
1144  ProgramStateRef State = Pred->getState();
1145  const LocationContext *LC = Pred->getLocationContext();
1146  if (getObjectUnderConstruction(State, BTE, LC)) {
1147  TempDtorBuilder.markInfeasible(false);
1148  TempDtorBuilder.generateNode(State, true, Pred);
1149  } else {
1150  TempDtorBuilder.markInfeasible(true);
1151  TempDtorBuilder.generateNode(State, false, Pred);
1152  }
1153 }
1154 
1156  ExplodedNodeSet &PreVisit,
1157  ExplodedNodeSet &Dst) {
1158  // This is a fallback solution in case we didn't have a construction
1159  // context when we were constructing the temporary. Otherwise the map should
1160  // have been populated there.
1161  if (!getAnalysisManager().options.ShouldIncludeTemporaryDtorsInCFG) {
1162  // In case we don't have temporary destructors in the CFG, do not mark
1163  // the initialization - we would otherwise never clean it up.
1164  Dst = PreVisit;
1165  return;
1166  }
1167  StmtNodeBuilder StmtBldr(PreVisit, Dst, *currBldrCtx);
1168  for (ExplodedNode *Node : PreVisit) {
1169  ProgramStateRef State = Node->getState();
1170  const LocationContext *LC = Node->getLocationContext();
1171  if (!getObjectUnderConstruction(State, BTE, LC)) {
1172  // FIXME: Currently the state might also already contain the marker due to
1173  // incorrect handling of temporaries bound to default parameters; for
1174  // those, we currently skip the CXXBindTemporaryExpr but rely on adding
1175  // temporary destructor nodes.
1176  State = addObjectUnderConstruction(State, BTE, LC, UnknownVal());
1177  }
1178  StmtBldr.generateNode(BTE, Node, State);
1179  }
1180 }
1181 
1183  PointerEscapeKind K) const {
1184  class CollectReachableSymbolsCallback final : public SymbolVisitor {
1185  InvalidatedSymbols Symbols;
1186 
1187  public:
1188  explicit CollectReachableSymbolsCallback(ProgramStateRef) {}
1189 
1190  const InvalidatedSymbols &getSymbols() const { return Symbols; }
1191 
1192  bool VisitSymbol(SymbolRef Sym) override {
1193  Symbols.insert(Sym);
1194  return true;
1195  }
1196  };
1197 
1198  const CollectReachableSymbolsCallback &Scanner =
1199  State->scanReachableSymbols<CollectReachableSymbolsCallback>(V);
1201  State, Scanner.getSymbols(), /*CallEvent*/ nullptr, K, nullptr);
1202 }
1203 
1204 void ExprEngine::Visit(const Stmt *S, ExplodedNode *Pred,
1205  ExplodedNodeSet &DstTop) {
1206  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
1207  S->getBeginLoc(), "Error evaluating statement");
1208  ExplodedNodeSet Dst;
1209  StmtNodeBuilder Bldr(Pred, DstTop, *currBldrCtx);
1210 
1211  assert(!isa<Expr>(S) || S == cast<Expr>(S)->IgnoreParens());
1212 
1213  switch (S->getStmtClass()) {
1214  // C++, OpenMP and ARC stuff we don't support yet.
1215  case Expr::ObjCIndirectCopyRestoreExprClass:
1216  case Stmt::CXXDependentScopeMemberExprClass:
1217  case Stmt::CXXInheritedCtorInitExprClass:
1218  case Stmt::CXXTryStmtClass:
1219  case Stmt::CXXTypeidExprClass:
1220  case Stmt::CXXUuidofExprClass:
1221  case Stmt::CXXFoldExprClass:
1222  case Stmt::MSPropertyRefExprClass:
1223  case Stmt::MSPropertySubscriptExprClass:
1224  case Stmt::CXXUnresolvedConstructExprClass:
1225  case Stmt::DependentScopeDeclRefExprClass:
1226  case Stmt::ArrayTypeTraitExprClass:
1227  case Stmt::ExpressionTraitExprClass:
1228  case Stmt::UnresolvedLookupExprClass:
1229  case Stmt::UnresolvedMemberExprClass:
1230  case Stmt::TypoExprClass:
1231  case Stmt::CXXNoexceptExprClass:
1232  case Stmt::PackExpansionExprClass:
1233  case Stmt::SubstNonTypeTemplateParmPackExprClass:
1234  case Stmt::FunctionParmPackExprClass:
1235  case Stmt::CoroutineBodyStmtClass:
1236  case Stmt::CoawaitExprClass:
1237  case Stmt::DependentCoawaitExprClass:
1238  case Stmt::CoreturnStmtClass:
1239  case Stmt::CoyieldExprClass:
1240  case Stmt::SEHTryStmtClass:
1241  case Stmt::SEHExceptStmtClass:
1242  case Stmt::SEHLeaveStmtClass:
1243  case Stmt::SEHFinallyStmtClass:
1244  case Stmt::OMPParallelDirectiveClass:
1245  case Stmt::OMPSimdDirectiveClass:
1246  case Stmt::OMPForDirectiveClass:
1247  case Stmt::OMPForSimdDirectiveClass:
1248  case Stmt::OMPSectionsDirectiveClass:
1249  case Stmt::OMPSectionDirectiveClass:
1250  case Stmt::OMPSingleDirectiveClass:
1251  case Stmt::OMPMasterDirectiveClass:
1252  case Stmt::OMPCriticalDirectiveClass:
1253  case Stmt::OMPParallelForDirectiveClass:
1254  case Stmt::OMPParallelForSimdDirectiveClass:
1255  case Stmt::OMPParallelSectionsDirectiveClass:
1256  case Stmt::OMPTaskDirectiveClass:
1257  case Stmt::OMPTaskyieldDirectiveClass:
1258  case Stmt::OMPBarrierDirectiveClass:
1259  case Stmt::OMPTaskwaitDirectiveClass:
1260  case Stmt::OMPTaskgroupDirectiveClass:
1261  case Stmt::OMPFlushDirectiveClass:
1262  case Stmt::OMPOrderedDirectiveClass:
1263  case Stmt::OMPAtomicDirectiveClass:
1264  case Stmt::OMPTargetDirectiveClass:
1265  case Stmt::OMPTargetDataDirectiveClass:
1266  case Stmt::OMPTargetEnterDataDirectiveClass:
1267  case Stmt::OMPTargetExitDataDirectiveClass:
1268  case Stmt::OMPTargetParallelDirectiveClass:
1269  case Stmt::OMPTargetParallelForDirectiveClass:
1270  case Stmt::OMPTargetUpdateDirectiveClass:
1271  case Stmt::OMPTeamsDirectiveClass:
1272  case Stmt::OMPCancellationPointDirectiveClass:
1273  case Stmt::OMPCancelDirectiveClass:
1274  case Stmt::OMPTaskLoopDirectiveClass:
1275  case Stmt::OMPTaskLoopSimdDirectiveClass:
1276  case Stmt::OMPDistributeDirectiveClass:
1277  case Stmt::OMPDistributeParallelForDirectiveClass:
1278  case Stmt::OMPDistributeParallelForSimdDirectiveClass:
1279  case Stmt::OMPDistributeSimdDirectiveClass:
1280  case Stmt::OMPTargetParallelForSimdDirectiveClass:
1281  case Stmt::OMPTargetSimdDirectiveClass:
1282  case Stmt::OMPTeamsDistributeDirectiveClass:
1283  case Stmt::OMPTeamsDistributeSimdDirectiveClass:
1284  case Stmt::OMPTeamsDistributeParallelForSimdDirectiveClass:
1285  case Stmt::OMPTeamsDistributeParallelForDirectiveClass:
1286  case Stmt::OMPTargetTeamsDirectiveClass:
1287  case Stmt::OMPTargetTeamsDistributeDirectiveClass:
1288  case Stmt::OMPTargetTeamsDistributeParallelForDirectiveClass:
1289  case Stmt::OMPTargetTeamsDistributeParallelForSimdDirectiveClass:
1290  case Stmt::OMPTargetTeamsDistributeSimdDirectiveClass:
1291  case Stmt::CapturedStmtClass: {
1292  const ExplodedNode *node = Bldr.generateSink(S, Pred, Pred->getState());
1293  Engine.addAbortedBlock(node, currBldrCtx->getBlock());
1294  break;
1295  }
1296 
1297  case Stmt::ParenExprClass:
1298  llvm_unreachable("ParenExprs already handled.");
1299  case Stmt::GenericSelectionExprClass:
1300  llvm_unreachable("GenericSelectionExprs already handled.");
1301  // Cases that should never be evaluated simply because they shouldn't
1302  // appear in the CFG.
1303  case Stmt::BreakStmtClass:
1304  case Stmt::CaseStmtClass:
1305  case Stmt::CompoundStmtClass:
1306  case Stmt::ContinueStmtClass:
1307  case Stmt::CXXForRangeStmtClass:
1308  case Stmt::DefaultStmtClass:
1309  case Stmt::DoStmtClass:
1310  case Stmt::ForStmtClass:
1311  case Stmt::GotoStmtClass:
1312  case Stmt::IfStmtClass:
1313  case Stmt::IndirectGotoStmtClass:
1314  case Stmt::LabelStmtClass:
1315  case Stmt::NoStmtClass:
1316  case Stmt::NullStmtClass:
1317  case Stmt::SwitchStmtClass:
1318  case Stmt::WhileStmtClass:
1319  case Expr::MSDependentExistsStmtClass:
1320  llvm_unreachable("Stmt should not be in analyzer evaluation loop");
1321 
1322  case Stmt::ObjCSubscriptRefExprClass:
1323  case Stmt::ObjCPropertyRefExprClass:
1324  llvm_unreachable("These are handled by PseudoObjectExpr");
1325 
1326  case Stmt::GNUNullExprClass: {
1327  // GNU __null is a pointer-width integer, not an actual pointer.
1328  ProgramStateRef state = Pred->getState();
1329  state = state->BindExpr(S, Pred->getLocationContext(),
1330  svalBuilder.makeIntValWithPtrWidth(0, false));
1331  Bldr.generateNode(S, Pred, state);
1332  break;
1333  }
1334 
1335  case Stmt::ObjCAtSynchronizedStmtClass:
1336  Bldr.takeNodes(Pred);
1337  VisitObjCAtSynchronizedStmt(cast<ObjCAtSynchronizedStmt>(S), Pred, Dst);
1338  Bldr.addNodes(Dst);
1339  break;
1340 
1341  case Expr::ConstantExprClass:
1342  case Stmt::ExprWithCleanupsClass:
1343  // Handled due to fully linearised CFG.
1344  break;
1345 
1346  case Stmt::CXXBindTemporaryExprClass: {
1347  Bldr.takeNodes(Pred);
1348  ExplodedNodeSet PreVisit;
1349  getCheckerManager().runCheckersForPreStmt(PreVisit, Pred, S, *this);
1350  ExplodedNodeSet Next;
1351  VisitCXXBindTemporaryExpr(cast<CXXBindTemporaryExpr>(S), PreVisit, Next);
1352  getCheckerManager().runCheckersForPostStmt(Dst, Next, S, *this);
1353  Bldr.addNodes(Dst);
1354  break;
1355  }
1356 
1357  // Cases not handled yet; but will handle some day.
1358  case Stmt::DesignatedInitExprClass:
1359  case Stmt::DesignatedInitUpdateExprClass:
1360  case Stmt::ArrayInitLoopExprClass:
1361  case Stmt::ArrayInitIndexExprClass:
1362  case Stmt::ExtVectorElementExprClass:
1363  case Stmt::ImaginaryLiteralClass:
1364  case Stmt::ObjCAtCatchStmtClass:
1365  case Stmt::ObjCAtFinallyStmtClass:
1366  case Stmt::ObjCAtTryStmtClass:
1367  case Stmt::ObjCAutoreleasePoolStmtClass:
1368  case Stmt::ObjCEncodeExprClass:
1369  case Stmt::ObjCIsaExprClass:
1370  case Stmt::ObjCProtocolExprClass:
1371  case Stmt::ObjCSelectorExprClass:
1372  case Stmt::ParenListExprClass:
1373  case Stmt::ShuffleVectorExprClass:
1374  case Stmt::ConvertVectorExprClass:
1375  case Stmt::VAArgExprClass:
1376  case Stmt::CUDAKernelCallExprClass:
1377  case Stmt::OpaqueValueExprClass:
1378  case Stmt::AsTypeExprClass:
1379  // Fall through.
1380 
1381  // Cases we intentionally don't evaluate, since they don't need
1382  // to be explicitly evaluated.
1383  case Stmt::PredefinedExprClass:
1384  case Stmt::AddrLabelExprClass:
1385  case Stmt::AttributedStmtClass:
1386  case Stmt::IntegerLiteralClass:
1387  case Stmt::FixedPointLiteralClass:
1388  case Stmt::CharacterLiteralClass:
1389  case Stmt::ImplicitValueInitExprClass:
1390  case Stmt::CXXScalarValueInitExprClass:
1391  case Stmt::CXXBoolLiteralExprClass:
1392  case Stmt::ObjCBoolLiteralExprClass:
1393  case Stmt::ObjCAvailabilityCheckExprClass:
1394  case Stmt::FloatingLiteralClass:
1395  case Stmt::NoInitExprClass:
1396  case Stmt::SizeOfPackExprClass:
1397  case Stmt::StringLiteralClass:
1398  case Stmt::SourceLocExprClass:
1399  case Stmt::ObjCStringLiteralClass:
1400  case Stmt::CXXPseudoDestructorExprClass:
1401  case Stmt::SubstNonTypeTemplateParmExprClass:
1402  case Stmt::CXXNullPtrLiteralExprClass:
1403  case Stmt::OMPArraySectionExprClass:
1404  case Stmt::TypeTraitExprClass: {
1405  Bldr.takeNodes(Pred);
1406  ExplodedNodeSet preVisit;
1407  getCheckerManager().runCheckersForPreStmt(preVisit, Pred, S, *this);
1408  getCheckerManager().runCheckersForPostStmt(Dst, preVisit, S, *this);
1409  Bldr.addNodes(Dst);
1410  break;
1411  }
1412 
1413  case Stmt::CXXDefaultArgExprClass:
1414  case Stmt::CXXDefaultInitExprClass: {
1415  Bldr.takeNodes(Pred);
1416  ExplodedNodeSet PreVisit;
1417  getCheckerManager().runCheckersForPreStmt(PreVisit, Pred, S, *this);
1418 
1419  ExplodedNodeSet Tmp;
1420  StmtNodeBuilder Bldr2(PreVisit, Tmp, *currBldrCtx);
1421 
1422  const Expr *ArgE;
1423  if (const auto *DefE = dyn_cast<CXXDefaultArgExpr>(S))
1424  ArgE = DefE->getExpr();
1425  else if (const auto *DefE = dyn_cast<CXXDefaultInitExpr>(S))
1426  ArgE = DefE->getExpr();
1427  else
1428  llvm_unreachable("unknown constant wrapper kind");
1429 
1430  bool IsTemporary = false;
1431  if (const auto *MTE = dyn_cast<MaterializeTemporaryExpr>(ArgE)) {
1432  ArgE = MTE->GetTemporaryExpr();
1433  IsTemporary = true;
1434  }
1435 
1436  Optional<SVal> ConstantVal = svalBuilder.getConstantVal(ArgE);
1437  if (!ConstantVal)
1438  ConstantVal = UnknownVal();
1439 
1440  const LocationContext *LCtx = Pred->getLocationContext();
1441  for (const auto I : PreVisit) {
1442  ProgramStateRef State = I->getState();
1443  State = State->BindExpr(S, LCtx, *ConstantVal);
1444  if (IsTemporary)
1445  State = createTemporaryRegionIfNeeded(State, LCtx,
1446  cast<Expr>(S),
1447  cast<Expr>(S));
1448  Bldr2.generateNode(S, I, State);
1449  }
1450 
1451  getCheckerManager().runCheckersForPostStmt(Dst, Tmp, S, *this);
1452  Bldr.addNodes(Dst);
1453  break;
1454  }
1455 
1456  // Cases we evaluate as opaque expressions, conjuring a symbol.
1457  case Stmt::CXXStdInitializerListExprClass:
1458  case Expr::ObjCArrayLiteralClass:
1459  case Expr::ObjCDictionaryLiteralClass:
1460  case Expr::ObjCBoxedExprClass: {
1461  Bldr.takeNodes(Pred);
1462 
1463  ExplodedNodeSet preVisit;
1464  getCheckerManager().runCheckersForPreStmt(preVisit, Pred, S, *this);
1465 
1466  ExplodedNodeSet Tmp;
1467  StmtNodeBuilder Bldr2(preVisit, Tmp, *currBldrCtx);
1468 
1469  const auto *Ex = cast<Expr>(S);
1470  QualType resultType = Ex->getType();
1471 
1472  for (const auto N : preVisit) {
1473  const LocationContext *LCtx = N->getLocationContext();
1474  SVal result = svalBuilder.conjureSymbolVal(nullptr, Ex, LCtx,
1475  resultType,
1476  currBldrCtx->blockCount());
1477  ProgramStateRef State = N->getState()->BindExpr(Ex, LCtx, result);
1478 
1479  // Escape pointers passed into the list, unless it's an ObjC boxed
1480  // expression which is not a boxable C structure.
1481  if (!(isa<ObjCBoxedExpr>(Ex) &&
1482  !cast<ObjCBoxedExpr>(Ex)->getSubExpr()
1483  ->getType()->isRecordType()))
1484  for (auto Child : Ex->children()) {
1485  assert(Child);
1486  SVal Val = State->getSVal(Child, LCtx);
1487  State = escapeValue(State, Val, PSK_EscapeOther);
1488  }
1489 
1490  Bldr2.generateNode(S, N, State);
1491  }
1492 
1493  getCheckerManager().runCheckersForPostStmt(Dst, Tmp, S, *this);
1494  Bldr.addNodes(Dst);
1495  break;
1496  }
1497 
1498  case Stmt::ArraySubscriptExprClass:
1499  Bldr.takeNodes(Pred);
1500  VisitArraySubscriptExpr(cast<ArraySubscriptExpr>(S), Pred, Dst);
1501  Bldr.addNodes(Dst);
1502  break;
1503 
1504  case Stmt::GCCAsmStmtClass:
1505  Bldr.takeNodes(Pred);
1506  VisitGCCAsmStmt(cast<GCCAsmStmt>(S), Pred, Dst);
1507  Bldr.addNodes(Dst);
1508  break;
1509 
1510  case Stmt::MSAsmStmtClass:
1511  Bldr.takeNodes(Pred);
1512  VisitMSAsmStmt(cast<MSAsmStmt>(S), Pred, Dst);
1513  Bldr.addNodes(Dst);
1514  break;
1515 
1516  case Stmt::BlockExprClass:
1517  Bldr.takeNodes(Pred);
1518  VisitBlockExpr(cast<BlockExpr>(S), Pred, Dst);
1519  Bldr.addNodes(Dst);
1520  break;
1521 
1522  case Stmt::LambdaExprClass:
1523  if (AMgr.options.ShouldInlineLambdas) {
1524  Bldr.takeNodes(Pred);
1525  VisitLambdaExpr(cast<LambdaExpr>(S), Pred, Dst);
1526  Bldr.addNodes(Dst);
1527  } else {
1528  const ExplodedNode *node = Bldr.generateSink(S, Pred, Pred->getState());
1529  Engine.addAbortedBlock(node, currBldrCtx->getBlock());
1530  }
1531  break;
1532 
1533  case Stmt::BinaryOperatorClass: {
1534  const auto *B = cast<BinaryOperator>(S);
1535  if (B->isLogicalOp()) {
1536  Bldr.takeNodes(Pred);
1537  VisitLogicalExpr(B, Pred, Dst);
1538  Bldr.addNodes(Dst);
1539  break;
1540  }
1541  else if (B->getOpcode() == BO_Comma) {
1542  ProgramStateRef state = Pred->getState();
1543  Bldr.generateNode(B, Pred,
1544  state->BindExpr(B, Pred->getLocationContext(),
1545  state->getSVal(B->getRHS(),
1546  Pred->getLocationContext())));
1547  break;
1548  }
1549 
1550  Bldr.takeNodes(Pred);
1551 
1552  if (AMgr.options.ShouldEagerlyAssume &&
1553  (B->isRelationalOp() || B->isEqualityOp())) {
1554  ExplodedNodeSet Tmp;
1555  VisitBinaryOperator(cast<BinaryOperator>(S), Pred, Tmp);
1556  evalEagerlyAssumeBinOpBifurcation(Dst, Tmp, cast<Expr>(S));
1557  }
1558  else
1559  VisitBinaryOperator(cast<BinaryOperator>(S), Pred, Dst);
1560 
1561  Bldr.addNodes(Dst);
1562  break;
1563  }
1564 
1565  case Stmt::CXXOperatorCallExprClass: {
1566  const auto *OCE = cast<CXXOperatorCallExpr>(S);
1567 
1568  // For instance method operators, make sure the 'this' argument has a
1569  // valid region.
1570  const Decl *Callee = OCE->getCalleeDecl();
1571  if (const auto *MD = dyn_cast_or_null<CXXMethodDecl>(Callee)) {
1572  if (MD->isInstance()) {
1573  ProgramStateRef State = Pred->getState();
1574  const LocationContext *LCtx = Pred->getLocationContext();
1575  ProgramStateRef NewState =
1576  createTemporaryRegionIfNeeded(State, LCtx, OCE->getArg(0));
1577  if (NewState != State) {
1578  Pred = Bldr.generateNode(OCE, Pred, NewState, /*Tag=*/nullptr,
1580  // Did we cache out?
1581  if (!Pred)
1582  break;
1583  }
1584  }
1585  }
1586  // FALLTHROUGH
1587  LLVM_FALLTHROUGH;
1588  }
1589 
1590  case Stmt::CallExprClass:
1591  case Stmt::CXXMemberCallExprClass:
1592  case Stmt::UserDefinedLiteralClass:
1593  Bldr.takeNodes(Pred);
1594  VisitCallExpr(cast<CallExpr>(S), Pred, Dst);
1595  Bldr.addNodes(Dst);
1596  break;
1597 
1598  case Stmt::CXXCatchStmtClass:
1599  Bldr.takeNodes(Pred);
1600  VisitCXXCatchStmt(cast<CXXCatchStmt>(S), Pred, Dst);
1601  Bldr.addNodes(Dst);
1602  break;
1603 
1604  case Stmt::CXXTemporaryObjectExprClass:
1605  case Stmt::CXXConstructExprClass:
1606  Bldr.takeNodes(Pred);
1607  VisitCXXConstructExpr(cast<CXXConstructExpr>(S), Pred, Dst);
1608  Bldr.addNodes(Dst);
1609  break;
1610 
1611  case Stmt::CXXNewExprClass: {
1612  Bldr.takeNodes(Pred);
1613 
1614  ExplodedNodeSet PreVisit;
1615  getCheckerManager().runCheckersForPreStmt(PreVisit, Pred, S, *this);
1616 
1617  ExplodedNodeSet PostVisit;
1618  for (const auto i : PreVisit)
1619  VisitCXXNewExpr(cast<CXXNewExpr>(S), i, PostVisit);
1620 
1621  getCheckerManager().runCheckersForPostStmt(Dst, PostVisit, S, *this);
1622  Bldr.addNodes(Dst);
1623  break;
1624  }
1625 
1626  case Stmt::CXXDeleteExprClass: {
1627  Bldr.takeNodes(Pred);
1628  ExplodedNodeSet PreVisit;
1629  const auto *CDE = cast<CXXDeleteExpr>(S);
1630  getCheckerManager().runCheckersForPreStmt(PreVisit, Pred, S, *this);
1631 
1632  for (const auto i : PreVisit)
1633  VisitCXXDeleteExpr(CDE, i, Dst);
1634 
1635  Bldr.addNodes(Dst);
1636  break;
1637  }
1638  // FIXME: ChooseExpr is really a constant. We need to fix
1639  // the CFG do not model them as explicit control-flow.
1640 
1641  case Stmt::ChooseExprClass: { // __builtin_choose_expr
1642  Bldr.takeNodes(Pred);
1643  const auto *C = cast<ChooseExpr>(S);
1644  VisitGuardedExpr(C, C->getLHS(), C->getRHS(), Pred, Dst);
1645  Bldr.addNodes(Dst);
1646  break;
1647  }
1648 
1649  case Stmt::CompoundAssignOperatorClass:
1650  Bldr.takeNodes(Pred);
1651  VisitBinaryOperator(cast<BinaryOperator>(S), Pred, Dst);
1652  Bldr.addNodes(Dst);
1653  break;
1654 
1655  case Stmt::CompoundLiteralExprClass:
1656  Bldr.takeNodes(Pred);
1657  VisitCompoundLiteralExpr(cast<CompoundLiteralExpr>(S), Pred, Dst);
1658  Bldr.addNodes(Dst);
1659  break;
1660 
1661  case Stmt::BinaryConditionalOperatorClass:
1662  case Stmt::ConditionalOperatorClass: { // '?' operator
1663  Bldr.takeNodes(Pred);
1664  const auto *C = cast<AbstractConditionalOperator>(S);
1665  VisitGuardedExpr(C, C->getTrueExpr(), C->getFalseExpr(), Pred, Dst);
1666  Bldr.addNodes(Dst);
1667  break;
1668  }
1669 
1670  case Stmt::CXXThisExprClass:
1671  Bldr.takeNodes(Pred);
1672  VisitCXXThisExpr(cast<CXXThisExpr>(S), Pred, Dst);
1673  Bldr.addNodes(Dst);
1674  break;
1675 
1676  case Stmt::DeclRefExprClass: {
1677  Bldr.takeNodes(Pred);
1678  const auto *DE = cast<DeclRefExpr>(S);
1679  VisitCommonDeclRefExpr(DE, DE->getDecl(), Pred, Dst);
1680  Bldr.addNodes(Dst);
1681  break;
1682  }
1683 
1684  case Stmt::DeclStmtClass:
1685  Bldr.takeNodes(Pred);
1686  VisitDeclStmt(cast<DeclStmt>(S), Pred, Dst);
1687  Bldr.addNodes(Dst);
1688  break;
1689 
1690  case Stmt::ImplicitCastExprClass:
1691  case Stmt::CStyleCastExprClass:
1692  case Stmt::CXXStaticCastExprClass:
1693  case Stmt::CXXDynamicCastExprClass:
1694  case Stmt::CXXReinterpretCastExprClass:
1695  case Stmt::CXXConstCastExprClass:
1696  case Stmt::CXXFunctionalCastExprClass:
1697  case Stmt::ObjCBridgedCastExprClass: {
1698  Bldr.takeNodes(Pred);
1699  const auto *C = cast<CastExpr>(S);
1700  ExplodedNodeSet dstExpr;
1701  VisitCast(C, C->getSubExpr(), Pred, dstExpr);
1702 
1703  // Handle the postvisit checks.
1704  getCheckerManager().runCheckersForPostStmt(Dst, dstExpr, C, *this);
1705  Bldr.addNodes(Dst);
1706  break;
1707  }
1708 
1709  case Expr::MaterializeTemporaryExprClass: {
1710  Bldr.takeNodes(Pred);
1711  const auto *MTE = cast<MaterializeTemporaryExpr>(S);
1712  ExplodedNodeSet dstPrevisit;
1713  getCheckerManager().runCheckersForPreStmt(dstPrevisit, Pred, MTE, *this);
1714  ExplodedNodeSet dstExpr;
1715  for (const auto i : dstPrevisit)
1716  CreateCXXTemporaryObject(MTE, i, dstExpr);
1717  getCheckerManager().runCheckersForPostStmt(Dst, dstExpr, MTE, *this);
1718  Bldr.addNodes(Dst);
1719  break;
1720  }
1721 
1722  case Stmt::InitListExprClass:
1723  Bldr.takeNodes(Pred);
1724  VisitInitListExpr(cast<InitListExpr>(S), Pred, Dst);
1725  Bldr.addNodes(Dst);
1726  break;
1727 
1728  case Stmt::MemberExprClass:
1729  Bldr.takeNodes(Pred);
1730  VisitMemberExpr(cast<MemberExpr>(S), Pred, Dst);
1731  Bldr.addNodes(Dst);
1732  break;
1733 
1734  case Stmt::AtomicExprClass:
1735  Bldr.takeNodes(Pred);
1736  VisitAtomicExpr(cast<AtomicExpr>(S), Pred, Dst);
1737  Bldr.addNodes(Dst);
1738  break;
1739 
1740  case Stmt::ObjCIvarRefExprClass:
1741  Bldr.takeNodes(Pred);
1742  VisitLvalObjCIvarRefExpr(cast<ObjCIvarRefExpr>(S), Pred, Dst);
1743  Bldr.addNodes(Dst);
1744  break;
1745 
1746  case Stmt::ObjCForCollectionStmtClass:
1747  Bldr.takeNodes(Pred);
1748  VisitObjCForCollectionStmt(cast<ObjCForCollectionStmt>(S), Pred, Dst);
1749  Bldr.addNodes(Dst);
1750  break;
1751 
1752  case Stmt::ObjCMessageExprClass:
1753  Bldr.takeNodes(Pred);
1754  VisitObjCMessage(cast<ObjCMessageExpr>(S), Pred, Dst);
1755  Bldr.addNodes(Dst);
1756  break;
1757 
1758  case Stmt::ObjCAtThrowStmtClass:
1759  case Stmt::CXXThrowExprClass:
1760  // FIXME: This is not complete. We basically treat @throw as
1761  // an abort.
1762  Bldr.generateSink(S, Pred, Pred->getState());
1763  break;
1764 
1765  case Stmt::ReturnStmtClass:
1766  Bldr.takeNodes(Pred);
1767  VisitReturnStmt(cast<ReturnStmt>(S), Pred, Dst);
1768  Bldr.addNodes(Dst);
1769  break;
1770 
1771  case Stmt::OffsetOfExprClass: {
1772  Bldr.takeNodes(Pred);
1773  ExplodedNodeSet PreVisit;
1774  getCheckerManager().runCheckersForPreStmt(PreVisit, Pred, S, *this);
1775 
1776  ExplodedNodeSet PostVisit;
1777  for (const auto Node : PreVisit)
1778  VisitOffsetOfExpr(cast<OffsetOfExpr>(S), Node, PostVisit);
1779 
1780  getCheckerManager().runCheckersForPostStmt(Dst, PostVisit, S, *this);
1781  Bldr.addNodes(Dst);
1782  break;
1783  }
1784 
1785  case Stmt::UnaryExprOrTypeTraitExprClass:
1786  Bldr.takeNodes(Pred);
1787  VisitUnaryExprOrTypeTraitExpr(cast<UnaryExprOrTypeTraitExpr>(S),
1788  Pred, Dst);
1789  Bldr.addNodes(Dst);
1790  break;
1791 
1792  case Stmt::StmtExprClass: {
1793  const auto *SE = cast<StmtExpr>(S);
1794 
1795  if (SE->getSubStmt()->body_empty()) {
1796  // Empty statement expression.
1797  assert(SE->getType() == getContext().VoidTy
1798  && "Empty statement expression must have void type.");
1799  break;
1800  }
1801 
1802  if (const auto *LastExpr =
1803  dyn_cast<Expr>(*SE->getSubStmt()->body_rbegin())) {
1804  ProgramStateRef state = Pred->getState();
1805  Bldr.generateNode(SE, Pred,
1806  state->BindExpr(SE, Pred->getLocationContext(),
1807  state->getSVal(LastExpr,
1808  Pred->getLocationContext())));
1809  }
1810  break;
1811  }
1812 
1813  case Stmt::UnaryOperatorClass: {
1814  Bldr.takeNodes(Pred);
1815  const auto *U = cast<UnaryOperator>(S);
1816  if (AMgr.options.ShouldEagerlyAssume && (U->getOpcode() == UO_LNot)) {
1817  ExplodedNodeSet Tmp;
1818  VisitUnaryOperator(U, Pred, Tmp);
1819  evalEagerlyAssumeBinOpBifurcation(Dst, Tmp, U);
1820  }
1821  else
1822  VisitUnaryOperator(U, Pred, Dst);
1823  Bldr.addNodes(Dst);
1824  break;
1825  }
1826 
1827  case Stmt::PseudoObjectExprClass: {
1828  Bldr.takeNodes(Pred);
1829  ProgramStateRef state = Pred->getState();
1830  const auto *PE = cast<PseudoObjectExpr>(S);
1831  if (const Expr *Result = PE->getResultExpr()) {
1832  SVal V = state->getSVal(Result, Pred->getLocationContext());
1833  Bldr.generateNode(S, Pred,
1834  state->BindExpr(S, Pred->getLocationContext(), V));
1835  }
1836  else
1837  Bldr.generateNode(S, Pred,
1838  state->BindExpr(S, Pred->getLocationContext(),
1839  UnknownVal()));
1840 
1841  Bldr.addNodes(Dst);
1842  break;
1843  }
1844  }
1845 }
1846 
1847 bool ExprEngine::replayWithoutInlining(ExplodedNode *N,
1848  const LocationContext *CalleeLC) {
1849  const StackFrameContext *CalleeSF = CalleeLC->getStackFrame();
1850  const StackFrameContext *CallerSF = CalleeSF->getParent()->getStackFrame();
1851  assert(CalleeSF && CallerSF);
1852  ExplodedNode *BeforeProcessingCall = nullptr;
1853  const Stmt *CE = CalleeSF->getCallSite();
1854 
1855  // Find the first node before we started processing the call expression.
1856  while (N) {
1857  ProgramPoint L = N->getLocation();
1858  BeforeProcessingCall = N;
1859  N = N->pred_empty() ? nullptr : *(N->pred_begin());
1860 
1861  // Skip the nodes corresponding to the inlined code.
1862  if (L.getStackFrame() != CallerSF)
1863  continue;
1864  // We reached the caller. Find the node right before we started
1865  // processing the call.
1866  if (L.isPurgeKind())
1867  continue;
1868  if (L.getAs<PreImplicitCall>())
1869  continue;
1870  if (L.getAs<CallEnter>())
1871  continue;
1872  if (Optional<StmtPoint> SP = L.getAs<StmtPoint>())
1873  if (SP->getStmt() == CE)
1874  continue;
1875  break;
1876  }
1877 
1878  if (!BeforeProcessingCall)
1879  return false;
1880 
1881  // TODO: Clean up the unneeded nodes.
1882 
1883  // Build an Epsilon node from which we will restart the analyzes.
1884  // Note that CE is permitted to be NULL!
1885  ProgramPoint NewNodeLoc =
1886  EpsilonPoint(BeforeProcessingCall->getLocationContext(), CE);
1887  // Add the special flag to GDM to signal retrying with no inlining.
1888  // Note, changing the state ensures that we are not going to cache out.
1889  ProgramStateRef NewNodeState = BeforeProcessingCall->getState();
1890  NewNodeState =
1891  NewNodeState->set<ReplayWithoutInlining>(const_cast<Stmt *>(CE));
1892 
1893  // Make the new node a successor of BeforeProcessingCall.
1894  bool IsNew = false;
1895  ExplodedNode *NewNode = G.getNode(NewNodeLoc, NewNodeState, false, &IsNew);
1896  // We cached out at this point. Caching out is common due to us backtracking
1897  // from the inlined function, which might spawn several paths.
1898  if (!IsNew)
1899  return true;
1900 
1901  NewNode->addPredecessor(BeforeProcessingCall, G);
1902 
1903  // Add the new node to the work list.
1904  Engine.enqueueStmtNode(NewNode, CalleeSF->getCallSiteBlock(),
1905  CalleeSF->getIndex());
1906  NumTimesRetriedWithoutInlining++;
1907  return true;
1908 }
1909 
1910 /// Block entrance. (Update counters).
1912  NodeBuilderWithSinks &nodeBuilder,
1913  ExplodedNode *Pred) {
1915  // If we reach a loop which has a known bound (and meets
1916  // other constraints) then consider completely unrolling it.
1917  if(AMgr.options.ShouldUnrollLoops) {
1918  unsigned maxBlockVisitOnPath = AMgr.options.maxBlockVisitOnPath;
1919  const Stmt *Term = nodeBuilder.getContext().getBlock()->getTerminatorStmt();
1920  if (Term) {
1921  ProgramStateRef NewState = updateLoopStack(Term, AMgr.getASTContext(),
1922  Pred, maxBlockVisitOnPath);
1923  if (NewState != Pred->getState()) {
1924  ExplodedNode *UpdatedNode = nodeBuilder.generateNode(NewState, Pred);
1925  if (!UpdatedNode)
1926  return;
1927  Pred = UpdatedNode;
1928  }
1929  }
1930  // Is we are inside an unrolled loop then no need the check the counters.
1931  if(isUnrolledState(Pred->getState()))
1932  return;
1933  }
1934 
1935  // If this block is terminated by a loop and it has already been visited the
1936  // maximum number of times, widen the loop.
1937  unsigned int BlockCount = nodeBuilder.getContext().blockCount();
1938  if (BlockCount == AMgr.options.maxBlockVisitOnPath - 1 &&
1939  AMgr.options.ShouldWidenLoops) {
1940  const Stmt *Term = nodeBuilder.getContext().getBlock()->getTerminatorStmt();
1941  if (!(Term &&
1942  (isa<ForStmt>(Term) || isa<WhileStmt>(Term) || isa<DoStmt>(Term))))
1943  return;
1944  // Widen.
1945  const LocationContext *LCtx = Pred->getLocationContext();
1946  ProgramStateRef WidenedState =
1947  getWidenedLoopState(Pred->getState(), LCtx, BlockCount, Term);
1948  nodeBuilder.generateNode(WidenedState, Pred);
1949  return;
1950  }
1951 
1952  // FIXME: Refactor this into a checker.
1953  if (BlockCount >= AMgr.options.maxBlockVisitOnPath) {
1954  static SimpleProgramPointTag tag(TagProviderName, "Block count exceeded");
1955  const ExplodedNode *Sink =
1956  nodeBuilder.generateSink(Pred->getState(), Pred, &tag);
1957 
1958  // Check if we stopped at the top level function or not.
1959  // Root node should have the location context of the top most function.
1960  const LocationContext *CalleeLC = Pred->getLocation().getLocationContext();
1961  const LocationContext *CalleeSF = CalleeLC->getStackFrame();
1962  const LocationContext *RootLC =
1963  (*G.roots_begin())->getLocation().getLocationContext();
1964  if (RootLC->getStackFrame() != CalleeSF) {
1965  Engine.FunctionSummaries->markReachedMaxBlockCount(CalleeSF->getDecl());
1966 
1967  // Re-run the call evaluation without inlining it, by storing the
1968  // no-inlining policy in the state and enqueuing the new work item on
1969  // the list. Replay should almost never fail. Use the stats to catch it
1970  // if it does.
1971  if ((!AMgr.options.NoRetryExhausted &&
1972  replayWithoutInlining(Pred, CalleeLC)))
1973  return;
1974  NumMaxBlockCountReachedInInlined++;
1975  } else
1976  NumMaxBlockCountReached++;
1977 
1978  // Make sink nodes as exhausted(for stats) only if retry failed.
1979  Engine.blocksExhausted.push_back(std::make_pair(L, Sink));
1980  }
1981 }
1982 
1983 //===----------------------------------------------------------------------===//
1984 // Branch processing.
1985 //===----------------------------------------------------------------------===//
1986 
1987 /// RecoverCastedSymbol - A helper function for ProcessBranch that is used
1988 /// to try to recover some path-sensitivity for casts of symbolic
1989 /// integers that promote their values (which are currently not tracked well).
1990 /// This function returns the SVal bound to Condition->IgnoreCasts if all the
1991 // cast(s) did was sign-extend the original value.
1993  const Stmt *Condition,
1994  const LocationContext *LCtx,
1995  ASTContext &Ctx) {
1996 
1997  const auto *Ex = dyn_cast<Expr>(Condition);
1998  if (!Ex)
1999  return UnknownVal();
2000 
2001  uint64_t bits = 0;
2002  bool bitsInit = false;
2003 
2004  while (const auto *CE = dyn_cast<CastExpr>(Ex)) {
2005  QualType T = CE->getType();
2006 
2007  if (!T->isIntegralOrEnumerationType())
2008  return UnknownVal();
2009 
2010  uint64_t newBits = Ctx.getTypeSize(T);
2011  if (!bitsInit || newBits < bits) {
2012  bitsInit = true;
2013  bits = newBits;
2014  }
2015 
2016  Ex = CE->getSubExpr();
2017  }
2018 
2019  // We reached a non-cast. Is it a symbolic value?
2020  QualType T = Ex->getType();
2021 
2022  if (!bitsInit || !T->isIntegralOrEnumerationType() ||
2023  Ctx.getTypeSize(T) > bits)
2024  return UnknownVal();
2025 
2026  return state->getSVal(Ex, LCtx);
2027 }
2028 
2029 #ifndef NDEBUG
2030 static const Stmt *getRightmostLeaf(const Stmt *Condition) {
2031  while (Condition) {
2032  const auto *BO = dyn_cast<BinaryOperator>(Condition);
2033  if (!BO || !BO->isLogicalOp()) {
2034  return Condition;
2035  }
2036  Condition = BO->getRHS()->IgnoreParens();
2037  }
2038  return nullptr;
2039 }
2040 #endif
2041 
2042 // Returns the condition the branch at the end of 'B' depends on and whose value
2043 // has been evaluated within 'B'.
2044 // In most cases, the terminator condition of 'B' will be evaluated fully in
2045 // the last statement of 'B'; in those cases, the resolved condition is the
2046 // given 'Condition'.
2047 // If the condition of the branch is a logical binary operator tree, the CFG is
2048 // optimized: in that case, we know that the expression formed by all but the
2049 // rightmost leaf of the logical binary operator tree must be true, and thus
2050 // the branch condition is at this point equivalent to the truth value of that
2051 // rightmost leaf; the CFG block thus only evaluates this rightmost leaf
2052 // expression in its final statement. As the full condition in that case was
2053 // not evaluated, and is thus not in the SVal cache, we need to use that leaf
2054 // expression to evaluate the truth value of the condition in the current state
2055 // space.
2056 static const Stmt *ResolveCondition(const Stmt *Condition,
2057  const CFGBlock *B) {
2058  if (const auto *Ex = dyn_cast<Expr>(Condition))
2059  Condition = Ex->IgnoreParens();
2060 
2061  const auto *BO = dyn_cast<BinaryOperator>(Condition);
2062  if (!BO || !BO->isLogicalOp())
2063  return Condition;
2064 
2065  assert(B->getTerminator().isStmtBranch() &&
2066  "Other kinds of branches are handled separately!");
2067 
2068  // For logical operations, we still have the case where some branches
2069  // use the traditional "merge" approach and others sink the branch
2070  // directly into the basic blocks representing the logical operation.
2071  // We need to distinguish between those two cases here.
2072 
2073  // The invariants are still shifting, but it is possible that the
2074  // last element in a CFGBlock is not a CFGStmt. Look for the last
2075  // CFGStmt as the value of the condition.
2076  CFGBlock::const_reverse_iterator I = B->rbegin(), E = B->rend();
2077  for (; I != E; ++I) {
2078  CFGElement Elem = *I;
2079  Optional<CFGStmt> CS = Elem.getAs<CFGStmt>();
2080  if (!CS)
2081  continue;
2082  const Stmt *LastStmt = CS->getStmt();
2083  assert(LastStmt == Condition || LastStmt == getRightmostLeaf(Condition));
2084  return LastStmt;
2085  }
2086  llvm_unreachable("could not resolve condition");
2087 }
2088 
2089 void ExprEngine::processBranch(const Stmt *Condition,
2090  NodeBuilderContext& BldCtx,
2091  ExplodedNode *Pred,
2092  ExplodedNodeSet &Dst,
2093  const CFGBlock *DstT,
2094  const CFGBlock *DstF) {
2095  assert((!Condition || !isa<CXXBindTemporaryExpr>(Condition)) &&
2096  "CXXBindTemporaryExprs are handled by processBindTemporary.");
2097  const LocationContext *LCtx = Pred->getLocationContext();
2098  PrettyStackTraceLocationContext StackCrashInfo(LCtx);
2099  currBldrCtx = &BldCtx;
2100 
2101  // Check for NULL conditions; e.g. "for(;;)"
2102  if (!Condition) {
2103  BranchNodeBuilder NullCondBldr(Pred, Dst, BldCtx, DstT, DstF);
2104  NullCondBldr.markInfeasible(false);
2105  NullCondBldr.generateNode(Pred->getState(), true, Pred);
2106  return;
2107  }
2108 
2109  if (const auto *Ex = dyn_cast<Expr>(Condition))
2110  Condition = Ex->IgnoreParens();
2111 
2112  Condition = ResolveCondition(Condition, BldCtx.getBlock());
2113  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
2114  Condition->getBeginLoc(),
2115  "Error evaluating branch");
2116 
2117  ExplodedNodeSet CheckersOutSet;
2118  getCheckerManager().runCheckersForBranchCondition(Condition, CheckersOutSet,
2119  Pred, *this);
2120  // We generated only sinks.
2121  if (CheckersOutSet.empty())
2122  return;
2123 
2124  BranchNodeBuilder builder(CheckersOutSet, Dst, BldCtx, DstT, DstF);
2125  for (const auto PredI : CheckersOutSet) {
2126  if (PredI->isSink())
2127  continue;
2128 
2129  ProgramStateRef PrevState = PredI->getState();
2130  SVal X = PrevState->getSVal(Condition, PredI->getLocationContext());
2131 
2132  if (X.isUnknownOrUndef()) {
2133  // Give it a chance to recover from unknown.
2134  if (const auto *Ex = dyn_cast<Expr>(Condition)) {
2135  if (Ex->getType()->isIntegralOrEnumerationType()) {
2136  // Try to recover some path-sensitivity. Right now casts of symbolic
2137  // integers that promote their values are currently not tracked well.
2138  // If 'Condition' is such an expression, try and recover the
2139  // underlying value and use that instead.
2140  SVal recovered = RecoverCastedSymbol(PrevState, Condition,
2141  PredI->getLocationContext(),
2142  getContext());
2143 
2144  if (!recovered.isUnknown()) {
2145  X = recovered;
2146  }
2147  }
2148  }
2149  }
2150 
2151  // If the condition is still unknown, give up.
2152  if (X.isUnknownOrUndef()) {
2153  builder.generateNode(PrevState, true, PredI);
2154  builder.generateNode(PrevState, false, PredI);
2155  continue;
2156  }
2157 
2158  DefinedSVal V = X.castAs<DefinedSVal>();
2159 
2160  ProgramStateRef StTrue, StFalse;
2161  std::tie(StTrue, StFalse) = PrevState->assume(V);
2162 
2163  // Process the true branch.
2164  if (builder.isFeasible(true)) {
2165  if (StTrue)
2166  builder.generateNode(StTrue, true, PredI);
2167  else
2168  builder.markInfeasible(true);
2169  }
2170 
2171  // Process the false branch.
2172  if (builder.isFeasible(false)) {
2173  if (StFalse)
2174  builder.generateNode(StFalse, false, PredI);
2175  else
2176  builder.markInfeasible(false);
2177  }
2178  }
2179  currBldrCtx = nullptr;
2180 }
2181 
2182 /// The GDM component containing the set of global variables which have been
2183 /// previously initialized with explicit initializers.
2184 REGISTER_TRAIT_WITH_PROGRAMSTATE(InitializedGlobalsSet,
2185  llvm::ImmutableSet<const VarDecl *>)
2186 
2188  NodeBuilderContext &BuilderCtx,
2189  ExplodedNode *Pred,
2190  ExplodedNodeSet &Dst,
2191  const CFGBlock *DstT,
2192  const CFGBlock *DstF) {
2193  PrettyStackTraceLocationContext CrashInfo(Pred->getLocationContext());
2194  currBldrCtx = &BuilderCtx;
2195 
2196  const auto *VD = cast<VarDecl>(DS->getSingleDecl());
2197  ProgramStateRef state = Pred->getState();
2198  bool initHasRun = state->contains<InitializedGlobalsSet>(VD);
2199  BranchNodeBuilder builder(Pred, Dst, BuilderCtx, DstT, DstF);
2200 
2201  if (!initHasRun) {
2202  state = state->add<InitializedGlobalsSet>(VD);
2203  }
2204 
2205  builder.generateNode(state, initHasRun, Pred);
2206  builder.markInfeasible(!initHasRun);
2207 
2208  currBldrCtx = nullptr;
2209 }
2210 
2211 /// processIndirectGoto - Called by CoreEngine. Used to generate successor
2212 /// nodes by processing the 'effects' of a computed goto jump.
2214  ProgramStateRef state = builder.getState();
2215  SVal V = state->getSVal(builder.getTarget(), builder.getLocationContext());
2216 
2217  // Three possibilities:
2218  //
2219  // (1) We know the computed label.
2220  // (2) The label is NULL (or some other constant), or Undefined.
2221  // (3) We have no clue about the label. Dispatch to all targets.
2222  //
2223 
2224  using iterator = IndirectGotoNodeBuilder::iterator;
2225 
2227  const LabelDecl *L = LV->getLabel();
2228 
2229  for (iterator I = builder.begin(), E = builder.end(); I != E; ++I) {
2230  if (I.getLabel() == L) {
2231  builder.generateNode(I, state);
2232  return;
2233  }
2234  }
2235 
2236  llvm_unreachable("No block with label.");
2237  }
2238 
2239  if (V.getAs<loc::ConcreteInt>() || V.getAs<UndefinedVal>()) {
2240  // Dispatch to the first target and mark it as a sink.
2241  //ExplodedNode* N = builder.generateNode(builder.begin(), state, true);
2242  // FIXME: add checker visit.
2243  // UndefBranches.insert(N);
2244  return;
2245  }
2246 
2247  // This is really a catch-all. We don't support symbolics yet.
2248  // FIXME: Implement dispatch for symbolic pointers.
2249 
2250  for (iterator I = builder.begin(), E = builder.end(); I != E; ++I)
2251  builder.generateNode(I, state);
2252 }
2253 
2255  ExplodedNode *Pred,
2256  ExplodedNodeSet &Dst,
2257  const BlockEdge &L) {
2258  SaveAndRestore<const NodeBuilderContext *> NodeContextRAII(currBldrCtx, &BC);
2259  getCheckerManager().runCheckersForBeginFunction(Dst, L, Pred, *this);
2260 }
2261 
2262 /// ProcessEndPath - Called by CoreEngine. Used to generate end-of-path
2263 /// nodes when the control reaches the end of a function.
2265  ExplodedNode *Pred,
2266  const ReturnStmt *RS) {
2267  ProgramStateRef State = Pred->getState();
2268 
2269  if (!Pred->getStackFrame()->inTopFrame())
2270  State = finishArgumentConstruction(
2272  Pred->getStackFrame(), Pred->getState()));
2273 
2274  // FIXME: We currently cannot assert that temporaries are clear, because
2275  // lifetime extended temporaries are not always modelled correctly. In some
2276  // cases when we materialize the temporary, we do
2277  // createTemporaryRegionIfNeeded(), and the region changes, and also the
2278  // respective destructor becomes automatic from temporary. So for now clean up
2279  // the state manually before asserting. Ideally, this braced block of code
2280  // should go away.
2281  {
2282  const LocationContext *FromLC = Pred->getLocationContext();
2283  const LocationContext *ToLC = FromLC->getStackFrame()->getParent();
2284  const LocationContext *LC = FromLC;
2285  while (LC != ToLC) {
2286  assert(LC && "ToLC must be a parent of FromLC!");
2287  for (auto I : State->get<ObjectsUnderConstruction>())
2288  if (I.first.getLocationContext() == LC) {
2289  // The comment above only pardons us for not cleaning up a
2290  // temporary destructor. If any other statements are found here,
2291  // it must be a separate problem.
2292  assert(I.first.getItem().getKind() ==
2294  I.first.getItem().getKind() ==
2296  State = State->remove<ObjectsUnderConstruction>(I.first);
2297  }
2298  LC = LC->getParent();
2299  }
2300  }
2301 
2302  // Perform the transition with cleanups.
2303  if (State != Pred->getState()) {
2304  ExplodedNodeSet PostCleanup;
2305  NodeBuilder Bldr(Pred, PostCleanup, BC);
2306  Pred = Bldr.generateNode(Pred->getLocation(), State, Pred);
2307  if (!Pred) {
2308  // The node with clean temporaries already exists. We might have reached
2309  // it on a path on which we initialize different temporaries.
2310  return;
2311  }
2312  }
2313 
2314  assert(areAllObjectsFullyConstructed(Pred->getState(),
2315  Pred->getLocationContext(),
2316  Pred->getStackFrame()->getParent()));
2317 
2319 
2320  ExplodedNodeSet Dst;
2321  if (Pred->getLocationContext()->inTopFrame()) {
2322  // Remove dead symbols.
2323  ExplodedNodeSet AfterRemovedDead;
2324  removeDeadOnEndOfFunction(BC, Pred, AfterRemovedDead);
2325 
2326  // Notify checkers.
2327  for (const auto I : AfterRemovedDead)
2328  getCheckerManager().runCheckersForEndFunction(BC, Dst, I, *this, RS);
2329  } else {
2330  getCheckerManager().runCheckersForEndFunction(BC, Dst, Pred, *this, RS);
2331  }
2332 
2333  Engine.enqueueEndOfFunction(Dst, RS);
2334 }
2335 
2336 /// ProcessSwitch - Called by CoreEngine. Used to generate successor
2337 /// nodes by processing the 'effects' of a switch statement.
2339  using iterator = SwitchNodeBuilder::iterator;
2340 
2341  ProgramStateRef state = builder.getState();
2342  const Expr *CondE = builder.getCondition();
2343  SVal CondV_untested = state->getSVal(CondE, builder.getLocationContext());
2344 
2345  if (CondV_untested.isUndef()) {
2346  //ExplodedNode* N = builder.generateDefaultCaseNode(state, true);
2347  // FIXME: add checker
2348  //UndefBranches.insert(N);
2349 
2350  return;
2351  }
2352  DefinedOrUnknownSVal CondV = CondV_untested.castAs<DefinedOrUnknownSVal>();
2353 
2354  ProgramStateRef DefaultSt = state;
2355 
2356  iterator I = builder.begin(), EI = builder.end();
2357  bool defaultIsFeasible = I == EI;
2358 
2359  for ( ; I != EI; ++I) {
2360  // Successor may be pruned out during CFG construction.
2361  if (!I.getBlock())
2362  continue;
2363 
2364  const CaseStmt *Case = I.getCase();
2365 
2366  // Evaluate the LHS of the case value.
2367  llvm::APSInt V1 = Case->getLHS()->EvaluateKnownConstInt(getContext());
2368  assert(V1.getBitWidth() == getContext().getIntWidth(CondE->getType()));
2369 
2370  // Get the RHS of the case, if it exists.
2371  llvm::APSInt V2;
2372  if (const Expr *E = Case->getRHS())
2373  V2 = E->EvaluateKnownConstInt(getContext());
2374  else
2375  V2 = V1;
2376 
2377  ProgramStateRef StateCase;
2378  if (Optional<NonLoc> NL = CondV.getAs<NonLoc>())
2379  std::tie(StateCase, DefaultSt) =
2380  DefaultSt->assumeInclusiveRange(*NL, V1, V2);
2381  else // UnknownVal
2382  StateCase = DefaultSt;
2383 
2384  if (StateCase)
2385  builder.generateCaseStmtNode(I, StateCase);
2386 
2387  // Now "assume" that the case doesn't match. Add this state
2388  // to the default state (if it is feasible).
2389  if (DefaultSt)
2390  defaultIsFeasible = true;
2391  else {
2392  defaultIsFeasible = false;
2393  break;
2394  }
2395  }
2396 
2397  if (!defaultIsFeasible)
2398  return;
2399 
2400  // If we have switch(enum value), the default branch is not
2401  // feasible if all of the enum constants not covered by 'case:' statements
2402  // are not feasible values for the switch condition.
2403  //
2404  // Note that this isn't as accurate as it could be. Even if there isn't
2405  // a case for a particular enum value as long as that enum value isn't
2406  // feasible then it shouldn't be considered for making 'default:' reachable.
2407  const SwitchStmt *SS = builder.getSwitch();
2408  const Expr *CondExpr = SS->getCond()->IgnoreParenImpCasts();
2409  if (CondExpr->getType()->getAs<EnumType>()) {
2410  if (SS->isAllEnumCasesCovered())
2411  return;
2412  }
2413 
2414  builder.generateDefaultCaseNode(DefaultSt);
2415 }
2416 
2417 //===----------------------------------------------------------------------===//
2418 // Transfer functions: Loads and stores.
2419 //===----------------------------------------------------------------------===//
2420 
2422  ExplodedNode *Pred,
2423  ExplodedNodeSet &Dst) {
2424  StmtNodeBuilder Bldr(Pred, Dst, *currBldrCtx);
2425 
2426  ProgramStateRef state = Pred->getState();
2427  const LocationContext *LCtx = Pred->getLocationContext();
2428 
2429  if (const auto *VD = dyn_cast<VarDecl>(D)) {
2430  // C permits "extern void v", and if you cast the address to a valid type,
2431  // you can even do things with it. We simply pretend
2432  assert(Ex->isGLValue() || VD->getType()->isVoidType());
2433  const LocationContext *LocCtxt = Pred->getLocationContext();
2434  const Decl *D = LocCtxt->getDecl();
2435  const auto *MD = dyn_cast_or_null<CXXMethodDecl>(D);
2436  const auto *DeclRefEx = dyn_cast<DeclRefExpr>(Ex);
2438 
2439  if (AMgr.options.ShouldInlineLambdas && DeclRefEx &&
2440  DeclRefEx->refersToEnclosingVariableOrCapture() && MD &&
2441  MD->getParent()->isLambda()) {
2442  // Lookup the field of the lambda.
2443  const CXXRecordDecl *CXXRec = MD->getParent();
2444  llvm::DenseMap<const VarDecl *, FieldDecl *> LambdaCaptureFields;
2445  FieldDecl *LambdaThisCaptureField;
2446  CXXRec->getCaptureFields(LambdaCaptureFields, LambdaThisCaptureField);
2447 
2448  // Sema follows a sequence of complex rules to determine whether the
2449  // variable should be captured.
2450  if (const FieldDecl *FD = LambdaCaptureFields[VD]) {
2451  Loc CXXThis =
2452  svalBuilder.getCXXThis(MD, LocCtxt->getStackFrame());
2453  SVal CXXThisVal = state->getSVal(CXXThis);
2454  VInfo = std::make_pair(state->getLValue(FD, CXXThisVal), FD->getType());
2455  }
2456  }
2457 
2458  if (!VInfo)
2459  VInfo = std::make_pair(state->getLValue(VD, LocCtxt), VD->getType());
2460 
2461  SVal V = VInfo->first;
2462  bool IsReference = VInfo->second->isReferenceType();
2463 
2464  // For references, the 'lvalue' is the pointer address stored in the
2465  // reference region.
2466  if (IsReference) {
2467  if (const MemRegion *R = V.getAsRegion())
2468  V = state->getSVal(R);
2469  else
2470  V = UnknownVal();
2471  }
2472 
2473  Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V), nullptr,
2475  return;
2476  }
2477  if (const auto *ED = dyn_cast<EnumConstantDecl>(D)) {
2478  assert(!Ex->isGLValue());
2479  SVal V = svalBuilder.makeIntVal(ED->getInitVal());
2480  Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V));
2481  return;
2482  }
2483  if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
2484  SVal V = svalBuilder.getFunctionPointer(FD);
2485  Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V), nullptr,
2487  return;
2488  }
2489  if (isa<FieldDecl>(D) || isa<IndirectFieldDecl>(D)) {
2490  // FIXME: Compute lvalue of field pointers-to-member.
2491  // Right now we just use a non-null void pointer, so that it gives proper
2492  // results in boolean contexts.
2493  // FIXME: Maybe delegate this to the surrounding operator&.
2494  // Note how this expression is lvalue, however pointer-to-member is NonLoc.
2495  SVal V = svalBuilder.conjureSymbolVal(Ex, LCtx, getContext().VoidPtrTy,
2496  currBldrCtx->blockCount());
2497  state = state->assume(V.castAs<DefinedOrUnknownSVal>(), true);
2498  Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V), nullptr,
2500  return;
2501  }
2502  if (isa<BindingDecl>(D)) {
2503  // FIXME: proper support for bound declarations.
2504  // For now, let's just prevent crashing.
2505  return;
2506  }
2507 
2508  llvm_unreachable("Support for this Decl not implemented.");
2509 }
2510 
2511 /// VisitArraySubscriptExpr - Transfer function for array accesses
2513  ExplodedNode *Pred,
2514  ExplodedNodeSet &Dst){
2515  const Expr *Base = A->getBase()->IgnoreParens();
2516  const Expr *Idx = A->getIdx()->IgnoreParens();
2517 
2518  ExplodedNodeSet CheckerPreStmt;
2519  getCheckerManager().runCheckersForPreStmt(CheckerPreStmt, Pred, A, *this);
2520 
2521  ExplodedNodeSet EvalSet;
2522  StmtNodeBuilder Bldr(CheckerPreStmt, EvalSet, *currBldrCtx);
2523 
2524  bool IsVectorType = A->getBase()->getType()->isVectorType();
2525 
2526  // The "like" case is for situations where C standard prohibits the type to
2527  // be an lvalue, e.g. taking the address of a subscript of an expression of
2528  // type "void *".
2529  bool IsGLValueLike = A->isGLValue() ||
2530  (A->getType().isCForbiddenLValueType() && !AMgr.getLangOpts().CPlusPlus);
2531 
2532  for (auto *Node : CheckerPreStmt) {
2533  const LocationContext *LCtx = Node->getLocationContext();
2534  ProgramStateRef state = Node->getState();
2535 
2536  if (IsGLValueLike) {
2537  QualType T = A->getType();
2538 
2539  // One of the forbidden LValue types! We still need to have sensible
2540  // symbolic locations to represent this stuff. Note that arithmetic on
2541  // void pointers is a GCC extension.
2542  if (T->isVoidType())
2543  T = getContext().CharTy;
2544 
2545  SVal V = state->getLValue(T,
2546  state->getSVal(Idx, LCtx),
2547  state->getSVal(Base, LCtx));
2548  Bldr.generateNode(A, Node, state->BindExpr(A, LCtx, V), nullptr,
2550  } else if (IsVectorType) {
2551  // FIXME: non-glvalue vector reads are not modelled.
2552  Bldr.generateNode(A, Node, state, nullptr);
2553  } else {
2554  llvm_unreachable("Array subscript should be an lValue when not \
2555 a vector and not a forbidden lvalue type");
2556  }
2557  }
2558 
2559  getCheckerManager().runCheckersForPostStmt(Dst, EvalSet, A, *this);
2560 }
2561 
2562 /// VisitMemberExpr - Transfer function for member expressions.
2564  ExplodedNodeSet &Dst) {
2565  // FIXME: Prechecks eventually go in ::Visit().
2566  ExplodedNodeSet CheckedSet;
2567  getCheckerManager().runCheckersForPreStmt(CheckedSet, Pred, M, *this);
2568 
2569  ExplodedNodeSet EvalSet;
2570  ValueDecl *Member = M->getMemberDecl();
2571 
2572  // Handle static member variables and enum constants accessed via
2573  // member syntax.
2574  if (isa<VarDecl>(Member) || isa<EnumConstantDecl>(Member)) {
2575  for (const auto I : CheckedSet)
2576  VisitCommonDeclRefExpr(M, Member, I, EvalSet);
2577  } else {
2578  StmtNodeBuilder Bldr(CheckedSet, EvalSet, *currBldrCtx);
2579  ExplodedNodeSet Tmp;
2580 
2581  for (const auto I : CheckedSet) {
2582  ProgramStateRef state = I->getState();
2583  const LocationContext *LCtx = I->getLocationContext();
2584  Expr *BaseExpr = M->getBase();
2585 
2586  // Handle C++ method calls.
2587  if (const auto *MD = dyn_cast<CXXMethodDecl>(Member)) {
2588  if (MD->isInstance())
2589  state = createTemporaryRegionIfNeeded(state, LCtx, BaseExpr);
2590 
2591  SVal MDVal = svalBuilder.getFunctionPointer(MD);
2592  state = state->BindExpr(M, LCtx, MDVal);
2593 
2594  Bldr.generateNode(M, I, state);
2595  continue;
2596  }
2597 
2598  // Handle regular struct fields / member variables.
2599  const SubRegion *MR = nullptr;
2600  state = createTemporaryRegionIfNeeded(state, LCtx, BaseExpr,
2601  /*Result=*/nullptr,
2602  /*OutRegionWithAdjustments=*/&MR);
2603  SVal baseExprVal =
2604  MR ? loc::MemRegionVal(MR) : state->getSVal(BaseExpr, LCtx);
2605 
2606  const auto *field = cast<FieldDecl>(Member);
2607  SVal L = state->getLValue(field, baseExprVal);
2608 
2609  if (M->isGLValue() || M->getType()->isArrayType()) {
2610  // We special-case rvalues of array type because the analyzer cannot
2611  // reason about them, since we expect all regions to be wrapped in Locs.
2612  // We instead treat these as lvalues and assume that they will decay to
2613  // pointers as soon as they are used.
2614  if (!M->isGLValue()) {
2615  assert(M->getType()->isArrayType());
2616  const auto *PE =
2617  dyn_cast<ImplicitCastExpr>(I->getParentMap().getParentIgnoreParens(M));
2618  if (!PE || PE->getCastKind() != CK_ArrayToPointerDecay) {
2619  llvm_unreachable("should always be wrapped in ArrayToPointerDecay");
2620  }
2621  }
2622 
2623  if (field->getType()->isReferenceType()) {
2624  if (const MemRegion *R = L.getAsRegion())
2625  L = state->getSVal(R);
2626  else
2627  L = UnknownVal();
2628  }
2629 
2630  Bldr.generateNode(M, I, state->BindExpr(M, LCtx, L), nullptr,
2632  } else {
2633  Bldr.takeNodes(I);
2634  evalLoad(Tmp, M, M, I, state, L);
2635  Bldr.addNodes(Tmp);
2636  }
2637  }
2638  }
2639 
2640  getCheckerManager().runCheckersForPostStmt(Dst, EvalSet, M, *this);
2641 }
2642 
2644  ExplodedNodeSet &Dst) {
2645  ExplodedNodeSet AfterPreSet;
2646  getCheckerManager().runCheckersForPreStmt(AfterPreSet, Pred, AE, *this);
2647 
2648  // For now, treat all the arguments to C11 atomics as escaping.
2649  // FIXME: Ideally we should model the behavior of the atomics precisely here.
2650 
2651  ExplodedNodeSet AfterInvalidateSet;
2652  StmtNodeBuilder Bldr(AfterPreSet, AfterInvalidateSet, *currBldrCtx);
2653 
2654  for (const auto I : AfterPreSet) {
2655  ProgramStateRef State = I->getState();
2656  const LocationContext *LCtx = I->getLocationContext();
2657 
2658  SmallVector<SVal, 8> ValuesToInvalidate;
2659  for (unsigned SI = 0, Count = AE->getNumSubExprs(); SI != Count; SI++) {
2660  const Expr *SubExpr = AE->getSubExprs()[SI];
2661  SVal SubExprVal = State->getSVal(SubExpr, LCtx);
2662  ValuesToInvalidate.push_back(SubExprVal);
2663  }
2664 
2665  State = State->invalidateRegions(ValuesToInvalidate, AE,
2666  currBldrCtx->blockCount(),
2667  LCtx,
2668  /*CausedByPointerEscape*/true,
2669  /*Symbols=*/nullptr);
2670 
2671  SVal ResultVal = UnknownVal();
2672  State = State->BindExpr(AE, LCtx, ResultVal);
2673  Bldr.generateNode(AE, I, State, nullptr,
2675  }
2676 
2677  getCheckerManager().runCheckersForPostStmt(Dst, AfterInvalidateSet, AE, *this);
2678 }
2679 
2680 // A value escapes in four possible cases:
2681 // (1) We are binding to something that is not a memory region.
2682 // (2) We are binding to a MemRegion that does not have stack storage.
2683 // (3) We are binding to a top-level parameter region with a non-trivial
2684 // destructor. We won't see the destructor during analysis, but it's there.
2685 // (4) We are binding to a MemRegion with stack storage that the store
2686 // does not understand.
2689  SVal Val, const LocationContext *LCtx) {
2690 
2691  // Cases (1) and (2).
2692  const MemRegion *MR = Loc.getAsRegion();
2693  if (!MR || !MR->hasStackStorage())
2694  return escapeValue(State, Val, PSK_EscapeOnBind);
2695 
2696  // Case (3).
2697  if (const auto *VR = dyn_cast<VarRegion>(MR->getBaseRegion()))
2698  if (VR->hasStackParametersStorage() && VR->getStackFrame()->inTopFrame())
2699  if (const auto *RD = VR->getValueType()->getAsCXXRecordDecl())
2700  if (!RD->hasTrivialDestructor())
2701  return escapeValue(State, Val, PSK_EscapeOnBind);
2702 
2703  // Case (4): in order to test that, generate a new state with the binding
2704  // added. If it is the same state, then it escapes (since the store cannot
2705  // represent the binding).
2706  // Do this only if we know that the store is not supposed to generate the
2707  // same state.
2708  SVal StoredVal = State->getSVal(MR);
2709  if (StoredVal != Val)
2710  if (State == (State->bindLoc(loc::MemRegionVal(MR), Val, LCtx)))
2711  return escapeValue(State, Val, PSK_EscapeOnBind);
2712 
2713  return State;
2714 }
2715 
2718  const InvalidatedSymbols *Invalidated,
2719  ArrayRef<const MemRegion *> ExplicitRegions,
2720  const CallEvent *Call,
2722  if (!Invalidated || Invalidated->empty())
2723  return State;
2724 
2725  if (!Call)
2727  *Invalidated,
2728  nullptr,
2730  &ITraits);
2731 
2732  // If the symbols were invalidated by a call, we want to find out which ones
2733  // were invalidated directly due to being arguments to the call.
2734  InvalidatedSymbols SymbolsDirectlyInvalidated;
2735  for (const auto I : ExplicitRegions) {
2736  if (const SymbolicRegion *R = I->StripCasts()->getAs<SymbolicRegion>())
2737  SymbolsDirectlyInvalidated.insert(R->getSymbol());
2738  }
2739 
2740  InvalidatedSymbols SymbolsIndirectlyInvalidated;
2741  for (const auto &sym : *Invalidated) {
2742  if (SymbolsDirectlyInvalidated.count(sym))
2743  continue;
2744  SymbolsIndirectlyInvalidated.insert(sym);
2745  }
2746 
2747  if (!SymbolsDirectlyInvalidated.empty())
2749  SymbolsDirectlyInvalidated, Call, PSK_DirectEscapeOnCall, &ITraits);
2750 
2751  // Notify about the symbols that get indirectly invalidated by the call.
2752  if (!SymbolsIndirectlyInvalidated.empty())
2754  SymbolsIndirectlyInvalidated, Call, PSK_IndirectEscapeOnCall, &ITraits);
2755 
2756  return State;
2757 }
2758 
2759 /// evalBind - Handle the semantics of binding a value to a specific location.
2760 /// This method is used by evalStore and (soon) VisitDeclStmt, and others.
2761 void ExprEngine::evalBind(ExplodedNodeSet &Dst, const Stmt *StoreE,
2762  ExplodedNode *Pred,
2763  SVal location, SVal Val,
2764  bool atDeclInit, const ProgramPoint *PP) {
2765  const LocationContext *LC = Pred->getLocationContext();
2766  PostStmt PS(StoreE, LC);
2767  if (!PP)
2768  PP = &PS;
2769 
2770  // Do a previsit of the bind.
2771  ExplodedNodeSet CheckedSet;
2772  getCheckerManager().runCheckersForBind(CheckedSet, Pred, location, Val,
2773  StoreE, *this, *PP);
2774 
2775  StmtNodeBuilder Bldr(CheckedSet, Dst, *currBldrCtx);
2776 
2777  // If the location is not a 'Loc', it will already be handled by
2778  // the checkers. There is nothing left to do.
2779  if (!location.getAs<Loc>()) {
2780  const ProgramPoint L = PostStore(StoreE, LC, /*Loc*/nullptr,
2781  /*tag*/nullptr);
2782  ProgramStateRef state = Pred->getState();
2783  state = processPointerEscapedOnBind(state, location, Val, LC);
2784  Bldr.generateNode(L, state, Pred);
2785  return;
2786  }
2787 
2788  for (const auto PredI : CheckedSet) {
2789  ProgramStateRef state = PredI->getState();
2790 
2791  state = processPointerEscapedOnBind(state, location, Val, LC);
2792 
2793  // When binding the value, pass on the hint that this is a initialization.
2794  // For initializations, we do not need to inform clients of region
2795  // changes.
2796  state = state->bindLoc(location.castAs<Loc>(),
2797  Val, LC, /* notifyChanges = */ !atDeclInit);
2798 
2799  const MemRegion *LocReg = nullptr;
2800  if (Optional<loc::MemRegionVal> LocRegVal =
2801  location.getAs<loc::MemRegionVal>()) {
2802  LocReg = LocRegVal->getRegion();
2803  }
2804 
2805  const ProgramPoint L = PostStore(StoreE, LC, LocReg, nullptr);
2806  Bldr.generateNode(L, state, PredI);
2807  }
2808 }
2809 
2810 /// evalStore - Handle the semantics of a store via an assignment.
2811 /// @param Dst The node set to store generated state nodes
2812 /// @param AssignE The assignment expression if the store happens in an
2813 /// assignment.
2814 /// @param LocationE The location expression that is stored to.
2815 /// @param state The current simulation state
2816 /// @param location The location to store the value
2817 /// @param Val The value to be stored
2818 void ExprEngine::evalStore(ExplodedNodeSet &Dst, const Expr *AssignE,
2819  const Expr *LocationE,
2820  ExplodedNode *Pred,
2821  ProgramStateRef state, SVal location, SVal Val,
2822  const ProgramPointTag *tag) {
2823  // Proceed with the store. We use AssignE as the anchor for the PostStore
2824  // ProgramPoint if it is non-NULL, and LocationE otherwise.
2825  const Expr *StoreE = AssignE ? AssignE : LocationE;
2826 
2827  // Evaluate the location (checks for bad dereferences).
2828  ExplodedNodeSet Tmp;
2829  evalLocation(Tmp, AssignE, LocationE, Pred, state, location, false);
2830 
2831  if (Tmp.empty())
2832  return;
2833 
2834  if (location.isUndef())
2835  return;
2836 
2837  for (const auto I : Tmp)
2838  evalBind(Dst, StoreE, I, location, Val, false);
2839 }
2840 
2842  const Expr *NodeEx,
2843  const Expr *BoundEx,
2844  ExplodedNode *Pred,
2846  SVal location,
2847  const ProgramPointTag *tag,
2848  QualType LoadTy) {
2849  assert(!location.getAs<NonLoc>() && "location cannot be a NonLoc.");
2850  assert(NodeEx);
2851  assert(BoundEx);
2852  // Evaluate the location (checks for bad dereferences).
2853  ExplodedNodeSet Tmp;
2854  evalLocation(Tmp, NodeEx, BoundEx, Pred, state, location, true);
2855  if (Tmp.empty())
2856  return;
2857 
2858  StmtNodeBuilder Bldr(Tmp, Dst, *currBldrCtx);
2859  if (location.isUndef())
2860  return;
2861 
2862  // Proceed with the load.
2863  for (const auto I : Tmp) {
2864  state = I->getState();
2865  const LocationContext *LCtx = I->getLocationContext();
2866 
2867  SVal V = UnknownVal();
2868  if (location.isValid()) {
2869  if (LoadTy.isNull())
2870  LoadTy = BoundEx->getType();
2871  V = state->getSVal(location.castAs<Loc>(), LoadTy);
2872  }
2873 
2874  Bldr.generateNode(NodeEx, I, state->BindExpr(BoundEx, LCtx, V), tag,
2876  }
2877 }
2878 
2879 void ExprEngine::evalLocation(ExplodedNodeSet &Dst,
2880  const Stmt *NodeEx,
2881  const Stmt *BoundEx,
2882  ExplodedNode *Pred,
2884  SVal location,
2885  bool isLoad) {
2886  StmtNodeBuilder BldrTop(Pred, Dst, *currBldrCtx);
2887  // Early checks for performance reason.
2888  if (location.isUnknown()) {
2889  return;
2890  }
2891 
2892  ExplodedNodeSet Src;
2893  BldrTop.takeNodes(Pred);
2894  StmtNodeBuilder Bldr(Pred, Src, *currBldrCtx);
2895  if (Pred->getState() != state) {
2896  // Associate this new state with an ExplodedNode.
2897  // FIXME: If I pass null tag, the graph is incorrect, e.g for
2898  // int *p;
2899  // p = 0;
2900  // *p = 0xDEADBEEF;
2901  // "p = 0" is not noted as "Null pointer value stored to 'p'" but
2902  // instead "int *p" is noted as
2903  // "Variable 'p' initialized to a null pointer value"
2904 
2905  static SimpleProgramPointTag tag(TagProviderName, "Location");
2906  Bldr.generateNode(NodeEx, Pred, state, &tag);
2907  }
2908  ExplodedNodeSet Tmp;
2909  getCheckerManager().runCheckersForLocation(Tmp, Src, location, isLoad,
2910  NodeEx, BoundEx, *this);
2911  BldrTop.addNodes(Tmp);
2912 }
2913 
2914 std::pair<const ProgramPointTag *, const ProgramPointTag*>
2916  static SimpleProgramPointTag
2917  eagerlyAssumeBinOpBifurcationTrue(TagProviderName,
2918  "Eagerly Assume True"),
2919  eagerlyAssumeBinOpBifurcationFalse(TagProviderName,
2920  "Eagerly Assume False");
2921  return std::make_pair(&eagerlyAssumeBinOpBifurcationTrue,
2922  &eagerlyAssumeBinOpBifurcationFalse);
2923 }
2924 
2926  ExplodedNodeSet &Src,
2927  const Expr *Ex) {
2928  StmtNodeBuilder Bldr(Src, Dst, *currBldrCtx);
2929 
2930  for (const auto Pred : Src) {
2931  // Test if the previous node was as the same expression. This can happen
2932  // when the expression fails to evaluate to anything meaningful and
2933  // (as an optimization) we don't generate a node.
2934  ProgramPoint P = Pred->getLocation();
2935  if (!P.getAs<PostStmt>() || P.castAs<PostStmt>().getStmt() != Ex) {
2936  continue;
2937  }
2938 
2939  ProgramStateRef state = Pred->getState();
2940  SVal V = state->getSVal(Ex, Pred->getLocationContext());
2942  if (SEV && SEV->isExpression()) {
2943  const std::pair<const ProgramPointTag *, const ProgramPointTag*> &tags =
2945 
2946  ProgramStateRef StateTrue, StateFalse;
2947  std::tie(StateTrue, StateFalse) = state->assume(*SEV);
2948 
2949  // First assume that the condition is true.
2950  if (StateTrue) {
2951  SVal Val = svalBuilder.makeIntVal(1U, Ex->getType());
2952  StateTrue = StateTrue->BindExpr(Ex, Pred->getLocationContext(), Val);
2953  Bldr.generateNode(Ex, Pred, StateTrue, tags.first);
2954  }
2955 
2956  // Next, assume that the condition is false.
2957  if (StateFalse) {
2958  SVal Val = svalBuilder.makeIntVal(0U, Ex->getType());
2959  StateFalse = StateFalse->BindExpr(Ex, Pred->getLocationContext(), Val);
2960  Bldr.generateNode(Ex, Pred, StateFalse, tags.second);
2961  }
2962  }
2963  }
2964 }
2965 
2967  ExplodedNodeSet &Dst) {
2968  StmtNodeBuilder Bldr(Pred, Dst, *currBldrCtx);
2969  // We have processed both the inputs and the outputs. All of the outputs
2970  // should evaluate to Locs. Nuke all of their values.
2971 
2972  // FIXME: Some day in the future it would be nice to allow a "plug-in"
2973  // which interprets the inline asm and stores proper results in the
2974  // outputs.
2975 
2976  ProgramStateRef state = Pred->getState();
2977 
2978  for (const Expr *O : A->outputs()) {
2979  SVal X = state->getSVal(O, Pred->getLocationContext());
2980  assert(!X.getAs<NonLoc>()); // Should be an Lval, or unknown, undef.
2981 
2982  if (Optional<Loc> LV = X.getAs<Loc>())
2983  state = state->bindLoc(*LV, UnknownVal(), Pred->getLocationContext());
2984  }
2985 
2986  Bldr.generateNode(A, Pred, state);
2987 }
2988 
2990  ExplodedNodeSet &Dst) {
2991  StmtNodeBuilder Bldr(Pred, Dst, *currBldrCtx);
2992  Bldr.generateNode(A, Pred, Pred->getState());
2993 }
2994 
2995 //===----------------------------------------------------------------------===//
2996 // Visualization.
2997 //===----------------------------------------------------------------------===//
2998 
2999 #ifndef NDEBUG
3000 namespace llvm {
3001 
3002 template<>
3003 struct DOTGraphTraits<ExplodedGraph*> : public DefaultDOTGraphTraits {
3004  DOTGraphTraits (bool isSimple = false) : DefaultDOTGraphTraits(isSimple) {}
3005 
3006  static bool nodeHasBugReport(const ExplodedNode *N) {
3007  BugReporter &BR = static_cast<ExprEngine &>(
3008  N->getState()->getStateManager().getOwningEngine()).getBugReporter();
3009 
3010  const auto EQClasses =
3011  llvm::make_range(BR.EQClasses_begin(), BR.EQClasses_end());
3012 
3013  for (const auto &EQ : EQClasses) {
3014  for (const BugReport &Report : EQ) {
3015  if (Report.getErrorNode() == N)
3016  return true;
3017  }
3018  }
3019  return false;
3020  }
3021 
3022  /// \p PreCallback: callback before break.
3023  /// \p PostCallback: callback after break.
3024  /// \p Stop: stop iteration if returns {@code true}
3025  /// \return Whether {@code Stop} ever returned {@code true}.
3026  static bool traverseHiddenNodes(
3027  const ExplodedNode *N,
3028  llvm::function_ref<void(const ExplodedNode *)> PreCallback,
3029  llvm::function_ref<void(const ExplodedNode *)> PostCallback,
3030  llvm::function_ref<bool(const ExplodedNode *)> Stop) {
3031  const ExplodedNode *FirstHiddenNode = N;
3032  while (FirstHiddenNode->pred_size() == 1 &&
3033  isNodeHidden(*FirstHiddenNode->pred_begin())) {
3034  FirstHiddenNode = *FirstHiddenNode->pred_begin();
3035  }
3036  const ExplodedNode *OtherNode = FirstHiddenNode;
3037  while (true) {
3038  PreCallback(OtherNode);
3039  if (Stop(OtherNode))
3040  return true;
3041 
3042  if (OtherNode == N)
3043  break;
3044  PostCallback(OtherNode);
3045 
3046  OtherNode = *OtherNode->succ_begin();
3047  }
3048  return false;
3049  }
3050 
3051  static std::string getNodeAttributes(const ExplodedNode *N,
3052  ExplodedGraph *) {
3054  auto Noop = [](const ExplodedNode*){};
3055  if (traverseHiddenNodes(N, Noop, Noop, &nodeHasBugReport)) {
3056  Out.push_back("style=filled");
3057  Out.push_back("fillcolor=red");
3058  }
3059 
3060  if (traverseHiddenNodes(N, Noop, Noop,
3061  [](const ExplodedNode *C) { return C->isSink(); }))
3062  Out.push_back("color=blue");
3063  return llvm::join(Out, ",");
3064  }
3065 
3066  static bool isNodeHidden(const ExplodedNode *N) {
3067  return N->isTrivial();
3068  }
3069 
3070  static std::string getNodeLabel(const ExplodedNode *N, ExplodedGraph *G){
3071  std::string Buf;
3072  llvm::raw_string_ostream Out(Buf);
3073 
3074  const bool IsDot = true;
3075  const unsigned int Space = 1;
3076  ProgramStateRef State = N->getState();
3077 
3078  Out << "{ \"node_id\": " << N->getID(G) << ", \"pointer\": \""
3079  << (const void *)N << "\", \"state_id\": " << State->getID()
3080  << ", \"has_report\": " << (nodeHasBugReport(N) ? "true" : "false")
3081  << ",\\l";
3082 
3083  Indent(Out, Space, IsDot) << "\"program_points\": [\\l";
3084 
3085  // Dump program point for all the previously skipped nodes.
3086  traverseHiddenNodes(
3087  N,
3088  [&](const ExplodedNode *OtherNode) {
3089  Indent(Out, Space + 1, IsDot) << "{ ";
3090  OtherNode->getLocation().printJson(Out, /*NL=*/"\\l");
3091  Out << ", \"tag\": ";
3092  if (const ProgramPointTag *Tag = OtherNode->getLocation().getTag())
3093  Out << '\"' << Tag->getTagDescription() << "\" }";
3094  else
3095  Out << "null }";
3096  },
3097  // Adds a comma and a new-line between each program point.
3098  [&](const ExplodedNode *) { Out << ",\\l"; },
3099  [&](const ExplodedNode *) { return false; });
3100 
3101  Out << "\\l"; // Adds a new-line to the last program point.
3102  Indent(Out, Space, IsDot) << "],\\l";
3103 
3104  bool SameAsAllPredecessors =
3105  std::all_of(N->pred_begin(), N->pred_end(), [&](const ExplodedNode *P) {
3106  return P->getState() == State;
3107  });
3108 
3109  if (!SameAsAllPredecessors) {
3110  State->printDOT(Out, N->getLocationContext(), Space);
3111  } else {
3112  Indent(Out, Space, IsDot) << "\"program_state\": null";
3113  }
3114 
3115  Out << "\\l}";
3116  if (!N->succ_empty())
3117  Out << ',';
3118  Out << "\\l";
3119 
3120  return Out.str();
3121  }
3122 };
3123 
3124 } // namespace llvm
3125 #endif
3126 
3127 void ExprEngine::ViewGraph(bool trim) {
3128 #ifndef NDEBUG
3129  std::string Filename = DumpGraph(trim);
3130  llvm::DisplayGraph(Filename, false, llvm::GraphProgram::DOT);
3131 #endif
3132  llvm::errs() << "Warning: viewing graph requires assertions" << "\n";
3133 }
3134 
3135 
3137 #ifndef NDEBUG
3138  std::string Filename = DumpGraph(Nodes);
3139  llvm::DisplayGraph(Filename, false, llvm::GraphProgram::DOT);
3140 #endif
3141  llvm::errs() << "Warning: viewing graph requires assertions" << "\n";
3142 }
3143 
3144 std::string ExprEngine::DumpGraph(bool trim, StringRef Filename) {
3145 #ifndef NDEBUG
3146  if (trim) {
3147  std::vector<const ExplodedNode *> Src;
3148 
3149  // Iterate through the reports and get their nodes.
3151  EI = BR.EQClasses_begin(), EE = BR.EQClasses_end(); EI != EE; ++EI) {
3152  const auto *N = const_cast<ExplodedNode *>(EI->begin()->getErrorNode());
3153  if (N) Src.push_back(N);
3154  }
3155  return DumpGraph(Src, Filename);
3156  } else {
3157  return llvm::WriteGraph(&G, "ExprEngine", /*ShortNames=*/false,
3158  /*Title=*/"Exploded Graph", /*Filename=*/Filename);
3159  }
3160 #endif
3161  llvm::errs() << "Warning: dumping graph requires assertions" << "\n";
3162  return "";
3163 }
3164 
3166  StringRef Filename) {
3167 #ifndef NDEBUG
3168  std::unique_ptr<ExplodedGraph> TrimmedG(G.trim(Nodes));
3169 
3170  if (!TrimmedG.get()) {
3171  llvm::errs() << "warning: Trimmed ExplodedGraph is empty.\n";
3172  } else {
3173  return llvm::WriteGraph(TrimmedG.get(), "TrimmedExprEngine",
3174  /*ShortNames=*/false,
3175  /*Title=*/"Trimmed Exploded Graph",
3176  /*Filename=*/Filename);
3177  }
3178 #endif
3179  llvm::errs() << "Warning: dumping graph requires assertions" << "\n";
3180  return "";
3181 }
3182 
3184  static int index = 0;
3185  return &index;
3186 }
void processEndWorklist() override
Called by CoreEngine when the analysis worklist has terminated.
Definition: ExprEngine.cpp:630
bool isBaseInitializer() const
Determine whether this initializer is initializing a base class.
Definition: DeclCXX.h:2402
Defines the clang::ASTContext interface.
Represents C++ allocator call.
Definition: CFG.h:239
This represents a GCC inline-assembly statement extension.
Definition: Stmt.h:2830
TypedValueRegion - An abstract class representing regions having a typed value.
Definition: MemRegion.h:529
ProgramStateRef processRegionChange(ProgramStateRef state, const MemRegion *MR, const LocationContext *LCtx)
Definition: SubEngine.h:145
Expr * getInit() const
Get the initializer.
Definition: DeclCXX.h:2531
void VisitArraySubscriptExpr(const ArraySubscriptExpr *Ex, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitArraySubscriptExpr - Transfer function for array accesses.
void ProcessInitializer(const CFGInitializer I, ExplodedNode *Pred)
Definition: ExprEngine.cpp:823
SVal evalDerivedToBase(SVal Derived, const CastExpr *Cast)
Evaluates a chain of derived-to-base casts through the path specified in Cast.
Definition: Store.cpp:248
A (possibly-)qualified type.
Definition: Type.h:643
MemRegion - The root abstract class for all memory regions.
Definition: MemRegion.h:94
Static storage duration.
Definition: Specifiers.h:309
bool isArrayType() const
Definition: Type.h:6407
void markLive(SymbolRef sym)
Unconditionally marks a symbol as live.
bool isMemberPointerType() const
Definition: Type.h:6389
ValueDecl * getMemberDecl() const
Retrieve the member declaration to which this expression refers.
Definition: Expr.h:2892
void markInfeasible(bool branch)
Definition: CoreEngine.h:465
const Expr * skipRValueSubobjectAdjustments(SmallVectorImpl< const Expr *> &CommaLHS, SmallVectorImpl< SubobjectAdjustment > &Adjustments) const
Walk outwards from an expression we want to bind a reference to and find the expression whose lifetim...
Definition: Expr.cpp:76
const Stmt * getStmt() const
Definition: CFG.h:132
bool IsTemporaryCtorOrDtor
This call is a constructor or a destructor of a temporary value.
Definition: ExprEngine.h:106
bool operator==(CanQual< T > x, CanQual< U > y)
static bool nodeHasBugReport(const ExplodedNode *N)
bool isCForbiddenLValueType() const
Determine whether expressions of the given type are forbidden from being lvalues in C...
Definition: Type.h:6307
unsigned blockCount() const
Returns the number of times the current basic block has been visited on the exploded graph path...
Definition: CoreEngine.h:220
DominatorTree GraphTraits specialization so the DominatorTree can be iterable by generic graph iterat...
Definition: Dominators.h:29
void VisitCallExpr(const CallExpr *CE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitCall - Transfer function for function calls.
Stmt - This represents one statement.
Definition: Stmt.h:66
Information about invalidation for a particular region/symbol.
Definition: MemRegion.h:1439
This builder class is useful for generating nodes that resulted from visiting a statement.
Definition: CoreEngine.h:378
void VisitCXXBindTemporaryExpr(const CXXBindTemporaryExpr *BTE, ExplodedNodeSet &PreVisit, ExplodedNodeSet &Dst)
C Language Family Type Representation.
Defines the SourceManager interface.
static bool nodeHasBugReport(const ExplodedNode *N)
static const Stmt * getRightmostLeaf(const Stmt *Condition)
Expr * getBase() const
Definition: Expr.h:2886
void VisitMSAsmStmt(const MSAsmStmt *A, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitMSAsmStmt - Transfer function logic for MS inline asm.
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:88
Represents a point when we begin processing an inlined call.
Definition: ProgramPoint.h:630
Defines the PrettyStackTraceEntry class, which is used to make crashes give more contextual informati...
FunctionDecl * getOperatorNew() const
Definition: ExprCXX.h:2119
bool isVirtual() const
Determines whether the base class is a virtual base class (or not).
Definition: DeclCXX.h:245
IntrusiveRefCntPtr< const ProgramState > ProgramStateRef
ExprEngine(cross_tu::CrossTranslationUnitContext &CTU, AnalysisManager &mgr, SetOfConstDecls *VisitedCalleesIn, FunctionSummariesTy *FS, InliningModes HowToInlineIn)
Definition: ExprEngine.cpp:205
StringRef P
const CastExpr * BasePath
Definition: Expr.h:71
SVal evalBinOp(ProgramStateRef state, BinaryOperator::Opcode op, NonLoc L, NonLoc R, QualType T)
Definition: ExprEngine.h:584
void processBranch(const Stmt *Condition, NodeBuilderContext &BuilderCtx, ExplodedNode *Pred, ExplodedNodeSet &Dst, const CFGBlock *DstT, const CFGBlock *DstF) override
ProcessBranch - Called by CoreEngine.
The pointer has been passed to a function indirectly.
void ViewGraph(bool trim=false)
Visualize the ExplodedGraph created by executing the simulation.
void processCleanupTemporaryBranch(const CXXBindTemporaryExpr *BTE, NodeBuilderContext &BldCtx, ExplodedNode *Pred, ExplodedNodeSet &Dst, const CFGBlock *DstT, const CFGBlock *DstF) override
Called by CoreEngine.
Represents C++ object destructor generated from a call to delete.
Definition: CFG.h:408
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Definition: Type.h:2829
Hints for figuring out of a call should be inlined during evalCall().
Definition: ExprEngine.h:96
Represents a program point just before an implicit call event.
Definition: ProgramPoint.h:583
bool IsArrayCtorOrDtor
This call is a constructor or a destructor for a single element within an array, a part of array cons...
Definition: ExprEngine.h:103
void ProcessMemberDtor(const CFGMemberDtor D, ExplodedNode *Pred, ExplodedNodeSet &Dst)
StorageDuration
The storage duration for an object (per C++ [basic.stc]).
Definition: Specifiers.h:305
void runCheckersForPrintStateJson(raw_ostream &Out, ProgramStateRef State, const char *NL="\, unsigned int Space=0, bool IsDot=false) const
Run checkers for debug-printing a ProgramState.
T castAs() const
Convert to the specified CFGElement type, asserting that this CFGElement is of the desired type...
Definition: CFG.h:98
const ProgramStateRef & getState() const
DOTGraphTraits(bool isSimple=false)
void processCFGBlockEntrance(const BlockEdge &L, NodeBuilderWithSinks &nodeBuilder, ExplodedNode *Pred) override
Called by CoreEngine when processing the entrance of a CFGBlock.
Represents a point when we exit a loop.
Definition: ProgramPoint.h:713
ProgramStateRef getInitialState(const LocationContext *InitLoc) override
getInitialState - Return the initial state used for the root vertex in the ExplodedGraph.
Definition: ExprEngine.cpp:239
const CXXDestructorDecl * getDestructorDecl(ASTContext &astContext) const
Definition: CFG.cpp:4803
static void printObjectsUnderConstructionJson(raw_ostream &Out, ProgramStateRef State, const char *NL, const LocationContext *LCtx, unsigned int Space=0, bool IsDot=false)
Definition: ExprEngine.cpp:562
bool isIndirectMemberInitializer() const
Definition: DeclCXX.h:2414
bool isConsumedExpr(Expr *E) const
Definition: ParentMap.cpp:159
void VisitUnaryOperator(const UnaryOperator *B, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitUnaryOperator - Transfer function logic for unary operators.
void takeNodes(const ExplodedNodeSet &S)
Definition: CoreEngine.h:329
Represents a variable declaration or definition.
Definition: Decl.h:812
ProgramStateRef notifyCheckersOfPointerEscape(ProgramStateRef State, const InvalidatedSymbols *Invalidated, ArrayRef< const MemRegion *> ExplicitRegions, const CallEvent *Call, RegionAndSymbolInvalidationTraits &ITraits) override
Call PointerEscape callback when a value escapes as a result of region invalidation.
ASTContext & getASTContext() const
REGISTER_TRAIT_WITH_PROGRAMSTATE(ObjectsUnderConstruction, ObjectsUnderConstructionMap) static const char *TagProviderName
const T * getAs() const
Member-template getAs<specific type>&#39;.
Definition: Type.h:6818
void ProcessDeleteDtor(const CFGDeleteDtor D, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Definition: ExprEngine.cpp:991
loc::MemRegionVal getCXXThis(const CXXMethodDecl *D, const StackFrameContext *SFC)
Return a memory region for the &#39;this&#39; object reference.
static Optional< SVal > getObjectUnderConstruction(ProgramStateRef State, const ConstructionContextItem &Item, const LocationContext *LC)
By looking at a certain item that may be potentially part of an object&#39;s ConstructionContext, retrieve such object&#39;s location.
Definition: ExprEngine.cpp:481
void evalStore(ExplodedNodeSet &Dst, const Expr *AssignE, const Expr *StoreE, ExplodedNode *Pred, ProgramStateRef St, SVal TargetLV, SVal Val, const ProgramPointTag *tag=nullptr)
evalStore - Handle the semantics of a store via an assignment.
bool isUnrolledState(ProgramStateRef State)
Returns if the given State indicates that is inside a completely unrolled loop.
const ElementRegion * GetElementZeroRegion(const SubRegion *R, QualType T)
Definition: Store.cpp:67
void enqueue(ExplodedNodeSet &Set)
Enqueue the given set of nodes onto the work list.
Definition: CoreEngine.cpp:572
const internal::VariadicDynCastAllOfMatcher< Decl, VarDecl > varDecl
Matches variable declarations.
const Stmt * getTriggerStmt() const
Definition: CFG.h:393
Describes how types, statements, expressions, and declarations should be printed. ...
Definition: PrettyPrinter.h:37
Defines the Objective-C statement AST node classes.
void removeDead(ExplodedNode *Node, ExplodedNodeSet &Out, const Stmt *ReferenceStmt, const LocationContext *LC, const Stmt *DiagnosticStmt=nullptr, ProgramPoint::Kind K=ProgramPoint::PreStmtPurgeDeadSymbolsKind)
Run the analyzer&#39;s garbage collection - remove dead symbols and bindings from the state...
Definition: ExprEngine.cpp:696
ProgramStateRef removeDeadBindings(ProgramStateRef St, const StackFrameContext *LCtx, SymbolReaper &SymReaper)
Represents a parameter to a function.
Definition: Decl.h:1564
Defines the clang::Expr interface and subclasses for C++ expressions.
long i
Definition: xmmintrin.h:1456
void VisitCXXThisExpr(const CXXThisExpr *TE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
BoundNodesTreeBuilder Nodes
static bool shouldRemoveDeadBindings(AnalysisManager &AMgr, const Stmt *S, const ExplodedNode *Pred, const LocationContext *LC)
Definition: ExprEngine.cpp:670
void ProcessTemporaryDtor(const CFGTemporaryDtor D, ExplodedNode *Pred, ExplodedNodeSet &Dst)
void ProcessLoopExit(const Stmt *S, ExplodedNode *Pred)
Definition: ExprEngine.cpp:805
void runCheckersForLocation(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, SVal location, bool isLoad, const Stmt *NodeEx, const Stmt *BoundEx, ExprEngine &Eng)
Run checkers for load/store of a location.
Symbolic value.
Definition: SymExpr.h:29
bool haveEqualEnvironments(ProgramStateRef S1, ProgramStateRef S2) const
Definition: ProgramState.h:560
ProgramStateRef runCheckersForPointerEscape(ProgramStateRef State, const InvalidatedSymbols &Escaped, const CallEvent *Call, PointerEscapeKind Kind, RegionAndSymbolInvalidationTraits *ITraits)
Run checkers when pointers escape.
One of these records is kept for each identifier that is lexed.
A pointer escapes due to binding its value to a location that the analyzer cannot track...
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:154
LineState State
void runCheckersForLiveSymbols(ProgramStateRef state, SymbolReaper &SymReaper)
Run checkers for live symbols.
void printJson(raw_ostream &Out, PrinterHelper *Helper, const PrintingPolicy &Policy, bool AddQuotes) const
Pretty-prints in JSON format.
SourceLocation getBeginLoc() const LLVM_READONLY
Definition: Stmt.cpp:263
Represents a member of a struct/union/class.
Definition: Decl.h:2605
Represents a program point after a store evaluation.
Definition: ProgramPoint.h:431
Represents C++ object destructor implicitly generated for automatic object or temporary bound to cons...
Definition: CFG.h:383
bool haveEqualStores(ProgramStateRef S1, ProgramStateRef S2) const
Definition: ProgramState.h:564
ProgramStateRef processLoopEnd(const Stmt *LoopStmt, ProgramStateRef State)
Updates the given ProgramState.
bool isReferenceType() const
Definition: Type.h:6363
void ProcessImplicitDtor(const CFGImplicitDtor D, ExplodedNode *Pred)
Definition: ExprEngine.cpp:911
bool isAllEnumCasesCovered() const
Returns true if the SwitchStmt is a switch of an enum value and all cases have been explicitly covere...
Definition: Stmt.h:2149
void addPredecessor(ExplodedNode *V, ExplodedGraph &G)
addPredeccessor - Adds a predecessor to the current node, and in tandem add this node as a successor ...
i32 captured_struct **param SharedsTy A type which contains references the shared variables *param Shareds Context with the list of shared variables from the p *TaskFunction *param Data Additional data for task generation like final * state
const StackFrameContext * getStackFrame() const
Definition: ProgramPoint.h:183
bool isIntegralOrEnumerationType() const
Determine whether this type is an integral or enumeration type.
Definition: Type.h:6714
void enableNodeReclamation(unsigned Interval)
Enable tracking of recently allocated nodes for potential reclamation when calling reclaimRecentlyAll...
ProgramStateRef processPointerEscapedOnBind(ProgramStateRef State, SVal Loc, SVal Val, const LocationContext *LCtx) override
Call PointerEscape callback when a value escapes as a result of bind.
bool isGLValue() const
Definition: Expr.h:261
static bool isLocType(QualType T)
Definition: SVals.h:329
void VisitOffsetOfExpr(const OffsetOfExpr *Ex, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitOffsetOfExpr - Transfer function for offsetof.
This is a meta program point, which should be skipped by all the diagnostic reasoning etc...
Definition: ProgramPoint.h:732
ProgramStateRef updateLoopStack(const Stmt *LoopStmt, ASTContext &ASTCtx, ExplodedNode *Pred, unsigned maxVisitOnPath)
Updates the stack of loops contained by the ProgramState.
ExplodedNode * generateSink(const Stmt *S, ExplodedNode *Pred, ProgramStateRef St, const ProgramPointTag *tag=nullptr, ProgramPoint::Kind K=ProgramPoint::PostStmtKind)
Definition: CoreEngine.h:417
enum clang::SubobjectAdjustment::@47 Kind
SourceLocation getBeginLoc() const LLVM_READONLY
Definition: ExprCXX.h:1304
Forward-declares and imports various common LLVM datatypes that clang wants to use unqualified...
STATISTIC(NumRemoveDeadBindings, "The # of times RemoveDeadBindings is called")
const LocationContext * getLocationContext() const
ExplodedNode * generateCaseStmtNode(const iterator &I, ProgramStateRef State)
Definition: CoreEngine.cpp:662
virtual bool inTopFrame() const
Return true if the current LocationContext has no caller context.
const clang::PrintingPolicy & getPrintingPolicy() const
Definition: ASTContext.h:657
static bool isRecordType(QualType T)
const LocationContext * getParent() const
A builtin binary operation expression such as "x + y" or "x <= y".
Definition: Expr.h:3407
bool isUnknown() const
Definition: SVals.h:136
If a crash happens while one of these objects are live, the message is printed out along with the spe...
void VisitReturnStmt(const ReturnStmt *R, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitReturnStmt - Transfer function logic for return statements.
const VarDecl * getVarDecl() const
Definition: CFG.h:388
CaseStmt - Represent a case statement.
Definition: Stmt.h:1456
const CXXBaseSpecifier * getBaseSpecifier() const
Definition: CFG.h:439
bool isAnyMemberInitializer() const
Definition: DeclCXX.h:2410
An adjustment to be made to the temporary created when emitting a reference binding, which accesses a particular subobject of that temporary.
Definition: Expr.h:63
void ProcessNewAllocator(const CXXNewExpr *NE, ExplodedNode *Pred)
Definition: ExprEngine.cpp:938
void ProcessAutomaticObjDtor(const CFGAutomaticObjDtor D, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Definition: ExprEngine.cpp:957
Represents binding an expression to a temporary.
Definition: ExprCXX.h:1277
virtual SVal getLValueField(const FieldDecl *D, SVal Base)
Definition: Store.h:145
FieldDecl * getAnyMember() const
Definition: DeclCXX.h:2475
void VisitDeclStmt(const DeclStmt *DS, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitDeclStmt - Transfer function logic for DeclStmts.
CXXDestructorDecl * getDestructor() const
Returns the destructor decl for this class.
Definition: DeclCXX.cpp:1724
FieldDecl * getMember() const
If this is a member initializer, returns the declaration of the non-static data member being initiali...
Definition: DeclCXX.h:2469
RangeSelector node(std::string ID)
Selects a node, including trailing semicolon (for non-expression statements).
void runCheckersForEndFunction(NodeBuilderContext &BC, ExplodedNodeSet &Dst, ExplodedNode *Pred, ExprEngine &Eng, const ReturnStmt *RS)
Run checkers on end of function.
reverse_iterator rend()
Definition: CFG.h:727
void processStaticInitializer(const DeclStmt *DS, NodeBuilderContext &BuilderCtx, ExplodedNode *Pred, ExplodedNodeSet &Dst, const CFGBlock *DstT, const CFGBlock *DstF) override
Called by CoreEngine.
const CFGBlock * getCallSiteBlock() const
void evalBind(ExplodedNodeSet &Dst, const Stmt *StoreE, ExplodedNode *Pred, SVal location, SVal Val, bool atDeclInit=false, const ProgramPoint *PP=nullptr)
evalBind - Handle the semantics of binding a value to a specific location.
CheckerManager & getCheckerManager() const
Definition: ExprEngine.h:190
void VisitLogicalExpr(const BinaryOperator *B, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitLogicalExpr - Transfer function logic for &#39;&&&#39;, &#39;||&#39;.
bool isArrayForm() const
Definition: ExprCXX.h:2287
CXXCtorInitializer * getInitializer() const
Definition: CFG.h:224
void removeDeadOnEndOfFunction(NodeBuilderContext &BC, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Remove dead bindings/symbols before exiting a function.
void runCheckersForBind(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, SVal location, SVal val, const Stmt *S, ExprEngine &Eng, const ProgramPoint &PP)
Run checkers for binding of a value to a location.
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Definition: Type.cpp:1636
const FieldDecl * getFieldDecl() const
Definition: CFG.h:460
const Stmt * getCallSite() const
Expr ** getSubExprs()
Definition: Expr.h:5866
void VisitCXXCatchStmt(const CXXCatchStmt *CS, ExplodedNode *Pred, ExplodedNodeSet &Dst)
bool isDelegatingInitializer() const
Determine whether this initializer is creating a delegating constructor.
Definition: DeclCXX.h:2430
StringRef Filename
Definition: Format.cpp:1709
const CXXBindTemporaryExpr * getBindTemporaryExpr() const
Definition: CFG.h:481
Represents a single basic block in a source-level CFG.
Definition: CFG.h:570
void VisitInitListExpr(const InitListExpr *E, ExplodedNode *Pred, ExplodedNodeSet &Dst)
llvm::APSInt EvaluateKnownConstInt(const ASTContext &Ctx, SmallVectorImpl< PartialDiagnosticAt > *Diag=nullptr) const
EvaluateKnownConstInt - Call EvaluateAsRValue and return the folded integer.
InliningModes
The modes of inlining, which override the default analysis-wide settings.
Definition: ExprEngine.h:87
SymbolicRegion - A special, "non-concrete" region.
Definition: MemRegion.h:763
void runCheckersForPostStmt(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const Stmt *S, ExprEngine &Eng, bool wasInlined=false)
Run checkers for post-visiting Stmts.
static unsigned getNumSubExprs(AtomicOp Op)
Determine the number of arguments the specified atomic builtin should have.
Definition: Expr.cpp:4423
void ProcessBaseDtor(const CFGBaseDtor D, ExplodedNode *Pred, ExplodedNodeSet &Dst)
DefinedOrUnknownSVal makeZeroVal(QualType type)
Construct an SVal representing &#39;0&#39; for the specified type.
Definition: SValBuilder.cpp:52
void processSwitch(SwitchNodeBuilder &builder) override
ProcessSwitch - Called by CoreEngine.
void processBeginOfFunction(NodeBuilderContext &BC, ExplodedNode *Pred, ExplodedNodeSet &Dst, const BlockEdge &L) override
Called by CoreEngine.
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Definition: Decl.h:636
This represents one expression.
Definition: Expr.h:108
Defines the clang::LangOptions interface.
void VisitLvalObjCIvarRefExpr(const ObjCIvarRefExpr *DR, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Transfer function logic for computing the lvalue of an Objective-C ivar.
void VisitCXXNewExpr(const CXXNewExpr *CNE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
void VisitCXXNewAllocatorCall(const CXXNewExpr *CNE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
const Expr * getCondition() const
Definition: CoreEngine.h:570
CallEventRef getCaller(const StackFrameContext *CalleeCtx, ProgramStateRef State)
Gets an outside caller given a callee context.
Definition: CallEvent.cpp:1362
void VisitCast(const CastExpr *CastE, const Expr *Ex, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitCast - Transfer function logic for all casts (implicit and explicit).
#define V(N, I)
Definition: ASTContext.h:2912
Represents a C++ destructor within a class.
Definition: DeclCXX.h:2825
const internal::VariadicAllOfMatcher< Decl > decl
Matches declarations.
This is the simplest builder which generates nodes in the ExplodedGraph.
Definition: CoreEngine.h:236
void Add(ExplodedNode *N)
The pointer has been passed to a function call directly.
struct DTB DerivedToBase
Definition: Expr.h:81
Expr * getRHS()
Definition: Stmt.h:1557
QualType getConditionType() const
Definition: SValBuilder.h:160
bool isValid() const
Definition: SVals.h:148
const LocationContext * getLocationContext() const
Definition: CoreEngine.h:574
bool inTopFrame() const override
Return true if the current LocationContext has no caller context.
void Visit(const Stmt *S, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Visit - Transfer function logic for all statements.
void FlushReports()
Generate and flush diagnostics for all bug reports.
Defines the clang::IdentifierInfo, clang::IdentifierTable, and clang::Selector interfaces.
static std::pair< const ProgramPointTag *, const ProgramPointTag * > geteagerlyAssumeBinOpBifurcationTags()
QualType getType() const
Definition: Expr.h:137
The reason for pointer escape is unknown.
ASTContext & getContext() const
getContext - Return the ASTContext associated with this analysis.
Definition: ExprEngine.h:182
Traits for storing the call processing policy inside GDM.
Definition: ExprEngine.h:859
DeclContext * getParent()
getParent - Returns the containing DeclContext.
Definition: DeclBase.h:1772
ReturnStmt - This represents a return, optionally of an expression: return; return 4;...
Definition: Stmt.h:2588
void VisitAtomicExpr(const AtomicExpr *E, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitAtomicExpr - Transfer function for builtin atomic expressions.
This represents a Microsoft inline-assembly statement extension.
Definition: Stmt.h:3053
const SwitchStmt * getSwitch() const
Definition: CoreEngine.h:560
void evalLoad(ExplodedNodeSet &Dst, const Expr *NodeEx, const Expr *BoundExpr, ExplodedNode *Pred, ProgramStateRef St, SVal location, const ProgramPointTag *tag=nullptr, QualType LoadTy=QualType())
Simulate a read of the result of Ex.
Represents C++ object destructor implicitly generated for base object in destructor.
Definition: CFG.h:434
QualType getDestroyedType() const
Retrieve the type being destroyed.
Definition: ExprCXX.cpp:224
const Expr * getSubExpr() const
Definition: ExprCXX.h:1300
bool isNull() const
Return true if this QualType doesn&#39;t point to a type yet.
Definition: Type.h:708
reverse_iterator rbegin()
Definition: CFG.h:726
virtual ProgramStateRef removeDeadBindings(ProgramStateRef state, SymbolReaper &SymReaper)=0
Scan all symbols referenced by the constraints.
Optional< T > getAs() const
Convert to the specified SVal type, returning None if this SVal is not of the desired type...
Definition: SVals.h:111
const MemRegion * getRegion() const
Get the underlining region.
Definition: SVals.h:605
ExplodedNode * generateNode(const iterator &I, ProgramStateRef State, bool isSink=false)
Definition: CoreEngine.cpp:643
While alive, includes the current analysis stack in a crash trace.
void processEndOfFunction(NodeBuilderContext &BC, ExplodedNode *Pred, const ReturnStmt *RS=nullptr) override
Called by CoreEngine.
Thread storage duration.
Definition: Specifiers.h:308
Expr * getArgument()
Definition: ExprCXX.h:2302
static const Stmt * ResolveCondition(const Stmt *Condition, const CFGBlock *B)
Kind getKind() const
Definition: CFG.h:118
void processCFGElement(const CFGElement E, ExplodedNode *Pred, unsigned StmtIdx, NodeBuilderContext *Ctx) override
processCFGElement - Called by CoreEngine.
Definition: ExprEngine.cpp:634
ProgramStateRef getInitialState(const LocationContext *InitLoc)
const LocationContext * getLocationContext() const
Definition: CoreEngine.h:520
const Stmt * getStmt() const
Definition: ProgramPoint.h:279
void VisitGuardedExpr(const Expr *Ex, const Expr *L, const Expr *R, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitGuardedExpr - Transfer function logic for ?, __builtin_choose.
void printJson(raw_ostream &Out, ProgramStateRef State, const LocationContext *LCtx, const char *NL, unsigned int Space, bool IsDot) const override
printJson - Called by ProgramStateManager to print checker-specific data.
Definition: ExprEngine.cpp:608
DefinedOrUnknownSVal conjureSymbolVal(const void *symbolTag, const Expr *expr, const LocationContext *LCtx, unsigned count)
Create a new symbol with a unique &#39;name&#39;.
ProgramStateRef getWidenedLoopState(ProgramStateRef PrevState, const LocationContext *LCtx, unsigned BlockCount, const Stmt *LoopStmt)
Get the states that result from widening the loop.
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of enums...
Definition: Type.h:4449
void runCheckersForBranchCondition(const Stmt *condition, ExplodedNodeSet &Dst, ExplodedNode *Pred, ExprEngine &Eng)
Run checkers for branch condition.
T castAs() const
Convert to the specified ProgramPoint type, asserting that this ProgramPoint is of the desired type...
Definition: ProgramPoint.h:140
static bool isCallStmt(const Stmt *S)
Returns true if this is a statement is a function or method call of some kind.
Definition: CallEvent.cpp:441
ProgramPoints can be "tagged" as representing points specific to a given analysis entity...
Definition: ProgramPoint.h:39
AnalysisManager & getAnalysisManager() override
Definition: ExprEngine.h:184
std::string getNameAsString() const
Get a human-readable name for the declaration, even if it is one of the special kinds of names (C++ c...
Definition: Decl.h:291
void evalEagerlyAssumeBinOpBifurcation(ExplodedNodeSet &Dst, ExplodedNodeSet &Src, const Expr *Ex)
evalEagerlyAssumeBinOpBifurcation - Given the nodes in &#39;Src&#39;, eagerly assume symbolic expressions of ...
const MemRegion * getAsRegion() const
Definition: SVals.cpp:151
Represents a new-expression for memory allocation and constructor calls, e.g: "new CXXNewExpr(foo)"...
Definition: ExprCXX.h:2000
SourceLocation getBeginLoc() const
Definition: ExprCXX.h:2240
Expr * getLHS()
Definition: Stmt.h:1545
CallEventManager & getCallEventManager()
Definition: ProgramState.h:526
DeclStmt - Adaptor class for mixing declarations with statements and expressions. ...
Definition: Stmt.h:1196
void VisitCompoundLiteralExpr(const CompoundLiteralExpr *CL, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitCompoundLiteralExpr - Transfer function logic for compound literals.
Represents the declaration of a label.
Definition: Decl.h:468
ExplodedNode * generateNode(ProgramStateRef State, ExplodedNode *Pred, const ProgramPointTag *Tag=nullptr)
Definition: CoreEngine.h:353
void processIndirectGoto(IndirectGotoNodeBuilder &builder) override
processIndirectGoto - Called by CoreEngine.
QualType getBaseElementType(const ArrayType *VAT) const
Return the innermost element type of an array type.
const CXXTempObjectRegion * getCXXTempObjectRegion(Expr const *Ex, LocationContext const *LC)
Definition: MemRegion.cpp:1044
Expr * getCond()
Definition: Stmt.h:2055
void VisitCXXDeleteExpr(const CXXDeleteExpr *CDE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
bool IsCtorOrDtorWithImproperlyModeledTargetRegion
This call is a constructor or a destructor for which we do not currently compute the this-region corr...
Definition: ExprEngine.h:99
ProgramPoint getLocation() const
getLocation - Returns the edge associated with the given node.
SVal - This represents a symbolic expression, which can be either an L-value or an R-value...
Definition: SVals.h:75
int64_t getID(const ASTContext &Context) const
Definition: Stmt.cpp:288
const ArrayType * getAsArrayType(QualType T) const
Type Query functions.
AtomicExpr - Variadic atomic builtins: __atomic_exchange, __atomic_fetch_*, __atomic_load, __atomic_store, and __atomic_compare_exchange_*, for the similarly-named C++11 instructions, and __c11 variants for <stdatomic.h>, and corresponding __opencl_atomic_* for OpenCL 2.0.
Definition: Expr.h:5799
CanQualType VoidTy
Definition: ASTContext.h:1014
void VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *Ex, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitUnaryExprOrTypeTraitExpr - Transfer function for sizeof.
ProgramStateRef runCheckersForEvalAssume(ProgramStateRef state, SVal Cond, bool Assumption)
Run checkers for handling assumptions on symbolic values.
ImplicitCastExpr - Allows us to explicitly represent implicit type conversions, which have no direct ...
Definition: Expr.h:3247
BugReporter & getBugReporter()
Definition: ExprEngine.h:196
void VisitObjCForCollectionStmt(const ObjCForCollectionStmt *S, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitObjCForCollectionStmt - Transfer function logic for ObjCForCollectionStmt.
A class responsible for cleaning up unused symbols.
bool operator<(DeclarationName LHS, DeclarationName RHS)
Ordering on two declaration names.
void runCheckersForPreStmt(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const Stmt *S, ExprEngine &Eng)
Run checkers for pre-visiting Stmts.
bool isVectorType() const
Definition: Type.h:6443
bool isStmtBranch() const
Definition: CFG.h:533
ProgramStateRef getPersistentStateWithGDM(ProgramStateRef FromState, ProgramStateRef GDMState)
void insert(const ExplodedNodeSet &S)
Optional< T > getAs() const
Convert to the specified CFGElement type, returning None if this CFGElement is not of the desired typ...
Definition: CFG.h:109
Defines various enumerations that describe declaration and type specifiers.
StringRef getName() const
Return the actual identifier string.
ast_type_traits::DynTypedNode Node
CanQualType CharTy
Definition: ASTContext.h:1016
void runCheckersForDeadSymbols(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, SymbolReaper &SymReaper, const Stmt *S, ExprEngine &Eng, ProgramPoint::Kind K)
Run checkers for dead symbols.
Dataflow Directional Tag Classes.
void ProcessStmt(const Stmt *S, ExplodedNode *Pred)
Definition: ExprEngine.cpp:775
ExplodedNode * generateDefaultCaseNode(ProgramStateRef State, bool isSink=false)
Definition: CoreEngine.cpp:677
SValBuilder & getSValBuilder()
Definition: ExprEngine.h:194
Represents a delete expression for memory deallocation and destructor calls, e.g. ...
Definition: ExprCXX.h:2260
void addNodes(const ExplodedNodeSet &S)
Definition: CoreEngine.h:335
StoreManager & getStoreManager()
Definition: ExprEngine.h:386
Represents a program point just after an implicit call event.
Definition: ProgramPoint.h:600
ProgramStateRef processRegionChanges(ProgramStateRef state, const InvalidatedSymbols *invalidated, ArrayRef< const MemRegion *> ExplicitRegions, ArrayRef< const MemRegion *> Regions, const LocationContext *LCtx, const CallEvent *Call) override
processRegionChanges - Called by ProgramStateManager whenever a change is made to the store...
Definition: ExprEngine.cpp:550
SourceLocation getSourceLocation() const
Determine the source location of the initializer.
Definition: DeclCXX.cpp:2342
void VisitCXXDestructor(QualType ObjectType, const MemRegion *Dest, const Stmt *S, bool IsBaseDtor, ExplodedNode *Pred, ExplodedNodeSet &Dst, const EvalCallOptions &Options)
const NodeBuilderContext & getContext()
Definition: CoreEngine.h:326
std::unique_ptr< DiagnosticConsumer > create(StringRef OutputFile, DiagnosticOptions *Diags, bool MergeChildRecords=false)
Returns a DiagnosticConsumer that serializes diagnostics to a bitcode file.
This node builder keeps track of the generated sink nodes.
Definition: CoreEngine.h:341
bool isPurgeKind()
Is this a program point corresponding to purge/removal of dead symbols and bindings.
Definition: ProgramPoint.h:171
StmtClass getStmtClass() const
Definition: Stmt.h:1080
void reclaimRecentlyAllocatedNodes()
Reclaim "uninteresting" nodes created since the last time this method was called. ...
void VisitLambdaExpr(const LambdaExpr *LE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitLambdaExpr - Transfer function logic for LambdaExprs.
const Decl * getSingleDecl() const
Definition: Stmt.h:1211
Represents symbolic expression that isn&#39;t a location.
Definition: SVals.h:349
Stmt * getTerminatorStmt()
Definition: CFG.h:860
BranchNodeBuilder is responsible for constructing the nodes corresponding to the two branches of the ...
Definition: CoreEngine.h:430
Represents an abstract call to a function or method along a particular path.
Definition: CallEvent.h:170
ProgramStateRef getState() const
Definition: CoreEngine.h:572
const Stmt * getLoopStmt() const
Definition: CFG.h:269
ProgramStateManager & getStateManager() override
Definition: ExprEngine.h:384
This class is used for tools that requires cross translation unit capability.
const Decl * getDecl() const
const CXXDeleteExpr * getDeleteExpr() const
Definition: CFG.h:418
Represents a single point (AST node) in the program that requires attention during construction of an...
Expr * IgnoreParenImpCasts() LLVM_READONLY
Skip past any parentheses and implicit casts which might surround this expression until reaching a fi...
Definition: Expr.cpp:2917
const CXXTempObjectRegion * getCXXStaticTempObjectRegion(const Expr *Ex)
Create a CXXTempObjectRegion for temporaries which are lifetime-extended by static references...
Definition: MemRegion.cpp:967
PointerEscapeKind
Describes the different reasons a pointer escapes during analysis.
SwitchStmt - This represents a &#39;switch&#39; stmt.
Definition: Stmt.h:1995
SourceLocation getBeginLoc() const
Definition: ExprCXX.h:2311
unsigned getIntWidth(QualType T) const
Expr * IgnoreImplicit() LLVM_READONLY
Skip past any implicit AST nodes which might surround this expression until reaching a fixed point...
Definition: Expr.cpp:2909
void runCheckersForEndAnalysis(ExplodedGraph &G, BugReporter &BR, ExprEngine &Eng)
Run checkers for end of analysis.
T castAs() const
Convert to the specified SVal type, asserting that this SVal is of the desired type.
Definition: SVals.h:103
ArraySubscriptExpr - [C99 6.5.2.1] Array Subscripting.
Definition: Expr.h:2434
ExplodedNode * generateSink(ProgramStateRef State, ExplodedNode *Pred, const ProgramPointTag *Tag=nullptr)
Definition: CoreEngine.h:360
SubRegion - A region that subsets another larger region.
Definition: MemRegion.h:435
Represents a C++ base or member initializer.
Definition: DeclCXX.h:2333
void VisitCXXConstructExpr(const CXXConstructExpr *E, ExplodedNode *Pred, ExplodedNodeSet &Dst)
void VisitObjCAtSynchronizedStmt(const ObjCAtSynchronizedStmt *S, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Transfer function logic for ObjCAtSynchronizedStmts.
IndirectFieldDecl * getIndirectMember() const
Definition: DeclCXX.h:2483
const LocationContext * getLocationContext() const
Definition: ProgramPoint.h:179
void VisitObjCMessage(const ObjCMessageExpr *ME, ExplodedNode *Pred, ExplodedNodeSet &Dst)
bool hasStackStorage() const
Definition: MemRegion.cpp:1140
const StackFrameContext * getStackFrame() const
void printJson(raw_ostream &Out, const char *NL="\, unsigned int Space=0, bool IsDot=false, std::function< void(const LocationContext *)> printMoreInfoPerContext=[](const LocationContext *) {}) const
llvm::FoldingSet< BugReportEquivClass >::iterator EQClasses_iterator
Iterator over the set of BugReports tracked by the BugReporter.
Definition: BugReporter.h:467
Represents a base class of a C++ class.
Definition: DeclCXX.h:192
Stores options for the analyzer from the command line.
void getCaptureFields(llvm::DenseMap< const VarDecl *, FieldDecl *> &Captures, FieldDecl *&ThisCapture) const
For a closure type, retrieve the mapping from captured variables and this to the non-static data memb...
Definition: DeclCXX.cpp:1404
uint64_t getTypeSize(QualType T) const
Return the size of the specified (complete) type T, in bits.
Definition: ASTContext.h:2079
outputs_range outputs()
Definition: Stmt.h:2804
X
Add a minimal nested name specifier fixit hint to allow lookup of a tag name from an outer enclosing ...
Definition: SemaDecl.cpp:14125
ExplodedNode * generateNode(const ProgramPoint &PP, ProgramStateRef State, ExplodedNode *Pred)
Generates a node in the ExplodedGraph.
Definition: CoreEngine.h:289
const CXXNewExpr * getAllocatorExpr() const
Definition: CFG.h:245
void VisitBlockExpr(const BlockExpr *BE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitBlockExpr - Transfer function logic for BlockExprs.
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate.h) and friends (in DeclFriend.h).
MemberExpr - [C99 6.5.2.3] Structure and Union Members.
Definition: Expr.h:2809
Defines the clang::SourceLocation class and associated facilities.
Represents a C++ struct/union/class.
Definition: DeclCXX.h:300
bool isVoidType() const
Definition: Type.h:6610
Represents C++ object destructor implicitly generated by compiler on various occasions.
Definition: CFG.h:358
ProgramStateRef getState() const
Definition: CoreEngine.h:518
pred_iterator pred_begin()
ExplodedNode * generateNode(ProgramStateRef State, bool branch, ExplodedNode *Pred)
Definition: CoreEngine.cpp:629
Represents a top-level expression in a basic block.
Definition: CFG.h:55
This class is used for builtin types like &#39;int&#39;.
Definition: Type.h:2408
ProgramStateRef processAssume(ProgramStateRef state, SVal cond, bool assumption) override
evalAssume - Callback function invoked by the ConstraintManager when making assumptions about state v...
Definition: ExprEngine.cpp:544
Represents C++ object destructor implicitly generated for member object in destructor.
Definition: CFG.h:455
const MemRegion * getBaseRegion() const
Definition: MemRegion.cpp:1160
FieldDecl * Field
Definition: Expr.h:82
ExplodedNode * generateNode(const Stmt *S, ExplodedNode *Pred, ProgramStateRef St, const ProgramPointTag *tag=nullptr, ProgramPoint::Kind K=ProgramPoint::PostStmtKind)
Definition: CoreEngine.h:407
bool isUndef() const
Definition: SVals.h:140
static Decl::Kind getKind(const Decl *D)
Definition: DeclBase.cpp:943
ProgramStateRef runCheckersForRegionChanges(ProgramStateRef state, const InvalidatedSymbols *invalidated, ArrayRef< const MemRegion *> ExplicitRegions, ArrayRef< const MemRegion *> Regions, const LocationContext *LCtx, const CallEvent *Call)
Run checkers for region changes.
std::string DumpGraph(bool trim=false, StringRef Filename="")
Dump graph to the specified filename.
void runCheckersForBeginFunction(ExplodedNodeSet &Dst, const BlockEdge &L, ExplodedNode *Pred, ExprEngine &Eng)
Run checkers on beginning of function.
void VisitCommonDeclRefExpr(const Expr *DR, const NamedDecl *D, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Transfer function logic for DeclRefExprs and BlockDeclRefExprs.
raw_ostream & Indent(raw_ostream &Out, const unsigned int Space, bool IsDot)
Definition: JsonSupport.h:19
A reference to a declared variable, function, enum, etc.
Definition: Expr.h:1143
result[0]
Definition: emmintrin.h:120
Represents C++ base or member initializer from constructor&#39;s initialization list. ...
Definition: CFG.h:219
void VisitGCCAsmStmt(const GCCAsmStmt *A, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitGCCAsmStmt - Transfer function logic for inline asm.
const StackFrameContext * getStackFrame() const
void VisitMemberExpr(const MemberExpr *M, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitMemberExpr - Transfer function for member expressions.
QualType getType() const
Definition: Decl.h:647
ProgramStateRef escapeValue(ProgramStateRef State, SVal V, PointerEscapeKind K) const
A simple wrapper when you only need to notify checkers of pointer-escape of a single value...
llvm::ImmutableMap< ConstructedObjectKey, SVal > ObjectsUnderConstructionMap
Definition: ExprEngine.cpp:195
This represents a decl that may have a name.
Definition: Decl.h:248
Optional< T > getAs() const
Convert to the specified ProgramPoint type, returning None if this ProgramPoint is not of the desired...
Definition: ProgramPoint.h:151
ConstraintManager & getConstraintManager()
Definition: ExprEngine.h:388
void VisitBinaryOperator(const BinaryOperator *B, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitBinaryOperator - Transfer function logic for binary operators.
Definition: ExprEngineC.cpp:40
CFGTerminator getTerminator() const
Definition: CFG.h:858
AnalysisDeclContext * getAnalysisDeclContext() const
bool isFeasible(bool branch)
Definition: CoreEngine.h:472
void CreateCXXTemporaryObject(const MaterializeTemporaryExpr *ME, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Create a C++ temporary object for an rvalue.
static SVal RecoverCastedSymbol(ProgramStateRef state, const Stmt *Condition, const LocationContext *LCtx, ASTContext &Ctx)
RecoverCastedSymbol - A helper function for ProcessBranch that is used to try to recover some path-se...
const Expr * getTarget() const
Definition: CoreEngine.h:516
Represents C++ object destructor implicitly generated at the end of full expression for temporary obj...
Definition: CFG.h:476
const CFGBlock * getBlock() const
Return the CFGBlock associated with this builder.
Definition: CoreEngine.h:216
int64_t getID(const ASTContext &Context) const
Definition: DeclCXX.cpp:2323
bool isUnknownOrUndef() const
Definition: SVals.h:144
Expr * IgnoreParens() LLVM_READONLY
Skip past any parentheses which might surround this expression until reaching a fixed point...
Definition: Expr.cpp:2913
QualType getType() const
Retrieves the type of the base class.
Definition: DeclCXX.h:291
Represents the point where a loop ends.
Definition: CFG.h:265