clang  7.0.0svn
ExprEngineCallAndReturn.cpp
Go to the documentation of this file.
1 //=-- ExprEngineCallAndReturn.cpp - Support for call/return -----*- C++ -*-===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file defines ExprEngine's support for calls and returns.
11 //
12 //===----------------------------------------------------------------------===//
13 
17 #include "clang/AST/DeclCXX.h"
22 #include "llvm/ADT/SmallSet.h"
23 #include "llvm/ADT/Statistic.h"
24 #include "llvm/Support/SaveAndRestore.h"
25 
26 using namespace clang;
27 using namespace ento;
28 
29 #define DEBUG_TYPE "ExprEngine"
30 
31 STATISTIC(NumOfDynamicDispatchPathSplits,
32  "The # of times we split the path due to imprecise dynamic dispatch info");
33 
34 STATISTIC(NumInlinedCalls,
35  "The # of times we inlined a call");
36 
37 STATISTIC(NumReachedInlineCountMax,
38  "The # of times we reached inline count maximum");
39 
41  ExplodedNode *Pred) {
42  // Get the entry block in the CFG of the callee.
43  const StackFrameContext *calleeCtx = CE.getCalleeContext();
44  PrettyStackTraceLocationContext CrashInfo(calleeCtx);
45  const CFGBlock *Entry = CE.getEntry();
46 
47  // Validate the CFG.
48  assert(Entry->empty());
49  assert(Entry->succ_size() == 1);
50 
51  // Get the solitary successor.
52  const CFGBlock *Succ = *(Entry->succ_begin());
53 
54  // Construct an edge representing the starting location in the callee.
55  BlockEdge Loc(Entry, Succ, calleeCtx);
56 
57  ProgramStateRef state = Pred->getState();
58 
59  // Construct a new node, notify checkers that analysis of the function has
60  // begun, and add the resultant nodes to the worklist.
61  bool isNew;
62  ExplodedNode *Node = G.getNode(Loc, state, false, &isNew);
63  Node->addPredecessor(Pred, G);
64  if (isNew) {
65  ExplodedNodeSet DstBegin;
66  processBeginOfFunction(BC, Node, DstBegin, Loc);
67  Engine.enqueue(DstBegin);
68  }
69 }
70 
71 // Find the last statement on the path to the exploded node and the
72 // corresponding Block.
73 static std::pair<const Stmt*,
75  const Stmt *S = nullptr;
76  const CFGBlock *Blk = nullptr;
77  const StackFrameContext *SF =
79 
80  // Back up through the ExplodedGraph until we reach a statement node in this
81  // stack frame.
82  while (Node) {
83  const ProgramPoint &PP = Node->getLocation();
84 
85  if (PP.getLocationContext()->getCurrentStackFrame() == SF) {
86  if (Optional<StmtPoint> SP = PP.getAs<StmtPoint>()) {
87  S = SP->getStmt();
88  break;
89  } else if (Optional<CallExitEnd> CEE = PP.getAs<CallExitEnd>()) {
90  S = CEE->getCalleeContext()->getCallSite();
91  if (S)
92  break;
93 
94  // If there is no statement, this is an implicitly-generated call.
95  // We'll walk backwards over it and then continue the loop to find
96  // an actual statement.
98  do {
99  Node = Node->getFirstPred();
100  CE = Node->getLocationAs<CallEnter>();
101  } while (!CE || CE->getCalleeContext() != CEE->getCalleeContext());
102 
103  // Continue searching the graph.
104  } else if (Optional<BlockEdge> BE = PP.getAs<BlockEdge>()) {
105  Blk = BE->getSrc();
106  }
107  } else if (Optional<CallEnter> CE = PP.getAs<CallEnter>()) {
108  // If we reached the CallEnter for this function, it has no statements.
109  if (CE->getCalleeContext() == SF)
110  break;
111  }
112 
113  if (Node->pred_empty())
114  return std::make_pair(nullptr, nullptr);
115 
116  Node = *Node->pred_begin();
117  }
118 
119  return std::make_pair(S, Blk);
120 }
121 
122 /// Adjusts a return value when the called function's return type does not
123 /// match the caller's expression type. This can happen when a dynamic call
124 /// is devirtualized, and the overriding method has a covariant (more specific)
125 /// return type than the parent's method. For C++ objects, this means we need
126 /// to add base casts.
127 static SVal adjustReturnValue(SVal V, QualType ExpectedTy, QualType ActualTy,
128  StoreManager &StoreMgr) {
129  // For now, the only adjustments we handle apply only to locations.
130  if (!V.getAs<Loc>())
131  return V;
132 
133  // If the types already match, don't do any unnecessary work.
134  ExpectedTy = ExpectedTy.getCanonicalType();
135  ActualTy = ActualTy.getCanonicalType();
136  if (ExpectedTy == ActualTy)
137  return V;
138 
139  // No adjustment is needed between Objective-C pointer types.
140  if (ExpectedTy->isObjCObjectPointerType() &&
141  ActualTy->isObjCObjectPointerType())
142  return V;
143 
144  // C++ object pointers may need "derived-to-base" casts.
145  const CXXRecordDecl *ExpectedClass = ExpectedTy->getPointeeCXXRecordDecl();
146  const CXXRecordDecl *ActualClass = ActualTy->getPointeeCXXRecordDecl();
147  if (ExpectedClass && ActualClass) {
148  CXXBasePaths Paths(/*FindAmbiguities=*/true, /*RecordPaths=*/true,
149  /*DetectVirtual=*/false);
150  if (ActualClass->isDerivedFrom(ExpectedClass, Paths) &&
151  !Paths.isAmbiguous(ActualTy->getCanonicalTypeUnqualified())) {
152  return StoreMgr.evalDerivedToBase(V, Paths.front());
153  }
154  }
155 
156  // Unfortunately, Objective-C does not enforce that overridden methods have
157  // covariant return types, so we can't assert that that never happens.
158  // Be safe and return UnknownVal().
159  return UnknownVal();
160 }
161 
163  ExplodedNode *Pred,
164  ExplodedNodeSet &Dst) {
165  // Find the last statement in the function and the corresponding basic block.
166  const Stmt *LastSt = nullptr;
167  const CFGBlock *Blk = nullptr;
168  std::tie(LastSt, Blk) = getLastStmt(Pred);
169  if (!Blk || !LastSt) {
170  Dst.Add(Pred);
171  return;
172  }
173 
174  // Here, we destroy the current location context. We use the current
175  // function's entire body as a diagnostic statement, with which the program
176  // point will be associated. However, we only want to use LastStmt as a
177  // reference for what to clean up if it's a ReturnStmt; otherwise, everything
178  // is dead.
179  SaveAndRestore<const NodeBuilderContext *> NodeContextRAII(currBldrCtx, &BC);
180  const LocationContext *LCtx = Pred->getLocationContext();
181  removeDead(Pred, Dst, dyn_cast<ReturnStmt>(LastSt), LCtx,
182  LCtx->getAnalysisDeclContext()->getBody(),
184 }
185 
187  const StackFrameContext *calleeCtx) {
188  const Decl *RuntimeCallee = calleeCtx->getDecl();
189  const Decl *StaticDecl = Call->getDecl();
190  assert(RuntimeCallee);
191  if (!StaticDecl)
192  return true;
193  return RuntimeCallee->getCanonicalDecl() != StaticDecl->getCanonicalDecl();
194 }
195 
196 /// Returns true if the CXXConstructExpr \p E was intended to construct a
197 /// prvalue for the region in \p V.
198 ///
199 /// Note that we can't just test for rvalue vs. glvalue because
200 /// CXXConstructExprs embedded in DeclStmts and initializers are considered
201 /// rvalues by the AST, and the analyzer would like to treat them as lvalues.
202 static bool isTemporaryPRValue(const CXXConstructExpr *E, SVal V) {
203  if (E->isGLValue())
204  return false;
205 
206  const MemRegion *MR = V.getAsRegion();
207  if (!MR)
208  return false;
209 
210  return isa<CXXTempObjectRegion>(MR);
211 }
212 
213 /// The call exit is simulated with a sequence of nodes, which occur between
214 /// CallExitBegin and CallExitEnd. The following operations occur between the
215 /// two program points:
216 /// 1. CallExitBegin (triggers the start of call exit sequence)
217 /// 2. Bind the return value
218 /// 3. Run Remove dead bindings to clean up the dead symbols from the callee.
219 /// 4. CallExitEnd (switch to the caller context)
220 /// 5. PostStmt<CallExpr>
222  // Step 1 CEBNode was generated before the call.
224  const StackFrameContext *calleeCtx =
226 
227  // The parent context might not be a stack frame, so make sure we
228  // look up the first enclosing stack frame.
229  const StackFrameContext *callerCtx =
230  calleeCtx->getParent()->getCurrentStackFrame();
231 
232  const Stmt *CE = calleeCtx->getCallSite();
233  ProgramStateRef state = CEBNode->getState();
234  // Find the last statement in the function and the corresponding basic block.
235  const Stmt *LastSt = nullptr;
236  const CFGBlock *Blk = nullptr;
237  std::tie(LastSt, Blk) = getLastStmt(CEBNode);
238 
239  // Generate a CallEvent /before/ cleaning the state, so that we can get the
240  // correct value for 'this' (if necessary).
242  CallEventRef<> Call = CEMgr.getCaller(calleeCtx, state);
243 
244  // Step 2: generate node with bound return value: CEBNode -> BindedRetNode.
245 
246  // If the callee returns an expression, bind its value to CallExpr.
247  if (CE) {
248  if (const ReturnStmt *RS = dyn_cast_or_null<ReturnStmt>(LastSt)) {
249  const LocationContext *LCtx = CEBNode->getLocationContext();
250  SVal V = state->getSVal(RS, LCtx);
251 
252  // Ensure that the return type matches the type of the returned Expr.
253  if (wasDifferentDeclUsedForInlining(Call, calleeCtx)) {
254  QualType ReturnedTy =
255  CallEvent::getDeclaredResultType(calleeCtx->getDecl());
256  if (!ReturnedTy.isNull()) {
257  if (const Expr *Ex = dyn_cast<Expr>(CE)) {
258  V = adjustReturnValue(V, Ex->getType(), ReturnedTy,
259  getStoreManager());
260  }
261  }
262  }
263 
264  state = state->BindExpr(CE, callerCtx, V);
265  }
266 
267  // Bind the constructed object value to CXXConstructExpr.
268  if (const CXXConstructExpr *CCE = dyn_cast<CXXConstructExpr>(CE)) {
269  loc::MemRegionVal This =
270  svalBuilder.getCXXThis(CCE->getConstructor()->getParent(), calleeCtx);
271  SVal ThisV = state->getSVal(This);
272 
273  // If the constructed object is a temporary prvalue, get its bindings.
274  if (isTemporaryPRValue(CCE, ThisV))
275  ThisV = state->getSVal(ThisV.castAs<Loc>());
276 
277  state = state->BindExpr(CCE, callerCtx, ThisV);
278  }
279 
280  if (const auto *CNE = dyn_cast<CXXNewExpr>(CE)) {
281  // We are currently evaluating a CXXNewAllocator CFGElement. It takes a
282  // while to reach the actual CXXNewExpr element from here, so keep the
283  // region for later use.
284  // Additionally cast the return value of the inlined operator new
285  // (which is of type 'void *') to the correct object type.
286  SVal AllocV = state->getSVal(CNE, callerCtx);
287  AllocV = svalBuilder.evalCast(
288  AllocV, CNE->getType(),
289  getContext().getPointerType(getContext().VoidTy));
290 
291  state =
292  setCXXNewAllocatorValue(state, CNE, calleeCtx->getParent(), AllocV);
293  }
294  }
295 
296  // Step 3: BindedRetNode -> CleanedNodes
297  // If we can find a statement and a block in the inlined function, run remove
298  // dead bindings before returning from the call. This is important to ensure
299  // that we report the issues such as leaks in the stack contexts in which
300  // they occurred.
301  ExplodedNodeSet CleanedNodes;
302  if (LastSt && Blk && AMgr.options.AnalysisPurgeOpt != PurgeNone) {
303  static SimpleProgramPointTag retValBind("ExprEngine", "Bind Return Value");
304  PostStmt Loc(LastSt, calleeCtx, &retValBind);
305  bool isNew;
306  ExplodedNode *BindedRetNode = G.getNode(Loc, state, false, &isNew);
307  BindedRetNode->addPredecessor(CEBNode, G);
308  if (!isNew)
309  return;
310 
311  NodeBuilderContext Ctx(getCoreEngine(), Blk, BindedRetNode);
312  currBldrCtx = &Ctx;
313  // Here, we call the Symbol Reaper with 0 statement and callee location
314  // context, telling it to clean up everything in the callee's context
315  // (and its children). We use the callee's function body as a diagnostic
316  // statement, with which the program point will be associated.
317  removeDead(BindedRetNode, CleanedNodes, nullptr, calleeCtx,
318  calleeCtx->getAnalysisDeclContext()->getBody(),
320  currBldrCtx = nullptr;
321  } else {
322  CleanedNodes.Add(CEBNode);
323  }
324 
325  for (ExplodedNodeSet::iterator I = CleanedNodes.begin(),
326  E = CleanedNodes.end(); I != E; ++I) {
327 
328  // Step 4: Generate the CallExit and leave the callee's context.
329  // CleanedNodes -> CEENode
330  CallExitEnd Loc(calleeCtx, callerCtx);
331  bool isNew;
332  ProgramStateRef CEEState = (*I == CEBNode) ? state : (*I)->getState();
333 
334  ExplodedNode *CEENode = G.getNode(Loc, CEEState, false, &isNew);
335  CEENode->addPredecessor(*I, G);
336  if (!isNew)
337  return;
338 
339  // Step 5: Perform the post-condition check of the CallExpr and enqueue the
340  // result onto the work list.
341  // CEENode -> Dst -> WorkList
342  NodeBuilderContext Ctx(Engine, calleeCtx->getCallSiteBlock(), CEENode);
343  SaveAndRestore<const NodeBuilderContext*> NBCSave(currBldrCtx,
344  &Ctx);
345  SaveAndRestore<unsigned> CBISave(currStmtIdx, calleeCtx->getIndex());
346 
347  CallEventRef<> UpdatedCall = Call.cloneWithState(CEEState);
348 
349  ExplodedNodeSet DstPostCall;
350  if (const CXXNewExpr *CNE = dyn_cast_or_null<CXXNewExpr>(CE)) {
351  ExplodedNodeSet DstPostPostCallCallback;
352  getCheckerManager().runCheckersForPostCall(DstPostPostCallCallback,
353  CEENode, *UpdatedCall, *this,
354  /*WasInlined=*/true);
355  for (auto I : DstPostPostCallCallback) {
357  CNE, getCXXNewAllocatorValue(I->getState(), CNE,
358  calleeCtx->getParent()),
359  DstPostCall, I, *this,
360  /*WasInlined=*/true);
361  }
362  } else {
363  getCheckerManager().runCheckersForPostCall(DstPostCall, CEENode,
364  *UpdatedCall, *this,
365  /*WasInlined=*/true);
366  }
367  ExplodedNodeSet Dst;
368  if (const ObjCMethodCall *Msg = dyn_cast<ObjCMethodCall>(Call)) {
369  getCheckerManager().runCheckersForPostObjCMessage(Dst, DstPostCall, *Msg,
370  *this,
371  /*WasInlined=*/true);
372  } else if (CE &&
373  !(isa<CXXNewExpr>(CE) && // Called when visiting CXXNewExpr.
375  getCheckerManager().runCheckersForPostStmt(Dst, DstPostCall, CE,
376  *this, /*WasInlined=*/true);
377  } else {
378  Dst.insert(DstPostCall);
379  }
380 
381  // Enqueue the next element in the block.
382  for (ExplodedNodeSet::iterator PSI = Dst.begin(), PSE = Dst.end();
383  PSI != PSE; ++PSI) {
384  Engine.getWorkList()->enqueue(*PSI, calleeCtx->getCallSiteBlock(),
385  calleeCtx->getIndex()+1);
386  }
387  }
388 }
389 
390 void ExprEngine::examineStackFrames(const Decl *D, const LocationContext *LCtx,
391  bool &IsRecursive, unsigned &StackDepth) {
392  IsRecursive = false;
393  StackDepth = 0;
394 
395  while (LCtx) {
396  if (const StackFrameContext *SFC = dyn_cast<StackFrameContext>(LCtx)) {
397  const Decl *DI = SFC->getDecl();
398 
399  // Mark recursive (and mutually recursive) functions and always count
400  // them when measuring the stack depth.
401  if (DI == D) {
402  IsRecursive = true;
403  ++StackDepth;
404  LCtx = LCtx->getParent();
405  continue;
406  }
407 
408  // Do not count the small functions when determining the stack depth.
409  AnalysisDeclContext *CalleeADC = AMgr.getAnalysisDeclContext(DI);
410  const CFG *CalleeCFG = CalleeADC->getCFG();
411  if (CalleeCFG->getNumBlockIDs() > AMgr.options.getAlwaysInlineSize())
412  ++StackDepth;
413  }
414  LCtx = LCtx->getParent();
415  }
416 }
417 
418 // The GDM component containing the dynamic dispatch bifurcation info. When
419 // the exact type of the receiver is not known, we want to explore both paths -
420 // one on which we do inline it and the other one on which we don't. This is
421 // done to ensure we do not drop coverage.
422 // This is the map from the receiver region to a bool, specifying either we
423 // consider this region's information precise or not along the given path.
424 namespace {
426  DynamicDispatchModeInlined = 1,
427  DynamicDispatchModeConservative
428  };
429 } // end anonymous namespace
430 
431 REGISTER_TRAIT_WITH_PROGRAMSTATE(DynamicDispatchBifurcationMap,
433  unsigned))
434 
435 bool ExprEngine::inlineCall(const CallEvent &Call, const Decl *D,
436  NodeBuilder &Bldr, ExplodedNode *Pred,
438  assert(D);
439 
440  const LocationContext *CurLC = Pred->getLocationContext();
441  const StackFrameContext *CallerSFC = CurLC->getCurrentStackFrame();
442  const LocationContext *ParentOfCallee = CallerSFC;
443  if (Call.getKind() == CE_Block &&
444  !cast<BlockCall>(Call).isConversionFromLambda()) {
445  const BlockDataRegion *BR = cast<BlockCall>(Call).getBlockRegion();
446  assert(BR && "If we have the block definition we should have its region");
447  AnalysisDeclContext *BlockCtx = AMgr.getAnalysisDeclContext(D);
448  ParentOfCallee = BlockCtx->getBlockInvocationContext(CallerSFC,
449  cast<BlockDecl>(D),
450  BR);
451  }
452 
453  // This may be NULL, but that's fine.
454  const Expr *CallE = Call.getOriginExpr();
455 
456  // Construct a new stack frame for the callee.
457  AnalysisDeclContext *CalleeADC = AMgr.getAnalysisDeclContext(D);
458  const StackFrameContext *CalleeSFC =
459  CalleeADC->getStackFrame(ParentOfCallee, CallE,
460  currBldrCtx->getBlock(),
461  currStmtIdx);
462 
463  CallEnter Loc(CallE, CalleeSFC, CurLC);
464 
465  // Construct a new state which contains the mapping from actual to
466  // formal arguments.
467  State = State->enterStackFrame(Call, CalleeSFC);
468 
469  bool isNew;
470  if (ExplodedNode *N = G.getNode(Loc, State, false, &isNew)) {
471  N->addPredecessor(Pred, G);
472  if (isNew)
473  Engine.getWorkList()->enqueue(N);
474  }
475 
476  // If we decided to inline the call, the successor has been manually
477  // added onto the work list so remove it from the node builder.
478  Bldr.takeNodes(Pred);
479 
480  NumInlinedCalls++;
481  Engine.FunctionSummaries->bumpNumTimesInlined(D);
482 
483  // Mark the decl as visited.
484  if (VisitedCallees)
485  VisitedCallees->insert(D);
486 
487  return true;
488 }
489 
491  const Stmt *CallE) {
492  const void *ReplayState = State->get<ReplayWithoutInlining>();
493  if (!ReplayState)
494  return nullptr;
495 
496  assert(ReplayState == CallE && "Backtracked to the wrong call.");
497  (void)CallE;
498 
499  return State->remove<ReplayWithoutInlining>();
500 }
501 
503  ExplodedNodeSet &dst) {
504  // Perform the previsit of the CallExpr.
505  ExplodedNodeSet dstPreVisit;
506  getCheckerManager().runCheckersForPreStmt(dstPreVisit, Pred, CE, *this);
507 
508  // Get the call in its initial state. We use this as a template to perform
509  // all the checks.
511  CallEventRef<> CallTemplate
512  = CEMgr.getSimpleCall(CE, Pred->getState(), Pred->getLocationContext());
513 
514  // Evaluate the function call. We try each of the checkers
515  // to see if the can evaluate the function call.
516  ExplodedNodeSet dstCallEvaluated;
517  for (ExplodedNodeSet::iterator I = dstPreVisit.begin(), E = dstPreVisit.end();
518  I != E; ++I) {
519  evalCall(dstCallEvaluated, *I, *CallTemplate);
520  }
521 
522  // Finally, perform the post-condition check of the CallExpr and store
523  // the created nodes in 'Dst'.
524  // Note that if the call was inlined, dstCallEvaluated will be empty.
525  // The post-CallExpr check will occur in processCallExit.
526  getCheckerManager().runCheckersForPostStmt(dst, dstCallEvaluated, CE,
527  *this);
528 }
529 
531  const CallEvent &Call) {
532  // WARNING: At this time, the state attached to 'Call' may be older than the
533  // state in 'Pred'. This is a minor optimization since CheckerManager will
534  // use an updated CallEvent instance when calling checkers, but if 'Call' is
535  // ever used directly in this function all callers should be updated to pass
536  // the most recent state. (It is probably not worth doing the work here since
537  // for some callers this will not be necessary.)
538 
539  // Run any pre-call checks using the generic call interface.
540  ExplodedNodeSet dstPreVisit;
541  getCheckerManager().runCheckersForPreCall(dstPreVisit, Pred, Call, *this);
542 
543  // Actually evaluate the function call. We try each of the checkers
544  // to see if the can evaluate the function call, and get a callback at
545  // defaultEvalCall if all of them fail.
546  ExplodedNodeSet dstCallEvaluated;
547  getCheckerManager().runCheckersForEvalCall(dstCallEvaluated, dstPreVisit,
548  Call, *this);
549 
550  // Finally, run any post-call checks.
551  getCheckerManager().runCheckersForPostCall(Dst, dstCallEvaluated,
552  Call, *this);
553 }
554 
556  const LocationContext *LCtx,
558  const Expr *E = Call.getOriginExpr();
559  if (!E)
560  return State;
561 
562  // Some method families have known return values.
563  if (const ObjCMethodCall *Msg = dyn_cast<ObjCMethodCall>(&Call)) {
564  switch (Msg->getMethodFamily()) {
565  default:
566  break;
567  case OMF_autorelease:
568  case OMF_retain:
569  case OMF_self: {
570  // These methods return their receivers.
571  return State->BindExpr(E, LCtx, Msg->getReceiverSVal());
572  }
573  }
574  } else if (const CXXConstructorCall *C = dyn_cast<CXXConstructorCall>(&Call)){
575  SVal ThisV = C->getCXXThisVal();
576 
577  // If the constructed object is a temporary prvalue, get its bindings.
578  if (isTemporaryPRValue(cast<CXXConstructExpr>(E), ThisV))
579  ThisV = State->getSVal(ThisV.castAs<Loc>());
580 
581  return State->BindExpr(E, LCtx, ThisV);
582  }
583 
584  SVal R;
585  QualType ResultTy = Call.getResultType();
586  unsigned Count = currBldrCtx->blockCount();
587  if (auto RTC = getCurrentCFGElement().getAs<CFGCXXRecordTypedCall>()) {
588  // Conjure a temporary if the function returns an object by value.
589  MemRegionManager &MRMgr = svalBuilder.getRegionManager();
590  const CXXTempObjectRegion *TR = MRMgr.getCXXTempObjectRegion(E, LCtx);
591  State = addAllNecessaryTemporaryInfo(State, RTC->getConstructionContext(),
592  LCtx, TR);
593 
594  // Invalidate the region so that it didn't look uninitialized. Don't notify
595  // the checkers.
596  State = State->invalidateRegions(TR, E, Count, LCtx,
597  /* CausedByPointerEscape=*/false, nullptr,
598  &Call, nullptr);
599 
600  R = State->getSVal(TR, E->getType());
601  } else {
602  // Conjure a symbol if the return value is unknown.
603 
604  // See if we need to conjure a heap pointer instead of
605  // a regular unknown pointer.
606  bool IsHeapPointer = false;
607  if (const auto *CNE = dyn_cast<CXXNewExpr>(E))
608  if (CNE->getOperatorNew()->isReplaceableGlobalAllocationFunction()) {
609  // FIXME: Delegate this to evalCall in MallocChecker?
610  IsHeapPointer = true;
611  }
612 
613  R = IsHeapPointer ? svalBuilder.getConjuredHeapSymbolVal(E, LCtx, Count)
614  : svalBuilder.conjureSymbolVal(nullptr, E, LCtx, ResultTy,
615  Count);
616  }
617  return State->BindExpr(E, LCtx, R);
618 }
619 
620 // Conservatively evaluate call by invalidating regions and binding
621 // a conjured return value.
622 void ExprEngine::conservativeEvalCall(const CallEvent &Call, NodeBuilder &Bldr,
623  ExplodedNode *Pred,
625  State = Call.invalidateRegions(currBldrCtx->blockCount(), State);
626  State = bindReturnValue(Call, Pred->getLocationContext(), State);
627 
628  // And make the result node.
629  Bldr.generateNode(Call.getProgramPoint(), State, Pred);
630 }
631 
632 ExprEngine::CallInlinePolicy
633 ExprEngine::mayInlineCallKind(const CallEvent &Call, const ExplodedNode *Pred,
634  AnalyzerOptions &Opts,
635  const ExprEngine::EvalCallOptions &CallOpts) {
636  const LocationContext *CurLC = Pred->getLocationContext();
637  const StackFrameContext *CallerSFC = CurLC->getCurrentStackFrame();
638  switch (Call.getKind()) {
639  case CE_Function:
640  case CE_Block:
641  break;
642  case CE_CXXMember:
645  return CIP_DisallowedAlways;
646  break;
647  case CE_CXXConstructor: {
649  return CIP_DisallowedAlways;
650 
651  const CXXConstructorCall &Ctor = cast<CXXConstructorCall>(Call);
652 
653  const CXXConstructExpr *CtorExpr = Ctor.getOriginExpr();
654 
655  auto CCE = getCurrentCFGElement().getAs<CFGConstructor>();
656  const ConstructionContext *CC = CCE ? CCE->getConstructionContext()
657  : nullptr;
658 
659  if (CC && isa<NewAllocatedObjectConstructionContext>(CC) &&
660  !Opts.mayInlineCXXAllocator())
661  return CIP_DisallowedOnce;
662 
663  // FIXME: We don't handle constructors or destructors for arrays properly.
664  // Even once we do, we still need to be careful about implicitly-generated
665  // initializers for array fields in default move/copy constructors.
666  // We still allow construction into ElementRegion targets when they don't
667  // represent array elements.
668  if (CallOpts.IsArrayCtorOrDtor)
669  return CIP_DisallowedOnce;
670 
671  // Inlining constructors requires including initializers in the CFG.
672  const AnalysisDeclContext *ADC = CallerSFC->getAnalysisDeclContext();
673  assert(ADC->getCFGBuildOptions().AddInitializers && "No CFG initializers");
674  (void)ADC;
675 
676  // If the destructor is trivial, it's always safe to inline the constructor.
677  if (Ctor.getDecl()->getParent()->hasTrivialDestructor())
678  break;
679 
680  // For other types, only inline constructors if destructor inlining is
681  // also enabled.
683  return CIP_DisallowedAlways;
684 
685  if (CtorExpr->getConstructionKind() == CXXConstructExpr::CK_Complete) {
686  // If we don't handle temporary destructors, we shouldn't inline
687  // their constructors.
688  if (CallOpts.IsTemporaryCtorOrDtor &&
690  return CIP_DisallowedOnce;
691 
692  // If we did not find the correct this-region, it would be pointless
693  // to inline the constructor. Instead we will simply invalidate
694  // the fake temporary target.
696  return CIP_DisallowedOnce;
697 
698  // If the temporary is lifetime-extended by binding a smaller object
699  // within it to a reference, automatic destructors don't work properly.
701  return CIP_DisallowedOnce;
702 
703  // If the temporary is lifetime-extended by binding it to a reference-typ
704  // field within an aggregate, automatic destructors don't work properly.
706  return CIP_DisallowedOnce;
707  }
708 
709  break;
710  }
711  case CE_CXXDestructor: {
713  return CIP_DisallowedAlways;
714 
715  // Inlining destructors requires building the CFG correctly.
716  const AnalysisDeclContext *ADC = CallerSFC->getAnalysisDeclContext();
717  assert(ADC->getCFGBuildOptions().AddImplicitDtors && "No CFG destructors");
718  (void)ADC;
719 
720  // FIXME: We don't handle constructors or destructors for arrays properly.
721  if (CallOpts.IsArrayCtorOrDtor)
722  return CIP_DisallowedOnce;
723 
724  // Allow disabling temporary destructor inlining with a separate option.
725  if (CallOpts.IsTemporaryCtorOrDtor && !Opts.mayInlineCXXTemporaryDtors())
726  return CIP_DisallowedOnce;
727 
728  // If we did not find the correct this-region, it would be pointless
729  // to inline the destructor. Instead we will simply invalidate
730  // the fake temporary target.
732  return CIP_DisallowedOnce;
733  break;
734  }
735  case CE_CXXAllocator:
736  if (Opts.mayInlineCXXAllocator())
737  break;
738  // Do not inline allocators until we model deallocators.
739  // This is unfortunate, but basically necessary for smart pointers and such.
740  return CIP_DisallowedAlways;
741  case CE_ObjCMessage:
742  if (!Opts.mayInlineObjCMethod())
743  return CIP_DisallowedAlways;
744  if (!(Opts.getIPAMode() == IPAK_DynamicDispatch ||
746  return CIP_DisallowedAlways;
747  break;
748  }
749 
750  return CIP_Allowed;
751 }
752 
753 /// Returns true if the given C++ class contains a member with the given name.
754 static bool hasMember(const ASTContext &Ctx, const CXXRecordDecl *RD,
755  StringRef Name) {
756  const IdentifierInfo &II = Ctx.Idents.get(Name);
757  DeclarationName DeclName = Ctx.DeclarationNames.getIdentifier(&II);
758  if (!RD->lookup(DeclName).empty())
759  return true;
760 
761  CXXBasePaths Paths(false, false, false);
762  if (RD->lookupInBases(
763  [DeclName](const CXXBaseSpecifier *Specifier, CXXBasePath &Path) {
764  return CXXRecordDecl::FindOrdinaryMember(Specifier, Path, DeclName);
765  },
766  Paths))
767  return true;
768 
769  return false;
770 }
771 
772 /// Returns true if the given C++ class is a container or iterator.
773 ///
774 /// Our heuristic for this is whether it contains a method named 'begin()' or a
775 /// nested type named 'iterator' or 'iterator_category'.
776 static bool isContainerClass(const ASTContext &Ctx, const CXXRecordDecl *RD) {
777  return hasMember(Ctx, RD, "begin") ||
778  hasMember(Ctx, RD, "iterator") ||
779  hasMember(Ctx, RD, "iterator_category");
780 }
781 
782 /// Returns true if the given function refers to a method of a C++ container
783 /// or iterator.
784 ///
785 /// We generally do a poor job modeling most containers right now, and might
786 /// prefer not to inline their methods.
787 static bool isContainerMethod(const ASTContext &Ctx,
788  const FunctionDecl *FD) {
789  if (const CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(FD))
790  return isContainerClass(Ctx, MD->getParent());
791  return false;
792 }
793 
794 /// Returns true if the given function is the destructor of a class named
795 /// "shared_ptr".
796 static bool isCXXSharedPtrDtor(const FunctionDecl *FD) {
797  const CXXDestructorDecl *Dtor = dyn_cast<CXXDestructorDecl>(FD);
798  if (!Dtor)
799  return false;
800 
801  const CXXRecordDecl *RD = Dtor->getParent();
802  if (const IdentifierInfo *II = RD->getDeclName().getAsIdentifierInfo())
803  if (II->isStr("shared_ptr"))
804  return true;
805 
806  return false;
807 }
808 
809 /// Returns true if the function in \p CalleeADC may be inlined in general.
810 ///
811 /// This checks static properties of the function, such as its signature and
812 /// CFG, to determine whether the analyzer should ever consider inlining it,
813 /// in any context.
814 static bool mayInlineDecl(AnalysisManager &AMgr,
815  AnalysisDeclContext *CalleeADC) {
816  AnalyzerOptions &Opts = AMgr.getAnalyzerOptions();
817  // FIXME: Do not inline variadic calls.
818  if (CallEvent::isVariadic(CalleeADC->getDecl()))
819  return false;
820 
821  // Check certain C++-related inlining policies.
822  ASTContext &Ctx = CalleeADC->getASTContext();
823  if (Ctx.getLangOpts().CPlusPlus) {
824  if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(CalleeADC->getDecl())) {
825  // Conditionally control the inlining of template functions.
826  if (!Opts.mayInlineTemplateFunctions())
827  if (FD->getTemplatedKind() != FunctionDecl::TK_NonTemplate)
828  return false;
829 
830  // Conditionally control the inlining of C++ standard library functions.
831  if (!Opts.mayInlineCXXStandardLibrary())
832  if (Ctx.getSourceManager().isInSystemHeader(FD->getLocation()))
834  return false;
835 
836  // Conditionally control the inlining of methods on objects that look
837  // like C++ containers.
838  if (!Opts.mayInlineCXXContainerMethods())
839  if (!AMgr.isInCodeFile(FD->getLocation()))
840  if (isContainerMethod(Ctx, FD))
841  return false;
842 
843  // Conditionally control the inlining of the destructor of C++ shared_ptr.
844  // We don't currently do a good job modeling shared_ptr because we can't
845  // see the reference count, so treating as opaque is probably the best
846  // idea.
847  if (!Opts.mayInlineCXXSharedPtrDtor())
848  if (isCXXSharedPtrDtor(FD))
849  return false;
850  }
851  }
852 
853  // It is possible that the CFG cannot be constructed.
854  // Be safe, and check if the CalleeCFG is valid.
855  const CFG *CalleeCFG = CalleeADC->getCFG();
856  if (!CalleeCFG)
857  return false;
858 
859  // Do not inline large functions.
860  if (CalleeCFG->getNumBlockIDs() > Opts.getMaxInlinableSize())
861  return false;
862 
863  // It is possible that the live variables analysis cannot be
864  // run. If so, bail out.
865  if (!CalleeADC->getAnalysis<RelaxedLiveVariables>())
866  return false;
867 
868  return true;
869 }
870 
871 bool ExprEngine::shouldInlineCall(const CallEvent &Call, const Decl *D,
872  const ExplodedNode *Pred,
873  const EvalCallOptions &CallOpts) {
874  if (!D)
875  return false;
876 
878  AnalyzerOptions &Opts = AMgr.options;
880  AnalysisDeclContext *CalleeADC = ADCMgr.getContext(D);
881 
882  // The auto-synthesized bodies are essential to inline as they are
883  // usually small and commonly used. Note: we should do this check early on to
884  // ensure we always inline these calls.
885  if (CalleeADC->isBodyAutosynthesized())
886  return true;
887 
888  if (!AMgr.shouldInlineCall())
889  return false;
890 
891  // Check if this function has been marked as non-inlinable.
892  Optional<bool> MayInline = Engine.FunctionSummaries->mayInline(D);
893  if (MayInline.hasValue()) {
894  if (!MayInline.getValue())
895  return false;
896 
897  } else {
898  // We haven't actually checked the static properties of this function yet.
899  // Do that now, and record our decision in the function summaries.
900  if (mayInlineDecl(getAnalysisManager(), CalleeADC)) {
901  Engine.FunctionSummaries->markMayInline(D);
902  } else {
903  Engine.FunctionSummaries->markShouldNotInline(D);
904  return false;
905  }
906  }
907 
908  // Check if we should inline a call based on its kind.
909  // FIXME: this checks both static and dynamic properties of the call, which
910  // means we're redoing a bit of work that could be cached in the function
911  // summary.
912  CallInlinePolicy CIP = mayInlineCallKind(Call, Pred, Opts, CallOpts);
913  if (CIP != CIP_Allowed) {
914  if (CIP == CIP_DisallowedAlways) {
915  assert(!MayInline.hasValue() || MayInline.getValue());
916  Engine.FunctionSummaries->markShouldNotInline(D);
917  }
918  return false;
919  }
920 
921  const CFG *CalleeCFG = CalleeADC->getCFG();
922 
923  // Do not inline if recursive or we've reached max stack frame count.
924  bool IsRecursive = false;
925  unsigned StackDepth = 0;
926  examineStackFrames(D, Pred->getLocationContext(), IsRecursive, StackDepth);
927  if ((StackDepth >= Opts.InlineMaxStackDepth) &&
928  ((CalleeCFG->getNumBlockIDs() > Opts.getAlwaysInlineSize())
929  || IsRecursive))
930  return false;
931 
932  // Do not inline large functions too many times.
933  if ((Engine.FunctionSummaries->getNumTimesInlined(D) >
934  Opts.getMaxTimesInlineLarge()) &&
935  CalleeCFG->getNumBlockIDs() >=
937  NumReachedInlineCountMax++;
938  return false;
939  }
940 
941  if (HowToInline == Inline_Minimal &&
942  (CalleeCFG->getNumBlockIDs() > Opts.getAlwaysInlineSize()
943  || IsRecursive))
944  return false;
945 
946  return true;
947 }
948 
949 static bool isTrivialObjectAssignment(const CallEvent &Call) {
950  const CXXInstanceCall *ICall = dyn_cast<CXXInstanceCall>(&Call);
951  if (!ICall)
952  return false;
953 
954  const CXXMethodDecl *MD = dyn_cast_or_null<CXXMethodDecl>(ICall->getDecl());
955  if (!MD)
956  return false;
958  return false;
959 
960  return MD->isTrivial();
961 }
962 
964  const CallEvent &CallTemplate,
965  const EvalCallOptions &CallOpts) {
966  // Make sure we have the most recent state attached to the call.
967  ProgramStateRef State = Pred->getState();
968  CallEventRef<> Call = CallTemplate.cloneWithState(State);
969 
970  // Special-case trivial assignment operators.
971  if (isTrivialObjectAssignment(*Call)) {
972  performTrivialCopy(Bldr, Pred, *Call);
973  return;
974  }
975 
976  // Try to inline the call.
977  // The origin expression here is just used as a kind of checksum;
978  // this should still be safe even for CallEvents that don't come from exprs.
979  const Expr *E = Call->getOriginExpr();
980 
981  ProgramStateRef InlinedFailedState = getInlineFailedState(State, E);
982  if (InlinedFailedState) {
983  // If we already tried once and failed, make sure we don't retry later.
984  State = InlinedFailedState;
985  } else {
986  RuntimeDefinition RD = Call->getRuntimeDefinition();
987  const Decl *D = RD.getDecl();
988  if (shouldInlineCall(*Call, D, Pred, CallOpts)) {
989  if (RD.mayHaveOtherDefinitions()) {
991 
992  // Explore with and without inlining the call.
993  if (Options.getIPAMode() == IPAK_DynamicDispatchBifurcate) {
994  BifurcateCall(RD.getDispatchRegion(), *Call, D, Bldr, Pred);
995  return;
996  }
997 
998  // Don't inline if we're not in any dynamic dispatch mode.
999  if (Options.getIPAMode() != IPAK_DynamicDispatch) {
1000  conservativeEvalCall(*Call, Bldr, Pred, State);
1001  return;
1002  }
1003  }
1004 
1005  // We are not bifurcating and we do have a Decl, so just inline.
1006  if (inlineCall(*Call, D, Bldr, Pred, State))
1007  return;
1008  }
1009  }
1010 
1011  // If we can't inline it, handle the return value and invalidate the regions.
1012  conservativeEvalCall(*Call, Bldr, Pred, State);
1013 }
1014 
1015 void ExprEngine::BifurcateCall(const MemRegion *BifurReg,
1016  const CallEvent &Call, const Decl *D,
1017  NodeBuilder &Bldr, ExplodedNode *Pred) {
1018  assert(BifurReg);
1019  BifurReg = BifurReg->StripCasts();
1020 
1021  // Check if we've performed the split already - note, we only want
1022  // to split the path once per memory region.
1023  ProgramStateRef State = Pred->getState();
1024  const unsigned *BState =
1025  State->get<DynamicDispatchBifurcationMap>(BifurReg);
1026  if (BState) {
1027  // If we are on "inline path", keep inlining if possible.
1028  if (*BState == DynamicDispatchModeInlined)
1029  if (inlineCall(Call, D, Bldr, Pred, State))
1030  return;
1031  // If inline failed, or we are on the path where we assume we
1032  // don't have enough info about the receiver to inline, conjure the
1033  // return value and invalidate the regions.
1034  conservativeEvalCall(Call, Bldr, Pred, State);
1035  return;
1036  }
1037 
1038  // If we got here, this is the first time we process a message to this
1039  // region, so split the path.
1040  ProgramStateRef IState =
1041  State->set<DynamicDispatchBifurcationMap>(BifurReg,
1042  DynamicDispatchModeInlined);
1043  inlineCall(Call, D, Bldr, Pred, IState);
1044 
1045  ProgramStateRef NoIState =
1046  State->set<DynamicDispatchBifurcationMap>(BifurReg,
1047  DynamicDispatchModeConservative);
1048  conservativeEvalCall(Call, Bldr, Pred, NoIState);
1049 
1050  NumOfDynamicDispatchPathSplits++;
1051 }
1052 
1054  ExplodedNodeSet &Dst) {
1055  ExplodedNodeSet dstPreVisit;
1056  getCheckerManager().runCheckersForPreStmt(dstPreVisit, Pred, RS, *this);
1057 
1058  StmtNodeBuilder B(dstPreVisit, Dst, *currBldrCtx);
1059 
1060  if (RS->getRetValue()) {
1061  for (ExplodedNodeSet::iterator it = dstPreVisit.begin(),
1062  ei = dstPreVisit.end(); it != ei; ++it) {
1063  B.generateNode(RS, *it, (*it)->getState());
1064  }
1065  }
1066 }
AnalysisDeclContextManager & getAnalysisDeclContextManager()
Represents a function declaration or definition.
Definition: Decl.h:1714
unsigned InlineMaxStackDepth
The inlining stack depth limit.
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
bool empty() const
Definition: CFG.h:713
A (possibly-)qualified type.
Definition: Type.h:654
MemRegion - The root abstract class for all memory regions.
Definition: MemRegion.h:94
CallEventRef< T > cloneWithState(ProgramStateRef NewState) const
Returns a copy of this CallEvent, but using the given state.
const CXXConstructorDecl * getDecl() const override
Definition: CallEvent.h:815
bool IsTemporaryCtorOrDtor
This call is a constructor or a destructor of a temporary value.
Definition: ExprEngine.h:106
Stmt * getBody() const
Get the body of the Declaration.
succ_iterator succ_begin()
Definition: CFG.h:750
void VisitCallExpr(const CallExpr *CE, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitCall - Transfer function for function calls.
void processCallExit(ExplodedNode *Pred) override
Generate the sequence of nodes that simulate the call exit and the post visit for CallExpr...
Stmt - This represents one statement.
Definition: Stmt.h:66
This builder class is useful for generating nodes that resulted from visiting a statement.
Definition: CoreEngine.h:370
ProgramPoint getProgramPoint(bool IsPreVisit=false, const ProgramPointTag *Tag=nullptr) const
Returns an appropriate ProgramPoint for this call.
Definition: CallEvent.cpp:236
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:86
bool mayInlineCXXTemporaryDtors()
Returns true if C++ temporary destructors should be inlined during analysis.
Represents a point when we begin processing an inlined call.
Definition: ProgramPoint.h:600
Manages the lifetime of CallEvent objects.
Definition: CallEvent.h:1009
static bool isContainerMethod(const ASTContext &Ctx, const FunctionDecl *FD)
Returns true if the given function refers to a method of a C++ container or iterator.
bool isDerivedFrom(const CXXRecordDecl *Base) const
Determine whether this class is derived from the class Base.
Hints for figuring out of a call should be inlined during evalCall().
Definition: ExprEngine.h:96
Represents a call to a C++ constructor.
Definition: ExprCXX.h:1239
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
const NestedNameSpecifier * Specifier
CallEventRef getSimpleCall(const CallExpr *E, ProgramStateRef State, const LocationContext *LCtx)
Definition: CallEvent.cpp:1195
const ProgramStateRef & getState() const
SVal evalCast(SVal val, QualType castTy, QualType originalType)
Represents a path from a specific derived class (which is not represented as part of the path) to a p...
static bool wasDifferentDeclUsedForInlining(CallEventRef<> Call, const StackFrameContext *calleeCtx)
static std::pair< const Stmt *, const CFGBlock * > getLastStmt(const ExplodedNode *Node)
unsigned succ_size() const
Definition: CFG.h:768
const Expr * getOriginExpr() const
Returns the expression whose value will be the result of this call.
Definition: CallEvent.h:248
void takeNodes(const ExplodedNodeSet &S)
Definition: CoreEngine.h:321
ASTContext & getASTContext() const
loc::MemRegionVal getCXXThis(const CXXMethodDecl *D, const StackFrameContext *SFC)
Return a memory region for the &#39;this&#39; object reference.
static bool hasMember(const ASTContext &Ctx, const CXXRecordDecl *RD, StringRef Name)
Returns true if the given C++ class contains a member with the given name.
void enqueue(ExplodedNodeSet &Set)
Enqueue the given set of nodes onto the work list.
Definition: CoreEngine.cpp:520
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:752
bool mayInlineTemplateFunctions()
Returns whether or not templated functions may be considered for inlining.
bool isMoveAssignmentOperator() const
Determine whether this is a move assignment operator.
Definition: DeclCXX.cpp:2082
const CFGBlock * getEntry() const
Returns the entry block in the CFG for the entered function.
Definition: ProgramPoint.h:615
DeclarationName getDeclName() const
Get the actual, stored name of the declaration, which may be a special name.
Definition: Decl.h:297
One of these records is kept for each identifier that is lexed.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:150
LineState State
AnalysisDeclContext contains the context data for the function or method under analysis.
const Expr * getRetValue() const
Definition: Stmt.cpp:928
static bool isInCodeFile(SourceLocation SL, const SourceManager &SM)
void addPredecessor(ExplodedNode *V, ExplodedGraph &G)
addPredeccessor - Adds a predecessor to the current node, and in tandem add this node as a successor ...
void runCheckersForPostObjCMessage(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const ObjCMethodCall &msg, ExprEngine &Eng, bool wasInlined=false)
Run checkers for post-visiting obj-c messages.
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
Optional< T > getLocationAs() const LLVM_LVALUE_FUNCTION
IdentifierTable & Idents
Definition: ASTContext.h:538
STATISTIC(NumOfDynamicDispatchPathSplits, "The # of times we split the path due to imprecise dynamic dispatch info")
bool isGLValue() const
Definition: Expr.h:252
BlockDataRegion - A region that represents a block instance.
Definition: MemRegion.h:668
Represents any expression that calls an Objective-C method.
Definition: CallEvent.h:892
virtual Kind getKind() const =0
Returns the kind of call this is.
static bool isInStdNamespace(const Decl *D)
Returns true if the root namespace of the given declaration is the &#39;std&#39; C++ namespace.
WorkList * getWorkList() const
Definition: CoreEngine.h:165
void runCheckersForPreCall(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const CallEvent &Call, ExprEngine &Eng)
Run checkers for pre-visiting obj-c messages.
CFGElement getCurrentCFGElement()
Return the CFG element corresponding to the worklist element that is currently being processed by Exp...
Definition: ExprEngine.h:641
bool mayInlineCXXContainerMethods()
Returns whether or not methods of C++ container objects may be considered for inlining.
const StackFrameContext * getCurrentStackFrame() const
T * getAnalysis()
Return the specified analysis object, lazily running the analysis if necessary.
const LocationContext * getLocationContext() const
const LocationContext * getParent() const
virtual const CXXConstructExpr * getOriginExpr() const
Definition: CallEvent.h:811
unsigned getMinCFGSizeTreatFunctionsAsLarge()
Returns the number of basic blocks a function needs to have to be considered large for the &#39;max-times...
void VisitReturnStmt(const ReturnStmt *R, ExplodedNode *Pred, ExplodedNodeSet &Dst)
VisitReturnStmt - Transfer function logic for return statements.
const CoreEngine & getCoreEngine() const
Definition: ExprEngine.h:397
ExplodedNode * getFirstPred()
bool hasTrivialDestructor() const
Determine whether this class has a trivial destructor (C++ [class.dtor]p3)
Definition: DeclCXX.h:1453
void runCheckersForPostCall(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const CallEvent &Call, ExprEngine &Eng, bool wasInlined=false)
Run checkers for post-visiting obj-c messages.
static bool isCXXSharedPtrDtor(const FunctionDecl *FD)
Returns true if the given function is the destructor of a class named "shared_ptr".
static bool isVariadic(const Decl *D)
Returns true if the given decl is known to be variadic.
Definition: CallEvent.cpp:344
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
Definition: DeclBase.h:875
lookup_result lookup(DeclarationName Name) const
lookup - Find the declarations (if any) with the given Name in this context.
Definition: DeclBase.cpp:1539
AnalysisDeclContext * getAnalysisDeclContext(const Decl *D)
CheckerManager & getCheckerManager() const
Definition: ExprEngine.h:191
void removeDeadOnEndOfFunction(NodeBuilderContext &BC, ExplodedNode *Pred, ExplodedNodeSet &Dst)
Remove dead bindings/symbols before exiting a function.
static bool isTrivialObjectAssignment(const CallEvent &Call)
ProgramStateRef bindReturnValue(const CallEvent &Call, const LocationContext *LCtx, ProgramStateRef State)
Create a new state in which the call return value is binded to the call origin expression.
Represents a non-static C++ member function call, no matter how it is written.
Definition: CallEvent.h:621
static SVal adjustReturnValue(SVal V, QualType ExpectedTy, QualType ActualTy, StoreManager &StoreMgr)
Adjusts a return value when the called function&#39;s return type does not match the caller&#39;s expression ...
DeclarationNameTable DeclarationNames
Definition: ASTContext.h:541
CFGBlock - Represents a single basic block in a source-level CFG.
Definition: CFG.h:548
Represents a point when we finish the call exit sequence (for inlined call).
Definition: ProgramPoint.h:658
AnalysisDeclContext * getContext(const Decl *D)
void runCheckersForPostStmt(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const Stmt *S, ExprEngine &Eng, bool wasInlined=false)
Run checkers for post-visiting Stmts.
void processBeginOfFunction(NodeBuilderContext &BC, ExplodedNode *Pred, ExplodedNodeSet &Dst, const BlockEdge &L) override
Called by CoreEngine.
Expr - This represents one expression.
Definition: Expr.h:106
IPAKind getIPAMode()
Returns the inter-procedural analysis mode.
CFG - Represents a source-level, intra-procedural CFG that represents the control-flow of a Stmt...
Definition: CFG.h:1002
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
const CXXRecordDecl * getPointeeCXXRecordDecl() const
If this is a pointer or reference to a RecordType, return the CXXRecordDecl that the type refers to...
Definition: Type.cpp:1575
CallEventRef getCaller(const StackFrameContext *CalleeCtx, ProgramStateRef State)
Definition: CallEvent.cpp:1216
Represents a C++ destructor within a class.
Definition: DeclCXX.h:2671
AnalyzerOptions & getAnalyzerOptions() override
This is the simplest builder which generates nodes in the ExplodedGraph.
Definition: CoreEngine.h:228
CFGConstructor - Represents C++ constructor call.
Definition: CFG.h:150
void Add(ExplodedNode *N)
Refers to regular member function and operator calls.
bool mayInlineObjCMethod()
Returns true if ObjectiveC inlining is enabled, false otherwise.
IdentifierInfo * getAsIdentifierInfo() const
getAsIdentifierInfo - Retrieve the IdentifierInfo * stored in this declaration name, or NULL if this declaration name isn&#39;t a simple identifier.
Refers to constructors (implicit or explicit).
QualType getType() const
Definition: Expr.h:128
void runCheckersForEvalCall(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const CallEvent &CE, ExprEngine &Eng)
Run checkers for evaluating a call.
ASTContext & getContext() const
getContext - Return the ASTContext associated with this analysis.
Definition: ExprEngine.h:187
Traits for storing the call processing policy inside GDM.
Definition: ExprEngine.h:824
REGISTER_TRAIT_WITH_PROGRAMSTATE(DynamicDispatchBifurcationMap, CLANG_ENTO_PROGRAMSTATE_MAP(const MemRegion *, unsigned)) bool ExprEngine
ReturnStmt - This represents a return, optionally of an expression: return; return 4;...
Definition: Stmt.h:1433
bool isBodyAutosynthesized() const
Checks if the body of the Decl is generated by the BodyFarm.
static bool isTemporaryPRValue(const CXXConstructExpr *E, SVal V)
Returns true if the CXXConstructExpr E was intended to construct a prvalue for the region in V...
ExplodedNode * getNode(const ProgramPoint &L, ProgramStateRef State, bool IsSink=false, bool *IsNew=nullptr)
Retrieve the node associated with a (Location,State) pair, where the &#39;Location&#39; is a ProgramPoint in ...
const StackFrameContext * getStackFrame(LocationContext const *Parent, const Stmt *S, const CFGBlock *Blk, unsigned Idx)
bool isTrivial() const
Whether this function is "trivial" in some specialized C++ senses.
Definition: Decl.h:2050
Enable inlining of dynamically dispatched methods.
bool isNull() const
Return true if this QualType doesn&#39;t point to a type yet.
Definition: Type.h:719
Optional< T > getAs() const
Convert to the specified SVal type, returning None if this SVal is not of the desired type...
Definition: SVals.h:112
While alive, includes the current analysis stack in a crash trace.
CanQualType getCanonicalTypeUnqualified() const
const MemRegion * StripCasts(bool StripBaseCasts=true) const
Definition: MemRegion.cpp:1151
void runCheckersForNewAllocator(const CXXNewExpr *NE, SVal Target, ExplodedNodeSet &Dst, ExplodedNode *Pred, ExprEngine &Eng, bool wasInlined=false)
Run checkers between C++ operator new and constructor calls.
Defines the runtime definition of the called function.
Definition: CallEvent.h:127
QualType getCanonicalType() const
Definition: Type.h:5843
const FunctionDecl * getDecl() const override
Definition: CallEvent.cpp:513
IdentifierInfo & get(StringRef Name)
Return the identifier token info for the specified named identifier.
AnalysisManager & getAnalysisManager() override
Definition: ExprEngine.h:189
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:1845
CallEventManager & getCallEventManager()
Definition: ProgramState.h:557
const CXXTempObjectRegion * getCXXTempObjectRegion(Expr const *Ex, LocationContext const *LC)
Definition: MemRegion.cpp:1014
void evalCall(ExplodedNodeSet &Dst, ExplodedNode *Pred, const CallEvent &Call)
Evaluate a call, running pre- and post-call checks and allowing checkers to be responsible for handli...
bool mayInlineCXXStandardLibrary()
Returns whether or not C++ standard library functions may be considered for inlining.
Represents a static or instance method of a struct/union/class.
Definition: DeclCXX.h:2016
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:76
DeclarationName getIdentifier(const IdentifierInfo *ID)
getIdentifier - Create a declaration name that is a simple identifier.
#define CLANG_ENTO_PROGRAMSTATE_MAP(Key, Value)
Helper for registering a map trait.
const Decl * getDecl() const
bool isObjCObjectPointerType() const
Definition: Type.h:6125
Do minimal inlining of callees.
Definition: ExprEngine.h:92
unsigned getNumBlockIDs() const
getNumBlockIDs - Returns the total number of BlockIDs allocated (which start at 0).
Definition: CFG.h:1168
Refers to destructors (implicit or explicit).
void runCheckersForPreStmt(ExplodedNodeSet &Dst, const ExplodedNodeSet &Src, const Stmt *S, ExprEngine &Eng)
Run checkers for pre-visiting Stmts.
static bool isContainerClass(const ASTContext &Ctx, const CXXRecordDecl *RD)
Returns true if the given C++ class is a container or iterator.
const MemRegion * getDispatchRegion()
When other definitions are possible, returns the region whose runtime type determines the method defi...
Definition: CallEvent.h:152
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
static bool mayInlineDecl(AnalysisManager &AMgr, AnalysisDeclContext *CalleeADC)
Returns true if the function in CalleeADC may be inlined in general.
ast_type_traits::DynTypedNode Node
static ProgramStateRef getInlineFailedState(ProgramStateRef State, const Stmt *CallE)
Dataflow Directional Tag Classes.
CFG::BuildOptions & getCFGBuildOptions()
Return the build options used to construct the CFG.
StoreManager & getStoreManager()
Definition: ExprEngine.h:377
const StackFrameContext * getCalleeContext() const
Definition: ProgramPoint.h:610
DeclarationName - The name of a declaration.
const CXXRecordDecl * getParent() const
Returns the parent of this method declaration, which is the class in which this method is defined...
Definition: DeclCXX.h:2136
bool isAmbiguous(CanQualType BaseType)
Determine whether the path from the most-derived type to the given base type is ambiguous (i...
bool isCopyAssignmentOperator() const
Determine whether this is a copy-assignment operator, regardless of whether it was declared implicitl...
Definition: DeclCXX.cpp:2061
bool mayHaveOtherDefinitions()
Check if the definition we have is precise.
Definition: CallEvent.h:148
Represents an abstract call to a function or method along a particular path.
Definition: CallEvent.h:164
bool IsTemporaryLifetimeExtendedViaSubobject
This call is a constructor for a temporary that is lifetime-extended by binding a smaller object with...
Definition: ExprEngine.h:111
ProgramStateManager & getStateManager() override
Definition: ExprEngine.h:375
const Decl * getDecl() const
void defaultEvalCall(NodeBuilder &B, ExplodedNode *Pred, const CallEvent &Call, const EvalCallOptions &CallOpts={})
Default implementation of call evaluation.
bool lookupInBases(BaseMatchesCallback BaseMatches, CXXBasePaths &Paths, bool LookupInDependent=false) const
Look for entities within the base classes of this C++ class, transitively searching all base class su...
T castAs() const
Convert to the specified SVal type, asserting that this SVal is of the desired type.
Definition: SVals.h:104
bool includeTemporaryDtorsInCFG()
Returns whether or not the destructors for C++ temporary objects should be included in the CFG...
const LocationContext * getLocationContext() const
Definition: ProgramPoint.h:180
static QualType getDeclaredResultType(const Decl *D)
Returns the result type of a function or method declaration.
Definition: CallEvent.cpp:315
CXXBasePath & front()
Represents a base class of a C++ class.
Definition: DeclCXX.h:192
SourceManager & getSourceManager()
Definition: ASTContext.h:644
QualType getResultType() const
Returns the result type, adjusted for references.
Definition: CallEvent.cpp:69
ExplodedNode * generateNode(const ProgramPoint &PP, ProgramStateRef State, ExplodedNode *Pred)
Generates a node in the ExplodedGraph.
Definition: CoreEngine.h:281
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate.h) and friends (in DeclFriend.h).
ConstructionContext&#39;s subclasses describe different ways of constructing an object in C++...
Represents a C++ struct/union/class.
Definition: DeclCXX.h:300
bool mayInlineCXXMemberFunction(CXXInlineableMemberKind K)
Returns the option controlling which C++ member functions will be considered for inlining.
bool IsTemporaryLifetimeExtendedViaAggregate
This call is a constructor for a temporary that is lifetime-extended by binding it to a reference-typ...
Definition: ExprEngine.h:116
pred_iterator pred_begin()
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
Definition: Expr.h:2242
ExplodedNode * generateNode(const Stmt *S, ExplodedNode *Pred, ProgramStateRef St, const ProgramPointTag *tag=nullptr, ProgramPoint::Kind K=ProgramPoint::PostStmtKind)
Definition: CoreEngine.h:399
unsigned getMaxTimesInlineLarge()
Returns the maximum times a large function could be inlined.
ProgramStateRef invalidateRegions(unsigned BlockCount, ProgramStateRef Orig=nullptr) const
Returns a new state with all argument regions invalidated.
Definition: CallEvent.cpp:196
virtual void enqueue(const WorkListUnit &U)=0
const BlockInvocationContext * getBlockInvocationContext(const LocationContext *parent, const BlockDecl *BD, const void *ContextData)
BasePaths - Represents the set of paths from a derived class to one of its (direct or indirect) bases...
bool mayInlineCXXAllocator()
Returns whether or not allocator call may be considered for inlining.
AnalysisPurgeMode AnalysisPurgeOpt
Enable inlining of dynamically dispatched methods, bifurcate paths when exact type info is unavailabl...
bool mayInlineCXXSharedPtrDtor()
Returns whether or not the destructor of C++ &#39;shared_ptr&#39; may be considered for inlining.
Optional< T > getAs() const
Convert to the specified ProgramPoint type, returning None if this ProgramPoint is not of the desired...
Definition: ProgramPoint.h:152
AnalysisDeclContext * getAnalysisDeclContext() const
Represents a call to a C++ constructor.
Definition: CallEvent.h:786
const LangOptions & getLangOpts() const
Definition: ASTContext.h:689
void processCallEnter(NodeBuilderContext &BC, CallEnter CE, ExplodedNode *Pred) override
Generate the entry node of the callee.
CallEventRef< T > cloneWithState(ProgramStateRef State) const
Definition: CallEvent.h:108