ExprEngine.cpp revision 01d08018b7cf5ce1601707cfd7a84d22015fc04e
1//=-- ExprEngine.cpp - Path-Sensitive Expression-Level Dataflow ---*- 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 a meta-engine for path-sensitive dataflow analysis that
11//  is built on GREngine, but provides the boilerplate to execute transfer
12//  functions and build the ExplodedGraph at the expression level.
13//
14//===----------------------------------------------------------------------===//
15
16#include "clang/StaticAnalyzer/Core/CheckerManager.h"
17#include "clang/StaticAnalyzer/Core/BugReporter/BugType.h"
18#include "clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h"
19#include "clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h"
20#include "clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h"
21#include "clang/AST/CharUnits.h"
22#include "clang/AST/ParentMap.h"
23#include "clang/AST/StmtObjC.h"
24#include "clang/AST/DeclCXX.h"
25#include "clang/Basic/Builtins.h"
26#include "clang/Basic/SourceManager.h"
27#include "clang/Basic/PrettyStackTrace.h"
28#include "llvm/Support/raw_ostream.h"
29#include "llvm/ADT/ImmutableList.h"
30
31#ifndef NDEBUG
32#include "llvm/Support/GraphWriter.h"
33#endif
34
35using namespace clang;
36using namespace ento;
37using llvm::APSInt;
38
39//===----------------------------------------------------------------------===//
40// Utility functions.
41//===----------------------------------------------------------------------===//
42
43static inline Selector GetNullarySelector(const char* name, ASTContext &Ctx) {
44  IdentifierInfo* II = &Ctx.Idents.get(name);
45  return Ctx.Selectors.getSelector(0, &II);
46}
47
48//===----------------------------------------------------------------------===//
49// Engine construction and deletion.
50//===----------------------------------------------------------------------===//
51
52ExprEngine::ExprEngine(AnalysisManager &mgr, bool gcEnabled)
53  : AMgr(mgr),
54    AnalysisDeclContexts(mgr.getAnalysisDeclContextManager()),
55    Engine(*this),
56    G(Engine.getGraph()),
57    StateMgr(getContext(), mgr.getStoreManagerCreator(),
58             mgr.getConstraintManagerCreator(), G.getAllocator(),
59             *this),
60    SymMgr(StateMgr.getSymbolManager()),
61    svalBuilder(StateMgr.getSValBuilder()),
62    EntryNode(NULL),
63    currentStmt(NULL), currentStmtIdx(0), currentBuilderContext(0),
64    NSExceptionII(NULL), NSExceptionInstanceRaiseSelectors(NULL),
65    RaiseSel(GetNullarySelector("raise", getContext())),
66    ObjCGCEnabled(gcEnabled), BR(mgr, *this) {
67
68  if (mgr.shouldEagerlyTrimExplodedGraph()) {
69    // Enable eager node reclaimation when constructing the ExplodedGraph.
70    G.enableNodeReclamation();
71  }
72}
73
74ExprEngine::~ExprEngine() {
75  BR.FlushReports();
76  delete [] NSExceptionInstanceRaiseSelectors;
77}
78
79//===----------------------------------------------------------------------===//
80// Utility methods.
81//===----------------------------------------------------------------------===//
82
83ProgramStateRef ExprEngine::getInitialState(const LocationContext *InitLoc) {
84  ProgramStateRef state = StateMgr.getInitialState(InitLoc);
85  const Decl *D = InitLoc->getDecl();
86
87  // Preconditions.
88  // FIXME: It would be nice if we had a more general mechanism to add
89  // such preconditions.  Some day.
90  do {
91
92    if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {
93      // Precondition: the first argument of 'main' is an integer guaranteed
94      //  to be > 0.
95      const IdentifierInfo *II = FD->getIdentifier();
96      if (!II || !(II->getName() == "main" && FD->getNumParams() > 0))
97        break;
98
99      const ParmVarDecl *PD = FD->getParamDecl(0);
100      QualType T = PD->getType();
101      if (!T->isIntegerType())
102        break;
103
104      const MemRegion *R = state->getRegion(PD, InitLoc);
105      if (!R)
106        break;
107
108      SVal V = state->getSVal(loc::MemRegionVal(R));
109      SVal Constraint_untested = evalBinOp(state, BO_GT, V,
110                                           svalBuilder.makeZeroVal(T),
111                                           getContext().IntTy);
112
113      DefinedOrUnknownSVal *Constraint =
114        dyn_cast<DefinedOrUnknownSVal>(&Constraint_untested);
115
116      if (!Constraint)
117        break;
118
119      if (ProgramStateRef newState = state->assume(*Constraint, true))
120        state = newState;
121    }
122    break;
123  }
124  while (0);
125
126  if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) {
127    // Precondition: 'self' is always non-null upon entry to an Objective-C
128    // method.
129    const ImplicitParamDecl *SelfD = MD->getSelfDecl();
130    const MemRegion *R = state->getRegion(SelfD, InitLoc);
131    SVal V = state->getSVal(loc::MemRegionVal(R));
132
133    if (const Loc *LV = dyn_cast<Loc>(&V)) {
134      // Assume that the pointer value in 'self' is non-null.
135      state = state->assume(*LV, true);
136      assert(state && "'self' cannot be null");
137    }
138  }
139
140  if (const CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(D)) {
141    if (!MD->isStatic()) {
142      // Precondition: 'this' is always non-null upon entry to the
143      // top-level function.  This is our starting assumption for
144      // analyzing an "open" program.
145      const StackFrameContext *SFC = InitLoc->getCurrentStackFrame();
146      if (SFC->getParent() == 0) {
147        loc::MemRegionVal L(getCXXThisRegion(MD, SFC));
148        SVal V = state->getSVal(L);
149        if (const Loc *LV = dyn_cast<Loc>(&V)) {
150          state = state->assume(*LV, true);
151          assert(state && "'this' cannot be null");
152        }
153      }
154    }
155  }
156
157  return state;
158}
159
160//===----------------------------------------------------------------------===//
161// Top-level transfer function logic (Dispatcher).
162//===----------------------------------------------------------------------===//
163
164/// evalAssume - Called by ConstraintManager. Used to call checker-specific
165///  logic for handling assumptions on symbolic values.
166ProgramStateRef ExprEngine::processAssume(ProgramStateRef state,
167                                              SVal cond, bool assumption) {
168  return getCheckerManager().runCheckersForEvalAssume(state, cond, assumption);
169}
170
171bool ExprEngine::wantsRegionChangeUpdate(ProgramStateRef state) {
172  return getCheckerManager().wantsRegionChangeUpdate(state);
173}
174
175ProgramStateRef
176ExprEngine::processRegionChanges(ProgramStateRef state,
177                            const StoreManager::InvalidatedSymbols *invalidated,
178                                 ArrayRef<const MemRegion *> Explicits,
179                                 ArrayRef<const MemRegion *> Regions) {
180  return getCheckerManager().runCheckersForRegionChanges(state, invalidated,
181                                                         Explicits, Regions);
182}
183
184void ExprEngine::printState(raw_ostream &Out, ProgramStateRef State,
185                            const char *NL, const char *Sep) {
186  getCheckerManager().runCheckersForPrintState(Out, State, NL, Sep);
187}
188
189void ExprEngine::processEndWorklist(bool hasWorkRemaining) {
190  getCheckerManager().runCheckersForEndAnalysis(G, BR, *this);
191}
192
193void ExprEngine::processCFGElement(const CFGElement E, ExplodedNode *Pred,
194                                   unsigned StmtIdx, NodeBuilderContext *Ctx) {
195  currentStmtIdx = StmtIdx;
196  currentBuilderContext = Ctx;
197
198  switch (E.getKind()) {
199    case CFGElement::Invalid:
200      llvm_unreachable("Unexpected CFGElement kind.");
201    case CFGElement::Statement:
202      ProcessStmt(const_cast<Stmt*>(E.getAs<CFGStmt>()->getStmt()), Pred);
203      return;
204    case CFGElement::Initializer:
205      ProcessInitializer(E.getAs<CFGInitializer>()->getInitializer(), Pred);
206      return;
207    case CFGElement::AutomaticObjectDtor:
208    case CFGElement::BaseDtor:
209    case CFGElement::MemberDtor:
210    case CFGElement::TemporaryDtor:
211      ProcessImplicitDtor(*E.getAs<CFGImplicitDtor>(), Pred);
212      return;
213  }
214}
215
216static bool shouldRemoveDeadBindings(AnalysisManager &AMgr,
217                                     const CFGStmt S,
218                                     const ExplodedNode *Pred,
219                                     const LocationContext *LC) {
220
221  // Are we never purging state values?
222  if (AMgr.getPurgeMode() == PurgeNone)
223    return false;
224
225  // Is this the beginning of a basic block?
226  if (isa<BlockEntrance>(Pred->getLocation()))
227    return true;
228
229  // Is this on a non-expression?
230  if (!isa<Expr>(S.getStmt()))
231    return true;
232
233  // Is this an expression that is consumed by another expression?  If so,
234  // postpone cleaning out the state.
235  ParentMap &PM = LC->getAnalysisDeclContext()->getParentMap();
236  return !PM.isConsumedExpr(cast<Expr>(S.getStmt()));
237}
238
239void ExprEngine::ProcessStmt(const CFGStmt S,
240                             ExplodedNode *Pred) {
241  // Reclaim any unnecessary nodes in the ExplodedGraph.
242  G.reclaimRecentlyAllocatedNodes();
243
244  currentStmt = S.getStmt();
245  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
246                                currentStmt->getLocStart(),
247                                "Error evaluating statement");
248
249  EntryNode = Pred;
250
251  ProgramStateRef EntryState = EntryNode->getState();
252  CleanedState = EntryState;
253
254  // Create the cleaned state.
255  const LocationContext *LC = EntryNode->getLocationContext();
256  SymbolReaper SymReaper(LC, currentStmt, SymMgr, getStoreManager());
257
258  if (shouldRemoveDeadBindings(AMgr, S, Pred, LC)) {
259    getCheckerManager().runCheckersForLiveSymbols(CleanedState, SymReaper);
260
261    const StackFrameContext *SFC = LC->getCurrentStackFrame();
262
263    // Create a state in which dead bindings are removed from the environment
264    // and the store. TODO: The function should just return new env and store,
265    // not a new state.
266    CleanedState = StateMgr.removeDeadBindings(CleanedState, SFC, SymReaper);
267  }
268
269  // Process any special transfer function for dead symbols.
270  ExplodedNodeSet Tmp;
271  // A tag to track convenience transitions, which can be removed at cleanup.
272  static SimpleProgramPointTag cleanupTag("ExprEngine : Clean Node");
273
274  if (!SymReaper.hasDeadSymbols()) {
275    // Generate a CleanedNode that has the environment and store cleaned
276    // up. Since no symbols are dead, we can optimize and not clean out
277    // the constraint manager.
278    StmtNodeBuilder Bldr(Pred, Tmp, *currentBuilderContext);
279    Bldr.generateNode(currentStmt, EntryNode, CleanedState, false, &cleanupTag);
280
281  } else {
282    // Call checkers with the non-cleaned state so that they could query the
283    // values of the soon to be dead symbols.
284    ExplodedNodeSet CheckedSet;
285    getCheckerManager().runCheckersForDeadSymbols(CheckedSet, EntryNode,
286                                                 SymReaper, currentStmt, *this);
287
288    // For each node in CheckedSet, generate CleanedNodes that have the
289    // environment, the store, and the constraints cleaned up but have the
290    // user-supplied states as the predecessors.
291    StmtNodeBuilder Bldr(CheckedSet, Tmp, *currentBuilderContext);
292    for (ExplodedNodeSet::const_iterator
293          I = CheckedSet.begin(), E = CheckedSet.end(); I != E; ++I) {
294      ProgramStateRef CheckerState = (*I)->getState();
295
296      // The constraint manager has not been cleaned up yet, so clean up now.
297      CheckerState = getConstraintManager().removeDeadBindings(CheckerState,
298                                                               SymReaper);
299
300      assert(StateMgr.haveEqualEnvironments(CheckerState, EntryState) &&
301        "Checkers are not allowed to modify the Environment as a part of "
302        "checkDeadSymbols processing.");
303      assert(StateMgr.haveEqualStores(CheckerState, EntryState) &&
304        "Checkers are not allowed to modify the Store as a part of "
305        "checkDeadSymbols processing.");
306
307      // Create a state based on CleanedState with CheckerState GDM and
308      // generate a transition to that state.
309      ProgramStateRef CleanedCheckerSt =
310        StateMgr.getPersistentStateWithGDM(CleanedState, CheckerState);
311      Bldr.generateNode(currentStmt, *I, CleanedCheckerSt, false, &cleanupTag,
312                        ProgramPoint::PostPurgeDeadSymbolsKind);
313    }
314  }
315
316  ExplodedNodeSet Dst;
317  for (ExplodedNodeSet::iterator I=Tmp.begin(), E=Tmp.end(); I!=E; ++I) {
318    ExplodedNodeSet DstI;
319    // Visit the statement.
320    Visit(currentStmt, *I, DstI);
321    Dst.insert(DstI);
322  }
323
324  // Enqueue the new nodes onto the work list.
325  Engine.enqueue(Dst, currentBuilderContext->getBlock(), currentStmtIdx);
326
327  // NULL out these variables to cleanup.
328  CleanedState = NULL;
329  EntryNode = NULL;
330  currentStmt = 0;
331}
332
333void ExprEngine::ProcessInitializer(const CFGInitializer Init,
334                                    ExplodedNode *Pred) {
335  ExplodedNodeSet Dst;
336
337  // We don't set EntryNode and currentStmt. And we don't clean up state.
338  const CXXCtorInitializer *BMI = Init.getInitializer();
339  const StackFrameContext *stackFrame =
340                           cast<StackFrameContext>(Pred->getLocationContext());
341  const CXXConstructorDecl *decl =
342                           cast<CXXConstructorDecl>(stackFrame->getDecl());
343  const CXXThisRegion *thisReg = getCXXThisRegion(decl, stackFrame);
344
345  SVal thisVal = Pred->getState()->getSVal(thisReg);
346
347  if (BMI->isAnyMemberInitializer()) {
348    ExplodedNodeSet AfterEval;
349
350    // Evaluate the initializer.
351    Visit(BMI->getInit(), Pred, AfterEval);
352
353    StmtNodeBuilder Bldr(AfterEval, Dst, *currentBuilderContext);
354    for (ExplodedNodeSet::iterator I = AfterEval.begin(),
355                                   E = AfterEval.end(); I != E; ++I){
356      ExplodedNode *P = *I;
357      ProgramStateRef state = P->getState();
358
359      const FieldDecl *FD = BMI->getAnyMember();
360
361      SVal FieldLoc = state->getLValue(FD, thisVal);
362      SVal InitVal = state->getSVal(BMI->getInit(), Pred->getLocationContext());
363      state = state->bindLoc(FieldLoc, InitVal);
364
365      // Use a custom node building process.
366      PostInitializer PP(BMI, stackFrame);
367      // Builder automatically add the generated node to the deferred set,
368      // which are processed in the builder's dtor.
369      Bldr.generateNode(PP, P, state);
370    }
371  } else {
372    assert(BMI->isBaseInitializer());
373
374    // Get the base class declaration.
375    const CXXConstructExpr *ctorExpr = cast<CXXConstructExpr>(BMI->getInit());
376
377    // Create the base object region.
378    SVal baseVal =
379        getStoreManager().evalDerivedToBase(thisVal, ctorExpr->getType());
380    const MemRegion *baseReg = baseVal.getAsRegion();
381    assert(baseReg);
382
383    VisitCXXConstructExpr(ctorExpr, baseReg, Pred, Dst);
384  }
385
386  // Enqueue the new nodes onto the work list.
387  Engine.enqueue(Dst, currentBuilderContext->getBlock(), currentStmtIdx);
388}
389
390void ExprEngine::ProcessImplicitDtor(const CFGImplicitDtor D,
391                                     ExplodedNode *Pred) {
392  ExplodedNodeSet Dst;
393  switch (D.getKind()) {
394  case CFGElement::AutomaticObjectDtor:
395    ProcessAutomaticObjDtor(cast<CFGAutomaticObjDtor>(D), Pred, Dst);
396    break;
397  case CFGElement::BaseDtor:
398    ProcessBaseDtor(cast<CFGBaseDtor>(D), Pred, Dst);
399    break;
400  case CFGElement::MemberDtor:
401    ProcessMemberDtor(cast<CFGMemberDtor>(D), Pred, Dst);
402    break;
403  case CFGElement::TemporaryDtor:
404    ProcessTemporaryDtor(cast<CFGTemporaryDtor>(D), Pred, Dst);
405    break;
406  default:
407    llvm_unreachable("Unexpected dtor kind.");
408  }
409
410  // Enqueue the new nodes onto the work list.
411  Engine.enqueue(Dst, currentBuilderContext->getBlock(), currentStmtIdx);
412}
413
414void ExprEngine::ProcessAutomaticObjDtor(const CFGAutomaticObjDtor Dtor,
415                                         ExplodedNode *Pred,
416                                         ExplodedNodeSet &Dst) {
417  ProgramStateRef state = Pred->getState();
418  const VarDecl *varDecl = Dtor.getVarDecl();
419
420  QualType varType = varDecl->getType();
421
422  if (const ReferenceType *refType = varType->getAs<ReferenceType>())
423    varType = refType->getPointeeType();
424
425  const CXXRecordDecl *recordDecl = varType->getAsCXXRecordDecl();
426  assert(recordDecl && "get CXXRecordDecl fail");
427  const CXXDestructorDecl *dtorDecl = recordDecl->getDestructor();
428
429  Loc dest = state->getLValue(varDecl, Pred->getLocationContext());
430
431  VisitCXXDestructor(dtorDecl, cast<loc::MemRegionVal>(dest).getRegion(),
432                     Dtor.getTriggerStmt(), Pred, Dst);
433}
434
435void ExprEngine::ProcessBaseDtor(const CFGBaseDtor D,
436                                 ExplodedNode *Pred, ExplodedNodeSet &Dst) {}
437
438void ExprEngine::ProcessMemberDtor(const CFGMemberDtor D,
439                                   ExplodedNode *Pred, ExplodedNodeSet &Dst) {}
440
441void ExprEngine::ProcessTemporaryDtor(const CFGTemporaryDtor D,
442                                      ExplodedNode *Pred,
443                                      ExplodedNodeSet &Dst) {}
444
445void ExprEngine::Visit(const Stmt *S, ExplodedNode *Pred,
446                       ExplodedNodeSet &DstTop) {
447  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
448                                S->getLocStart(),
449                                "Error evaluating statement");
450  ExplodedNodeSet Dst;
451  StmtNodeBuilder Bldr(Pred, DstTop, *currentBuilderContext);
452
453  // Expressions to ignore.
454  if (const Expr *Ex = dyn_cast<Expr>(S))
455    S = Ex->IgnoreParens();
456
457  // FIXME: add metadata to the CFG so that we can disable
458  //  this check when we KNOW that there is no block-level subexpression.
459  //  The motivation is that this check requires a hashtable lookup.
460
461  if (S != currentStmt && Pred->getLocationContext()->getCFG()->isBlkExpr(S))
462    return;
463
464  switch (S->getStmtClass()) {
465    // C++ and ARC stuff we don't support yet.
466    case Expr::ObjCIndirectCopyRestoreExprClass:
467    case Stmt::CXXBindTemporaryExprClass:
468    case Stmt::CXXCatchStmtClass:
469    case Stmt::CXXDependentScopeMemberExprClass:
470    case Stmt::CXXPseudoDestructorExprClass:
471    case Stmt::CXXThrowExprClass:
472    case Stmt::CXXTryStmtClass:
473    case Stmt::CXXTypeidExprClass:
474    case Stmt::CXXUuidofExprClass:
475    case Stmt::CXXUnresolvedConstructExprClass:
476    case Stmt::CXXScalarValueInitExprClass:
477    case Stmt::DependentScopeDeclRefExprClass:
478    case Stmt::UnaryTypeTraitExprClass:
479    case Stmt::BinaryTypeTraitExprClass:
480    case Stmt::ArrayTypeTraitExprClass:
481    case Stmt::ExpressionTraitExprClass:
482    case Stmt::UnresolvedLookupExprClass:
483    case Stmt::UnresolvedMemberExprClass:
484    case Stmt::CXXNoexceptExprClass:
485    case Stmt::PackExpansionExprClass:
486    case Stmt::SubstNonTypeTemplateParmPackExprClass:
487    case Stmt::SEHTryStmtClass:
488    case Stmt::SEHExceptStmtClass:
489    case Stmt::LambdaExprClass:
490    case Stmt::SEHFinallyStmtClass: {
491      const ExplodedNode *node = Bldr.generateNode(S, Pred, Pred->getState());
492      Engine.addAbortedBlock(node, currentBuilderContext->getBlock());
493      break;
494    }
495
496    // We don't handle default arguments either yet, but we can fake it
497    // for now by just skipping them.
498    case Stmt::SubstNonTypeTemplateParmExprClass:
499    case Stmt::CXXDefaultArgExprClass:
500      break;
501
502    case Stmt::ParenExprClass:
503      llvm_unreachable("ParenExprs already handled.");
504    case Stmt::GenericSelectionExprClass:
505      llvm_unreachable("GenericSelectionExprs already handled.");
506    // Cases that should never be evaluated simply because they shouldn't
507    // appear in the CFG.
508    case Stmt::BreakStmtClass:
509    case Stmt::CaseStmtClass:
510    case Stmt::CompoundStmtClass:
511    case Stmt::ContinueStmtClass:
512    case Stmt::CXXForRangeStmtClass:
513    case Stmt::DefaultStmtClass:
514    case Stmt::DoStmtClass:
515    case Stmt::ForStmtClass:
516    case Stmt::GotoStmtClass:
517    case Stmt::IfStmtClass:
518    case Stmt::IndirectGotoStmtClass:
519    case Stmt::LabelStmtClass:
520    case Stmt::NoStmtClass:
521    case Stmt::NullStmtClass:
522    case Stmt::SwitchStmtClass:
523    case Stmt::WhileStmtClass:
524    case Expr::MSDependentExistsStmtClass:
525      llvm_unreachable("Stmt should not be in analyzer evaluation loop");
526
527    case Stmt::GNUNullExprClass: {
528      // GNU __null is a pointer-width integer, not an actual pointer.
529      ProgramStateRef state = Pred->getState();
530      state = state->BindExpr(S, Pred->getLocationContext(),
531                              svalBuilder.makeIntValWithPtrWidth(0, false));
532      Bldr.generateNode(S, Pred, state);
533      break;
534    }
535
536    case Stmt::ObjCAtSynchronizedStmtClass:
537      Bldr.takeNodes(Pred);
538      VisitObjCAtSynchronizedStmt(cast<ObjCAtSynchronizedStmt>(S), Pred, Dst);
539      Bldr.addNodes(Dst);
540      break;
541
542    case Stmt::ObjCPropertyRefExprClass:
543      // Implicitly handled by Environment::getSVal().
544      break;
545
546    case Stmt::ImplicitValueInitExprClass: {
547      ProgramStateRef state = Pred->getState();
548      QualType ty = cast<ImplicitValueInitExpr>(S)->getType();
549      SVal val = svalBuilder.makeZeroVal(ty);
550      Bldr.generateNode(S, Pred, state->BindExpr(S, Pred->getLocationContext(),
551                                                 val));
552      break;
553    }
554
555    case Stmt::ExprWithCleanupsClass:
556      Bldr.takeNodes(Pred);
557      Visit(cast<ExprWithCleanups>(S)->getSubExpr(), Pred, Dst);
558      Bldr.addNodes(Dst);
559      break;
560
561    // Cases not handled yet; but will handle some day.
562    case Stmt::DesignatedInitExprClass:
563    case Stmt::ExtVectorElementExprClass:
564    case Stmt::ImaginaryLiteralClass:
565    case Stmt::ObjCAtCatchStmtClass:
566    case Stmt::ObjCAtFinallyStmtClass:
567    case Stmt::ObjCAtTryStmtClass:
568    case Stmt::ObjCAutoreleasePoolStmtClass:
569    case Stmt::ObjCEncodeExprClass:
570    case Stmt::ObjCIsaExprClass:
571    case Stmt::ObjCProtocolExprClass:
572    case Stmt::ObjCSelectorExprClass:
573    case Stmt::ObjCStringLiteralClass:
574    case Stmt::ParenListExprClass:
575    case Stmt::PredefinedExprClass:
576    case Stmt::ShuffleVectorExprClass:
577    case Stmt::VAArgExprClass:
578    case Stmt::CUDAKernelCallExprClass:
579    case Stmt::OpaqueValueExprClass:
580    case Stmt::AsTypeExprClass:
581    case Stmt::AtomicExprClass:
582        // Fall through.
583
584    // Cases we intentionally don't evaluate, since they don't need
585    // to be explicitly evaluated.
586    case Stmt::AddrLabelExprClass:
587    case Stmt::IntegerLiteralClass:
588    case Stmt::CharacterLiteralClass:
589    case Stmt::CXXBoolLiteralExprClass:
590    case Stmt::FloatingLiteralClass:
591    case Stmt::SizeOfPackExprClass:
592    case Stmt::CXXNullPtrLiteralExprClass:
593      // No-op. Simply propagate the current state unchanged.
594      break;
595
596    case Stmt::ArraySubscriptExprClass:
597      Bldr.takeNodes(Pred);
598      VisitLvalArraySubscriptExpr(cast<ArraySubscriptExpr>(S), Pred, Dst);
599      Bldr.addNodes(Dst);
600      break;
601
602    case Stmt::AsmStmtClass:
603      Bldr.takeNodes(Pred);
604      VisitAsmStmt(cast<AsmStmt>(S), Pred, Dst);
605      Bldr.addNodes(Dst);
606      break;
607
608    case Stmt::BlockDeclRefExprClass: {
609      Bldr.takeNodes(Pred);
610      const BlockDeclRefExpr *BE = cast<BlockDeclRefExpr>(S);
611      VisitCommonDeclRefExpr(BE, BE->getDecl(), Pred, Dst);
612      Bldr.addNodes(Dst);
613      break;
614    }
615
616    case Stmt::BlockExprClass:
617      Bldr.takeNodes(Pred);
618      VisitBlockExpr(cast<BlockExpr>(S), Pred, Dst);
619      Bldr.addNodes(Dst);
620      break;
621
622    case Stmt::BinaryOperatorClass: {
623      const BinaryOperator* B = cast<BinaryOperator>(S);
624      if (B->isLogicalOp()) {
625        Bldr.takeNodes(Pred);
626        VisitLogicalExpr(B, Pred, Dst);
627        Bldr.addNodes(Dst);
628        break;
629      }
630      else if (B->getOpcode() == BO_Comma) {
631        ProgramStateRef state = Pred->getState();
632        Bldr.generateNode(B, Pred,
633                          state->BindExpr(B, Pred->getLocationContext(),
634                                          state->getSVal(B->getRHS(),
635                                                  Pred->getLocationContext())));
636        break;
637      }
638
639      Bldr.takeNodes(Pred);
640
641      if (AMgr.shouldEagerlyAssume() &&
642          (B->isRelationalOp() || B->isEqualityOp())) {
643        ExplodedNodeSet Tmp;
644        VisitBinaryOperator(cast<BinaryOperator>(S), Pred, Tmp);
645        evalEagerlyAssume(Dst, Tmp, cast<Expr>(S));
646      }
647      else
648        VisitBinaryOperator(cast<BinaryOperator>(S), Pred, Dst);
649
650      Bldr.addNodes(Dst);
651      break;
652    }
653
654    case Stmt::CallExprClass:
655    case Stmt::CXXOperatorCallExprClass:
656    case Stmt::CXXMemberCallExprClass: {
657      Bldr.takeNodes(Pred);
658      VisitCallExpr(cast<CallExpr>(S), Pred, Dst);
659      Bldr.addNodes(Dst);
660      break;
661    }
662
663    case Stmt::CXXTemporaryObjectExprClass:
664    case Stmt::CXXConstructExprClass: {
665      const CXXConstructExpr *C = cast<CXXConstructExpr>(S);
666      // For block-level CXXConstructExpr, we don't have a destination region.
667      // Let VisitCXXConstructExpr() create one.
668      Bldr.takeNodes(Pred);
669      VisitCXXConstructExpr(C, 0, Pred, Dst);
670      Bldr.addNodes(Dst);
671      break;
672    }
673
674    case Stmt::CXXNewExprClass: {
675      Bldr.takeNodes(Pred);
676      const CXXNewExpr *NE = cast<CXXNewExpr>(S);
677      VisitCXXNewExpr(NE, Pred, Dst);
678      Bldr.addNodes(Dst);
679      break;
680    }
681
682    case Stmt::CXXDeleteExprClass: {
683      Bldr.takeNodes(Pred);
684      const CXXDeleteExpr *CDE = cast<CXXDeleteExpr>(S);
685      VisitCXXDeleteExpr(CDE, Pred, Dst);
686      Bldr.addNodes(Dst);
687      break;
688    }
689      // FIXME: ChooseExpr is really a constant.  We need to fix
690      //        the CFG do not model them as explicit control-flow.
691
692    case Stmt::ChooseExprClass: { // __builtin_choose_expr
693      Bldr.takeNodes(Pred);
694      const ChooseExpr *C = cast<ChooseExpr>(S);
695      VisitGuardedExpr(C, C->getLHS(), C->getRHS(), Pred, Dst);
696      Bldr.addNodes(Dst);
697      break;
698    }
699
700    case Stmt::CompoundAssignOperatorClass:
701      Bldr.takeNodes(Pred);
702      VisitBinaryOperator(cast<BinaryOperator>(S), Pred, Dst);
703      Bldr.addNodes(Dst);
704      break;
705
706    case Stmt::CompoundLiteralExprClass:
707      Bldr.takeNodes(Pred);
708      VisitCompoundLiteralExpr(cast<CompoundLiteralExpr>(S), Pred, Dst);
709      Bldr.addNodes(Dst);
710      break;
711
712    case Stmt::BinaryConditionalOperatorClass:
713    case Stmt::ConditionalOperatorClass: { // '?' operator
714      Bldr.takeNodes(Pred);
715      const AbstractConditionalOperator *C
716        = cast<AbstractConditionalOperator>(S);
717      VisitGuardedExpr(C, C->getTrueExpr(), C->getFalseExpr(), Pred, Dst);
718      Bldr.addNodes(Dst);
719      break;
720    }
721
722    case Stmt::CXXThisExprClass:
723      Bldr.takeNodes(Pred);
724      VisitCXXThisExpr(cast<CXXThisExpr>(S), Pred, Dst);
725      Bldr.addNodes(Dst);
726      break;
727
728    case Stmt::DeclRefExprClass: {
729      Bldr.takeNodes(Pred);
730      const DeclRefExpr *DE = cast<DeclRefExpr>(S);
731      VisitCommonDeclRefExpr(DE, DE->getDecl(), Pred, Dst);
732      Bldr.addNodes(Dst);
733      break;
734    }
735
736    case Stmt::DeclStmtClass:
737      Bldr.takeNodes(Pred);
738      VisitDeclStmt(cast<DeclStmt>(S), Pred, Dst);
739      Bldr.addNodes(Dst);
740      break;
741
742    case Stmt::ImplicitCastExprClass:
743    case Stmt::CStyleCastExprClass:
744    case Stmt::CXXStaticCastExprClass:
745    case Stmt::CXXDynamicCastExprClass:
746    case Stmt::CXXReinterpretCastExprClass:
747    case Stmt::CXXConstCastExprClass:
748    case Stmt::CXXFunctionalCastExprClass:
749    case Stmt::ObjCBridgedCastExprClass: {
750      Bldr.takeNodes(Pred);
751      const CastExpr *C = cast<CastExpr>(S);
752      // Handle the previsit checks.
753      ExplodedNodeSet dstPrevisit;
754      getCheckerManager().runCheckersForPreStmt(dstPrevisit, Pred, C, *this);
755
756      // Handle the expression itself.
757      ExplodedNodeSet dstExpr;
758      for (ExplodedNodeSet::iterator i = dstPrevisit.begin(),
759                                     e = dstPrevisit.end(); i != e ; ++i) {
760        VisitCast(C, C->getSubExpr(), *i, dstExpr);
761      }
762
763      // Handle the postvisit checks.
764      getCheckerManager().runCheckersForPostStmt(Dst, dstExpr, C, *this);
765      Bldr.addNodes(Dst);
766      break;
767    }
768
769    case Expr::MaterializeTemporaryExprClass: {
770      Bldr.takeNodes(Pred);
771      const MaterializeTemporaryExpr *Materialize
772                                            = cast<MaterializeTemporaryExpr>(S);
773      if (!Materialize->getType()->isRecordType())
774        CreateCXXTemporaryObject(Materialize, Pred, Dst);
775      else
776        Visit(Materialize->GetTemporaryExpr(), Pred, Dst);
777      Bldr.addNodes(Dst);
778      break;
779    }
780
781    case Stmt::InitListExprClass:
782      Bldr.takeNodes(Pred);
783      VisitInitListExpr(cast<InitListExpr>(S), Pred, Dst);
784      Bldr.addNodes(Dst);
785      break;
786
787    case Stmt::MemberExprClass:
788      Bldr.takeNodes(Pred);
789      VisitMemberExpr(cast<MemberExpr>(S), Pred, Dst);
790      Bldr.addNodes(Dst);
791      break;
792
793    case Stmt::ObjCIvarRefExprClass:
794      Bldr.takeNodes(Pred);
795      VisitLvalObjCIvarRefExpr(cast<ObjCIvarRefExpr>(S), Pred, Dst);
796      Bldr.addNodes(Dst);
797      break;
798
799    case Stmt::ObjCForCollectionStmtClass:
800      Bldr.takeNodes(Pred);
801      VisitObjCForCollectionStmt(cast<ObjCForCollectionStmt>(S), Pred, Dst);
802      Bldr.addNodes(Dst);
803      break;
804
805    case Stmt::ObjCMessageExprClass:
806      Bldr.takeNodes(Pred);
807      VisitObjCMessage(cast<ObjCMessageExpr>(S), Pred, Dst);
808      Bldr.addNodes(Dst);
809      break;
810
811    case Stmt::ObjCAtThrowStmtClass: {
812      // FIXME: This is not complete.  We basically treat @throw as
813      // an abort.
814      Bldr.generateNode(S, Pred, Pred->getState());
815      break;
816    }
817
818    case Stmt::ReturnStmtClass:
819      Bldr.takeNodes(Pred);
820      VisitReturnStmt(cast<ReturnStmt>(S), Pred, Dst);
821      Bldr.addNodes(Dst);
822      break;
823
824    case Stmt::OffsetOfExprClass:
825      Bldr.takeNodes(Pred);
826      VisitOffsetOfExpr(cast<OffsetOfExpr>(S), Pred, Dst);
827      Bldr.addNodes(Dst);
828      break;
829
830    case Stmt::UnaryExprOrTypeTraitExprClass:
831      Bldr.takeNodes(Pred);
832      VisitUnaryExprOrTypeTraitExpr(cast<UnaryExprOrTypeTraitExpr>(S),
833                                    Pred, Dst);
834      Bldr.addNodes(Dst);
835      break;
836
837    case Stmt::StmtExprClass: {
838      const StmtExpr *SE = cast<StmtExpr>(S);
839
840      if (SE->getSubStmt()->body_empty()) {
841        // Empty statement expression.
842        assert(SE->getType() == getContext().VoidTy
843               && "Empty statement expression must have void type.");
844        break;
845      }
846
847      if (Expr *LastExpr = dyn_cast<Expr>(*SE->getSubStmt()->body_rbegin())) {
848        ProgramStateRef state = Pred->getState();
849        Bldr.generateNode(SE, Pred,
850                          state->BindExpr(SE, Pred->getLocationContext(),
851                                          state->getSVal(LastExpr,
852                                                  Pred->getLocationContext())));
853      }
854      break;
855    }
856
857    case Stmt::StringLiteralClass: {
858      ProgramStateRef state = Pred->getState();
859      SVal V = state->getLValue(cast<StringLiteral>(S));
860      Bldr.generateNode(S, Pred, state->BindExpr(S, Pred->getLocationContext(),
861                                                 V));
862      return;
863    }
864
865    case Stmt::UnaryOperatorClass: {
866      Bldr.takeNodes(Pred);
867      const UnaryOperator *U = cast<UnaryOperator>(S);
868      if (AMgr.shouldEagerlyAssume() && (U->getOpcode() == UO_LNot)) {
869        ExplodedNodeSet Tmp;
870        VisitUnaryOperator(U, Pred, Tmp);
871        evalEagerlyAssume(Dst, Tmp, U);
872      }
873      else
874        VisitUnaryOperator(U, Pred, Dst);
875      Bldr.addNodes(Dst);
876      break;
877    }
878
879    case Stmt::PseudoObjectExprClass: {
880      Bldr.takeNodes(Pred);
881      ProgramStateRef state = Pred->getState();
882      const PseudoObjectExpr *PE = cast<PseudoObjectExpr>(S);
883      if (const Expr *Result = PE->getResultExpr()) {
884        SVal V = state->getSVal(Result, Pred->getLocationContext());
885        Bldr.generateNode(S, Pred,
886                          state->BindExpr(S, Pred->getLocationContext(), V));
887      }
888      else
889        Bldr.generateNode(S, Pred,
890                          state->BindExpr(S, Pred->getLocationContext(),
891                                                   UnknownVal()));
892
893      Bldr.addNodes(Dst);
894      break;
895    }
896  }
897}
898
899/// Block entrance.  (Update counters).
900void ExprEngine::processCFGBlockEntrance(NodeBuilderWithSinks &nodeBuilder) {
901
902  // FIXME: Refactor this into a checker.
903  ExplodedNode *pred = nodeBuilder.getContext().getPred();
904
905  if (nodeBuilder.getContext().getCurrentBlockCount() >= AMgr.getMaxVisit()) {
906    static SimpleProgramPointTag tag("ExprEngine : Block count exceeded");
907    nodeBuilder.generateNode(pred->getState(), pred, &tag, true);
908  }
909}
910
911//===----------------------------------------------------------------------===//
912// Branch processing.
913//===----------------------------------------------------------------------===//
914
915ProgramStateRef ExprEngine::MarkBranch(ProgramStateRef state,
916                                           const Stmt *Terminator,
917                                           const LocationContext *LCtx,
918                                           bool branchTaken) {
919
920  switch (Terminator->getStmtClass()) {
921    default:
922      return state;
923
924    case Stmt::BinaryOperatorClass: { // '&&' and '||'
925
926      const BinaryOperator* B = cast<BinaryOperator>(Terminator);
927      BinaryOperator::Opcode Op = B->getOpcode();
928
929      assert (Op == BO_LAnd || Op == BO_LOr);
930
931      // For &&, if we take the true branch, then the value of the whole
932      // expression is that of the RHS expression.
933      //
934      // For ||, if we take the false branch, then the value of the whole
935      // expression is that of the RHS expression.
936
937      const Expr *Ex = (Op == BO_LAnd && branchTaken) ||
938                       (Op == BO_LOr && !branchTaken)
939                       ? B->getRHS() : B->getLHS();
940
941      return state->BindExpr(B, LCtx, UndefinedVal(Ex));
942    }
943
944    case Stmt::BinaryConditionalOperatorClass:
945    case Stmt::ConditionalOperatorClass: { // ?:
946      const AbstractConditionalOperator* C
947        = cast<AbstractConditionalOperator>(Terminator);
948
949      // For ?, if branchTaken == true then the value is either the LHS or
950      // the condition itself. (GNU extension).
951
952      const Expr *Ex;
953
954      if (branchTaken)
955        Ex = C->getTrueExpr();
956      else
957        Ex = C->getFalseExpr();
958
959      return state->BindExpr(C, LCtx, UndefinedVal(Ex));
960    }
961
962    case Stmt::ChooseExprClass: { // ?:
963
964      const ChooseExpr *C = cast<ChooseExpr>(Terminator);
965
966      const Expr *Ex = branchTaken ? C->getLHS() : C->getRHS();
967      return state->BindExpr(C, LCtx, UndefinedVal(Ex));
968    }
969  }
970}
971
972/// RecoverCastedSymbol - A helper function for ProcessBranch that is used
973/// to try to recover some path-sensitivity for casts of symbolic
974/// integers that promote their values (which are currently not tracked well).
975/// This function returns the SVal bound to Condition->IgnoreCasts if all the
976//  cast(s) did was sign-extend the original value.
977static SVal RecoverCastedSymbol(ProgramStateManager& StateMgr,
978                                ProgramStateRef state,
979                                const Stmt *Condition,
980                                const LocationContext *LCtx,
981                                ASTContext &Ctx) {
982
983  const Expr *Ex = dyn_cast<Expr>(Condition);
984  if (!Ex)
985    return UnknownVal();
986
987  uint64_t bits = 0;
988  bool bitsInit = false;
989
990  while (const CastExpr *CE = dyn_cast<CastExpr>(Ex)) {
991    QualType T = CE->getType();
992
993    if (!T->isIntegerType())
994      return UnknownVal();
995
996    uint64_t newBits = Ctx.getTypeSize(T);
997    if (!bitsInit || newBits < bits) {
998      bitsInit = true;
999      bits = newBits;
1000    }
1001
1002    Ex = CE->getSubExpr();
1003  }
1004
1005  // We reached a non-cast.  Is it a symbolic value?
1006  QualType T = Ex->getType();
1007
1008  if (!bitsInit || !T->isIntegerType() || Ctx.getTypeSize(T) > bits)
1009    return UnknownVal();
1010
1011  return state->getSVal(Ex, LCtx);
1012}
1013
1014void ExprEngine::processBranch(const Stmt *Condition, const Stmt *Term,
1015                               NodeBuilderContext& BldCtx,
1016                               ExplodedNode *Pred,
1017                               ExplodedNodeSet &Dst,
1018                               const CFGBlock *DstT,
1019                               const CFGBlock *DstF) {
1020  currentBuilderContext = &BldCtx;
1021
1022  // Check for NULL conditions; e.g. "for(;;)"
1023  if (!Condition) {
1024    BranchNodeBuilder NullCondBldr(Pred, Dst, BldCtx, DstT, DstF);
1025    NullCondBldr.markInfeasible(false);
1026    NullCondBldr.generateNode(Pred->getState(), true, Pred);
1027    return;
1028  }
1029
1030  PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
1031                                Condition->getLocStart(),
1032                                "Error evaluating branch");
1033
1034  ExplodedNodeSet CheckersOutSet;
1035  getCheckerManager().runCheckersForBranchCondition(Condition, CheckersOutSet,
1036                                                    Pred, *this);
1037  // We generated only sinks.
1038  if (CheckersOutSet.empty())
1039    return;
1040
1041  BranchNodeBuilder builder(CheckersOutSet, Dst, BldCtx, DstT, DstF);
1042  for (NodeBuilder::iterator I = CheckersOutSet.begin(),
1043                             E = CheckersOutSet.end(); E != I; ++I) {
1044    ExplodedNode *PredI = *I;
1045
1046    if (PredI->isSink())
1047      continue;
1048
1049    ProgramStateRef PrevState = Pred->getState();
1050    SVal X = PrevState->getSVal(Condition, Pred->getLocationContext());
1051
1052    if (X.isUnknownOrUndef()) {
1053      // Give it a chance to recover from unknown.
1054      if (const Expr *Ex = dyn_cast<Expr>(Condition)) {
1055        if (Ex->getType()->isIntegerType()) {
1056          // Try to recover some path-sensitivity.  Right now casts of symbolic
1057          // integers that promote their values are currently not tracked well.
1058          // If 'Condition' is such an expression, try and recover the
1059          // underlying value and use that instead.
1060          SVal recovered = RecoverCastedSymbol(getStateManager(),
1061                                               PrevState, Condition,
1062                                               Pred->getLocationContext(),
1063                                               getContext());
1064
1065          if (!recovered.isUnknown()) {
1066            X = recovered;
1067          }
1068        }
1069      }
1070    }
1071
1072    const LocationContext *LCtx = PredI->getLocationContext();
1073
1074    // If the condition is still unknown, give up.
1075    if (X.isUnknownOrUndef()) {
1076      builder.generateNode(MarkBranch(PrevState, Term, LCtx, true),
1077                           true, PredI);
1078      builder.generateNode(MarkBranch(PrevState, Term, LCtx, false),
1079                           false, PredI);
1080      continue;
1081    }
1082
1083    DefinedSVal V = cast<DefinedSVal>(X);
1084
1085    // Process the true branch.
1086    if (builder.isFeasible(true)) {
1087      if (ProgramStateRef state = PrevState->assume(V, true))
1088        builder.generateNode(MarkBranch(state, Term, LCtx, true),
1089                             true, PredI);
1090      else
1091        builder.markInfeasible(true);
1092    }
1093
1094    // Process the false branch.
1095    if (builder.isFeasible(false)) {
1096      if (ProgramStateRef state = PrevState->assume(V, false))
1097        builder.generateNode(MarkBranch(state, Term, LCtx, false),
1098                             false, PredI);
1099      else
1100        builder.markInfeasible(false);
1101    }
1102  }
1103  currentBuilderContext = 0;
1104}
1105
1106/// processIndirectGoto - Called by CoreEngine.  Used to generate successor
1107///  nodes by processing the 'effects' of a computed goto jump.
1108void ExprEngine::processIndirectGoto(IndirectGotoNodeBuilder &builder) {
1109
1110  ProgramStateRef state = builder.getState();
1111  SVal V = state->getSVal(builder.getTarget(), builder.getLocationContext());
1112
1113  // Three possibilities:
1114  //
1115  //   (1) We know the computed label.
1116  //   (2) The label is NULL (or some other constant), or Undefined.
1117  //   (3) We have no clue about the label.  Dispatch to all targets.
1118  //
1119
1120  typedef IndirectGotoNodeBuilder::iterator iterator;
1121
1122  if (isa<loc::GotoLabel>(V)) {
1123    const LabelDecl *L = cast<loc::GotoLabel>(V).getLabel();
1124
1125    for (iterator I = builder.begin(), E = builder.end(); I != E; ++I) {
1126      if (I.getLabel() == L) {
1127        builder.generateNode(I, state);
1128        return;
1129      }
1130    }
1131
1132    llvm_unreachable("No block with label.");
1133  }
1134
1135  if (isa<loc::ConcreteInt>(V) || isa<UndefinedVal>(V)) {
1136    // Dispatch to the first target and mark it as a sink.
1137    //ExplodedNode* N = builder.generateNode(builder.begin(), state, true);
1138    // FIXME: add checker visit.
1139    //    UndefBranches.insert(N);
1140    return;
1141  }
1142
1143  // This is really a catch-all.  We don't support symbolics yet.
1144  // FIXME: Implement dispatch for symbolic pointers.
1145
1146  for (iterator I=builder.begin(), E=builder.end(); I != E; ++I)
1147    builder.generateNode(I, state);
1148}
1149
1150/// ProcessEndPath - Called by CoreEngine.  Used to generate end-of-path
1151///  nodes when the control reaches the end of a function.
1152void ExprEngine::processEndOfFunction(NodeBuilderContext& BC) {
1153  StateMgr.EndPath(BC.Pred->getState());
1154  ExplodedNodeSet Dst;
1155  getCheckerManager().runCheckersForEndPath(BC, Dst, *this);
1156  Engine.enqueueEndOfFunction(Dst);
1157}
1158
1159/// ProcessSwitch - Called by CoreEngine.  Used to generate successor
1160///  nodes by processing the 'effects' of a switch statement.
1161void ExprEngine::processSwitch(SwitchNodeBuilder& builder) {
1162  typedef SwitchNodeBuilder::iterator iterator;
1163  ProgramStateRef state = builder.getState();
1164  const Expr *CondE = builder.getCondition();
1165  SVal  CondV_untested = state->getSVal(CondE, builder.getLocationContext());
1166
1167  if (CondV_untested.isUndef()) {
1168    //ExplodedNode* N = builder.generateDefaultCaseNode(state, true);
1169    // FIXME: add checker
1170    //UndefBranches.insert(N);
1171
1172    return;
1173  }
1174  DefinedOrUnknownSVal CondV = cast<DefinedOrUnknownSVal>(CondV_untested);
1175
1176  ProgramStateRef DefaultSt = state;
1177
1178  iterator I = builder.begin(), EI = builder.end();
1179  bool defaultIsFeasible = I == EI;
1180
1181  for ( ; I != EI; ++I) {
1182    // Successor may be pruned out during CFG construction.
1183    if (!I.getBlock())
1184      continue;
1185
1186    const CaseStmt *Case = I.getCase();
1187
1188    // Evaluate the LHS of the case value.
1189    llvm::APSInt V1 = Case->getLHS()->EvaluateKnownConstInt(getContext());
1190    assert(V1.getBitWidth() == getContext().getTypeSize(CondE->getType()));
1191
1192    // Get the RHS of the case, if it exists.
1193    llvm::APSInt V2;
1194    if (const Expr *E = Case->getRHS())
1195      V2 = E->EvaluateKnownConstInt(getContext());
1196    else
1197      V2 = V1;
1198
1199    // FIXME: Eventually we should replace the logic below with a range
1200    //  comparison, rather than concretize the values within the range.
1201    //  This should be easy once we have "ranges" for NonLVals.
1202
1203    do {
1204      nonloc::ConcreteInt CaseVal(getBasicVals().getValue(V1));
1205      DefinedOrUnknownSVal Res = svalBuilder.evalEQ(DefaultSt ? DefaultSt : state,
1206                                               CondV, CaseVal);
1207
1208      // Now "assume" that the case matches.
1209      if (ProgramStateRef stateNew = state->assume(Res, true)) {
1210        builder.generateCaseStmtNode(I, stateNew);
1211
1212        // If CondV evaluates to a constant, then we know that this
1213        // is the *only* case that we can take, so stop evaluating the
1214        // others.
1215        if (isa<nonloc::ConcreteInt>(CondV))
1216          return;
1217      }
1218
1219      // Now "assume" that the case doesn't match.  Add this state
1220      // to the default state (if it is feasible).
1221      if (DefaultSt) {
1222        if (ProgramStateRef stateNew = DefaultSt->assume(Res, false)) {
1223          defaultIsFeasible = true;
1224          DefaultSt = stateNew;
1225        }
1226        else {
1227          defaultIsFeasible = false;
1228          DefaultSt = NULL;
1229        }
1230      }
1231
1232      // Concretize the next value in the range.
1233      if (V1 == V2)
1234        break;
1235
1236      ++V1;
1237      assert (V1 <= V2);
1238
1239    } while (true);
1240  }
1241
1242  if (!defaultIsFeasible)
1243    return;
1244
1245  // If we have switch(enum value), the default branch is not
1246  // feasible if all of the enum constants not covered by 'case:' statements
1247  // are not feasible values for the switch condition.
1248  //
1249  // Note that this isn't as accurate as it could be.  Even if there isn't
1250  // a case for a particular enum value as long as that enum value isn't
1251  // feasible then it shouldn't be considered for making 'default:' reachable.
1252  const SwitchStmt *SS = builder.getSwitch();
1253  const Expr *CondExpr = SS->getCond()->IgnoreParenImpCasts();
1254  if (CondExpr->getType()->getAs<EnumType>()) {
1255    if (SS->isAllEnumCasesCovered())
1256      return;
1257  }
1258
1259  builder.generateDefaultCaseNode(DefaultSt);
1260}
1261
1262//===----------------------------------------------------------------------===//
1263// Transfer functions: Loads and stores.
1264//===----------------------------------------------------------------------===//
1265
1266void ExprEngine::VisitCommonDeclRefExpr(const Expr *Ex, const NamedDecl *D,
1267                                        ExplodedNode *Pred,
1268                                        ExplodedNodeSet &Dst) {
1269  StmtNodeBuilder Bldr(Pred, Dst, *currentBuilderContext);
1270
1271  ProgramStateRef state = Pred->getState();
1272  const LocationContext *LCtx = Pred->getLocationContext();
1273
1274  if (const VarDecl *VD = dyn_cast<VarDecl>(D)) {
1275    assert(Ex->isLValue());
1276    SVal V = state->getLValue(VD, Pred->getLocationContext());
1277
1278    // For references, the 'lvalue' is the pointer address stored in the
1279    // reference region.
1280    if (VD->getType()->isReferenceType()) {
1281      if (const MemRegion *R = V.getAsRegion())
1282        V = state->getSVal(R);
1283      else
1284        V = UnknownVal();
1285    }
1286
1287    Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V), false, 0,
1288                      ProgramPoint::PostLValueKind);
1289    return;
1290  }
1291  if (const EnumConstantDecl *ED = dyn_cast<EnumConstantDecl>(D)) {
1292    assert(!Ex->isLValue());
1293    SVal V = svalBuilder.makeIntVal(ED->getInitVal());
1294    Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V));
1295    return;
1296  }
1297  if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {
1298    SVal V = svalBuilder.getFunctionPointer(FD);
1299    Bldr.generateNode(Ex, Pred, state->BindExpr(Ex, LCtx, V), false, 0,
1300                      ProgramPoint::PostLValueKind);
1301    return;
1302  }
1303  assert (false &&
1304          "ValueDecl support for this ValueDecl not implemented.");
1305}
1306
1307/// VisitArraySubscriptExpr - Transfer function for array accesses
1308void ExprEngine::VisitLvalArraySubscriptExpr(const ArraySubscriptExpr *A,
1309                                             ExplodedNode *Pred,
1310                                             ExplodedNodeSet &Dst){
1311
1312  const Expr *Base = A->getBase()->IgnoreParens();
1313  const Expr *Idx  = A->getIdx()->IgnoreParens();
1314
1315
1316  ExplodedNodeSet checkerPreStmt;
1317  getCheckerManager().runCheckersForPreStmt(checkerPreStmt, Pred, A, *this);
1318
1319  StmtNodeBuilder Bldr(checkerPreStmt, Dst, *currentBuilderContext);
1320
1321  for (ExplodedNodeSet::iterator it = checkerPreStmt.begin(),
1322                                 ei = checkerPreStmt.end(); it != ei; ++it) {
1323    const LocationContext *LCtx = (*it)->getLocationContext();
1324    ProgramStateRef state = (*it)->getState();
1325    SVal V = state->getLValue(A->getType(),
1326                              state->getSVal(Idx, LCtx),
1327                              state->getSVal(Base, LCtx));
1328    assert(A->isLValue());
1329    Bldr.generateNode(A, *it, state->BindExpr(A, LCtx, V),
1330                      false, 0, ProgramPoint::PostLValueKind);
1331  }
1332}
1333
1334/// VisitMemberExpr - Transfer function for member expressions.
1335void ExprEngine::VisitMemberExpr(const MemberExpr *M, ExplodedNode *Pred,
1336                                 ExplodedNodeSet &TopDst) {
1337
1338  StmtNodeBuilder Bldr(Pred, TopDst, *currentBuilderContext);
1339  ExplodedNodeSet Dst;
1340  Decl *member = M->getMemberDecl();
1341  if (VarDecl *VD = dyn_cast<VarDecl>(member)) {
1342    assert(M->isLValue());
1343    Bldr.takeNodes(Pred);
1344    VisitCommonDeclRefExpr(M, VD, Pred, Dst);
1345    Bldr.addNodes(Dst);
1346    return;
1347  }
1348
1349  FieldDecl *field = dyn_cast<FieldDecl>(member);
1350  if (!field) // FIXME: skipping member expressions for non-fields
1351    return;
1352
1353  Expr *baseExpr = M->getBase()->IgnoreParens();
1354  ProgramStateRef state = Pred->getState();
1355  const LocationContext *LCtx = Pred->getLocationContext();
1356  SVal baseExprVal = state->getSVal(baseExpr, Pred->getLocationContext());
1357  if (isa<nonloc::LazyCompoundVal>(baseExprVal) ||
1358      isa<nonloc::CompoundVal>(baseExprVal) ||
1359      // FIXME: This can originate by conjuring a symbol for an unknown
1360      // temporary struct object, see test/Analysis/fields.c:
1361      // (p = getit()).x
1362      isa<nonloc::SymbolVal>(baseExprVal)) {
1363    Bldr.generateNode(M, Pred, state->BindExpr(M, LCtx, UnknownVal()));
1364    return;
1365  }
1366
1367  // FIXME: Should we insert some assumption logic in here to determine
1368  // if "Base" is a valid piece of memory?  Before we put this assumption
1369  // later when using FieldOffset lvals (which we no longer have).
1370
1371  // For all other cases, compute an lvalue.
1372  SVal L = state->getLValue(field, baseExprVal);
1373  if (M->isLValue())
1374    Bldr.generateNode(M, Pred, state->BindExpr(M, LCtx, L), false, 0,
1375                      ProgramPoint::PostLValueKind);
1376  else {
1377    Bldr.takeNodes(Pred);
1378    evalLoad(Dst, M, Pred, state, L);
1379    Bldr.addNodes(Dst);
1380  }
1381}
1382
1383/// evalBind - Handle the semantics of binding a value to a specific location.
1384///  This method is used by evalStore and (soon) VisitDeclStmt, and others.
1385void ExprEngine::evalBind(ExplodedNodeSet &Dst, const Stmt *StoreE,
1386                          ExplodedNode *Pred,
1387                          SVal location, SVal Val, bool atDeclInit,
1388                          ProgramPoint::Kind PointKind) {
1389
1390  // Do a previsit of the bind.
1391  ExplodedNodeSet CheckedSet;
1392  getCheckerManager().runCheckersForBind(CheckedSet, Pred, location, Val,
1393                                         StoreE, *this, PointKind);
1394
1395  // TODO:AZ Remove TmpDst after NB refactoring is done.
1396  ExplodedNodeSet TmpDst;
1397  StmtNodeBuilder Bldr(CheckedSet, TmpDst, *currentBuilderContext);
1398
1399  for (ExplodedNodeSet::iterator I = CheckedSet.begin(), E = CheckedSet.end();
1400       I!=E; ++I) {
1401    ProgramStateRef state = (*I)->getState();
1402
1403    if (atDeclInit) {
1404      const VarRegion *VR =
1405        cast<VarRegion>(cast<loc::MemRegionVal>(location).getRegion());
1406
1407      state = state->bindDecl(VR, Val);
1408    } else {
1409      state = state->bindLoc(location, Val);
1410    }
1411
1412    Bldr.generateNode(StoreE, *I, state, false, 0, PointKind);
1413  }
1414
1415  Dst.insert(TmpDst);
1416}
1417
1418/// evalStore - Handle the semantics of a store via an assignment.
1419///  @param Dst The node set to store generated state nodes
1420///  @param AssignE The assignment expression if the store happens in an
1421///         assignment.
1422///  @param LocatioinE The location expression that is stored to.
1423///  @param state The current simulation state
1424///  @param location The location to store the value
1425///  @param Val The value to be stored
1426void ExprEngine::evalStore(ExplodedNodeSet &Dst, const Expr *AssignE,
1427                             const Expr *LocationE,
1428                             ExplodedNode *Pred,
1429                             ProgramStateRef state, SVal location, SVal Val,
1430                             const ProgramPointTag *tag) {
1431  // Proceed with the store.  We use AssignE as the anchor for the PostStore
1432  // ProgramPoint if it is non-NULL, and LocationE otherwise.
1433  const Expr *StoreE = AssignE ? AssignE : LocationE;
1434
1435  if (isa<loc::ObjCPropRef>(location)) {
1436    loc::ObjCPropRef prop = cast<loc::ObjCPropRef>(location);
1437    return VisitObjCMessage(ObjCPropertySetter(prop.getPropRefExpr(),
1438                                               StoreE, Val), Pred, Dst);
1439  }
1440
1441  // Evaluate the location (checks for bad dereferences).
1442  ExplodedNodeSet Tmp;
1443  evalLocation(Tmp, LocationE, Pred, state, location, tag, false);
1444
1445  if (Tmp.empty())
1446    return;
1447
1448  if (location.isUndef())
1449    return;
1450
1451  for (ExplodedNodeSet::iterator NI=Tmp.begin(), NE=Tmp.end(); NI!=NE; ++NI)
1452    evalBind(Dst, StoreE, *NI, location, Val, false,
1453             ProgramPoint::PostStoreKind);
1454}
1455
1456void ExprEngine::evalLoad(ExplodedNodeSet &Dst, const Expr *Ex,
1457                            ExplodedNode *Pred,
1458                            ProgramStateRef state, SVal location,
1459                            const ProgramPointTag *tag, QualType LoadTy) {
1460  assert(!isa<NonLoc>(location) && "location cannot be a NonLoc.");
1461
1462  if (isa<loc::ObjCPropRef>(location)) {
1463    loc::ObjCPropRef prop = cast<loc::ObjCPropRef>(location);
1464    return VisitObjCMessage(ObjCPropertyGetter(prop.getPropRefExpr(), Ex),
1465                            Pred, Dst);
1466  }
1467
1468  // Are we loading from a region?  This actually results in two loads; one
1469  // to fetch the address of the referenced value and one to fetch the
1470  // referenced value.
1471  if (const TypedValueRegion *TR =
1472        dyn_cast_or_null<TypedValueRegion>(location.getAsRegion())) {
1473
1474    QualType ValTy = TR->getValueType();
1475    if (const ReferenceType *RT = ValTy->getAs<ReferenceType>()) {
1476      static SimpleProgramPointTag
1477             loadReferenceTag("ExprEngine : Load Reference");
1478      ExplodedNodeSet Tmp;
1479      evalLoadCommon(Tmp, Ex, Pred, state, location, &loadReferenceTag,
1480                     getContext().getPointerType(RT->getPointeeType()));
1481
1482      // Perform the load from the referenced value.
1483      for (ExplodedNodeSet::iterator I=Tmp.begin(), E=Tmp.end() ; I!=E; ++I) {
1484        state = (*I)->getState();
1485        location = state->getSVal(Ex, (*I)->getLocationContext());
1486        evalLoadCommon(Dst, Ex, *I, state, location, tag, LoadTy);
1487      }
1488      return;
1489    }
1490  }
1491
1492  evalLoadCommon(Dst, Ex, Pred, state, location, tag, LoadTy);
1493}
1494
1495void ExprEngine::evalLoadCommon(ExplodedNodeSet &Dst, const Expr *Ex,
1496                                  ExplodedNode *Pred,
1497                                  ProgramStateRef state, SVal location,
1498                                  const ProgramPointTag *tag, QualType LoadTy) {
1499
1500  // Evaluate the location (checks for bad dereferences).
1501  ExplodedNodeSet Tmp;
1502  evalLocation(Tmp, Ex, Pred, state, location, tag, true);
1503  if (Tmp.empty())
1504    return;
1505
1506  StmtNodeBuilder Bldr(Tmp, Dst, *currentBuilderContext);
1507  if (location.isUndef())
1508    return;
1509
1510  // Proceed with the load.
1511  for (ExplodedNodeSet::iterator NI=Tmp.begin(), NE=Tmp.end(); NI!=NE; ++NI) {
1512    state = (*NI)->getState();
1513    const LocationContext *LCtx = (*NI)->getLocationContext();
1514
1515    if (location.isUnknown()) {
1516      // This is important.  We must nuke the old binding.
1517      Bldr.generateNode(Ex, *NI, state->BindExpr(Ex, LCtx, UnknownVal()),
1518                        false, tag, ProgramPoint::PostLoadKind);
1519    }
1520    else {
1521      if (LoadTy.isNull())
1522        LoadTy = Ex->getType();
1523      SVal V = state->getSVal(cast<Loc>(location), LoadTy);
1524      Bldr.generateNode(Ex, *NI, state->bindExprAndLocation(Ex, LCtx,
1525                                                            location, V),
1526                        false, tag, ProgramPoint::PostLoadKind);
1527    }
1528  }
1529}
1530
1531void ExprEngine::evalLocation(ExplodedNodeSet &Dst, const Stmt *S,
1532                                ExplodedNode *Pred,
1533                                ProgramStateRef state, SVal location,
1534                                const ProgramPointTag *tag, bool isLoad) {
1535  StmtNodeBuilder BldrTop(Pred, Dst, *currentBuilderContext);
1536  // Early checks for performance reason.
1537  if (location.isUnknown()) {
1538    return;
1539  }
1540
1541  ExplodedNodeSet Src;
1542  BldrTop.takeNodes(Pred);
1543  StmtNodeBuilder Bldr(Pred, Src, *currentBuilderContext);
1544  if (Pred->getState() != state) {
1545    // Associate this new state with an ExplodedNode.
1546    // FIXME: If I pass null tag, the graph is incorrect, e.g for
1547    //   int *p;
1548    //   p = 0;
1549    //   *p = 0xDEADBEEF;
1550    // "p = 0" is not noted as "Null pointer value stored to 'p'" but
1551    // instead "int *p" is noted as
1552    // "Variable 'p' initialized to a null pointer value"
1553
1554    // FIXME: why is 'tag' not used instead of etag?
1555    static SimpleProgramPointTag etag("ExprEngine: Location");
1556
1557    Bldr.generateNode(S, Pred, state, false, &etag);
1558  }
1559  ExplodedNodeSet Tmp;
1560  getCheckerManager().runCheckersForLocation(Tmp, Src, location, isLoad, S,
1561                                             *this);
1562  BldrTop.addNodes(Tmp);
1563}
1564
1565std::pair<const ProgramPointTag *, const ProgramPointTag*>
1566ExprEngine::getEagerlyAssumeTags() {
1567  static SimpleProgramPointTag
1568         EagerlyAssumeTrue("ExprEngine : Eagerly Assume True"),
1569         EagerlyAssumeFalse("ExprEngine : Eagerly Assume False");
1570  return std::make_pair(&EagerlyAssumeTrue, &EagerlyAssumeFalse);
1571}
1572
1573void ExprEngine::evalEagerlyAssume(ExplodedNodeSet &Dst, ExplodedNodeSet &Src,
1574                                   const Expr *Ex) {
1575  StmtNodeBuilder Bldr(Src, Dst, *currentBuilderContext);
1576
1577  for (ExplodedNodeSet::iterator I=Src.begin(), E=Src.end(); I!=E; ++I) {
1578    ExplodedNode *Pred = *I;
1579    // Test if the previous node was as the same expression.  This can happen
1580    // when the expression fails to evaluate to anything meaningful and
1581    // (as an optimization) we don't generate a node.
1582    ProgramPoint P = Pred->getLocation();
1583    if (!isa<PostStmt>(P) || cast<PostStmt>(P).getStmt() != Ex) {
1584      continue;
1585    }
1586
1587    ProgramStateRef state = Pred->getState();
1588    SVal V = state->getSVal(Ex, Pred->getLocationContext());
1589    nonloc::SymbolVal *SEV = dyn_cast<nonloc::SymbolVal>(&V);
1590    if (SEV && SEV->isExpression()) {
1591      const std::pair<const ProgramPointTag *, const ProgramPointTag*> &tags =
1592        getEagerlyAssumeTags();
1593
1594      // First assume that the condition is true.
1595      if (ProgramStateRef StateTrue = state->assume(*SEV, true)) {
1596        SVal Val = svalBuilder.makeIntVal(1U, Ex->getType());
1597        StateTrue = StateTrue->BindExpr(Ex, Pred->getLocationContext(), Val);
1598        Bldr.generateNode(Ex, Pred, StateTrue, false, tags.first);
1599      }
1600
1601      // Next, assume that the condition is false.
1602      if (ProgramStateRef StateFalse = state->assume(*SEV, false)) {
1603        SVal Val = svalBuilder.makeIntVal(0U, Ex->getType());
1604        StateFalse = StateFalse->BindExpr(Ex, Pred->getLocationContext(), Val);
1605        Bldr.generateNode(Ex, Pred, StateFalse, false, tags.second);
1606      }
1607    }
1608  }
1609}
1610
1611void ExprEngine::VisitAsmStmt(const AsmStmt *A, ExplodedNode *Pred,
1612                                ExplodedNodeSet &Dst) {
1613  VisitAsmStmtHelperOutputs(A, A->begin_outputs(), A->end_outputs(), Pred, Dst);
1614}
1615
1616void ExprEngine::VisitAsmStmtHelperOutputs(const AsmStmt *A,
1617                                             AsmStmt::const_outputs_iterator I,
1618                                             AsmStmt::const_outputs_iterator E,
1619                                     ExplodedNode *Pred, ExplodedNodeSet &Dst) {
1620  if (I == E) {
1621    VisitAsmStmtHelperInputs(A, A->begin_inputs(), A->end_inputs(), Pred, Dst);
1622    return;
1623  }
1624
1625  ExplodedNodeSet Tmp;
1626  Visit(*I, Pred, Tmp);
1627  ++I;
1628
1629  for (ExplodedNodeSet::iterator NI = Tmp.begin(), NE = Tmp.end();NI != NE;++NI)
1630    VisitAsmStmtHelperOutputs(A, I, E, *NI, Dst);
1631}
1632
1633void ExprEngine::VisitAsmStmtHelperInputs(const AsmStmt *A,
1634                                            AsmStmt::const_inputs_iterator I,
1635                                            AsmStmt::const_inputs_iterator E,
1636                                            ExplodedNode *Pred,
1637                                            ExplodedNodeSet &Dst) {
1638  if (I == E) {
1639    StmtNodeBuilder Bldr(Pred, Dst, *currentBuilderContext);
1640    // We have processed both the inputs and the outputs.  All of the outputs
1641    // should evaluate to Locs.  Nuke all of their values.
1642
1643    // FIXME: Some day in the future it would be nice to allow a "plug-in"
1644    // which interprets the inline asm and stores proper results in the
1645    // outputs.
1646
1647    ProgramStateRef state = Pred->getState();
1648
1649    for (AsmStmt::const_outputs_iterator OI = A->begin_outputs(),
1650                                   OE = A->end_outputs(); OI != OE; ++OI) {
1651
1652      SVal X = state->getSVal(*OI, Pred->getLocationContext());
1653      assert (!isa<NonLoc>(X));  // Should be an Lval, or unknown, undef.
1654
1655      if (isa<Loc>(X))
1656        state = state->bindLoc(cast<Loc>(X), UnknownVal());
1657    }
1658
1659    Bldr.generateNode(A, Pred, state);
1660    return;
1661  }
1662
1663  ExplodedNodeSet Tmp;
1664  Visit(*I, Pred, Tmp);
1665
1666  ++I;
1667
1668  for (ExplodedNodeSet::iterator NI = Tmp.begin(), NE = Tmp.end(); NI!=NE; ++NI)
1669    VisitAsmStmtHelperInputs(A, I, E, *NI, Dst);
1670}
1671
1672
1673//===----------------------------------------------------------------------===//
1674// Visualization.
1675//===----------------------------------------------------------------------===//
1676
1677#ifndef NDEBUG
1678static ExprEngine* GraphPrintCheckerState;
1679static SourceManager* GraphPrintSourceManager;
1680
1681namespace llvm {
1682template<>
1683struct DOTGraphTraits<ExplodedNode*> :
1684  public DefaultDOTGraphTraits {
1685
1686  DOTGraphTraits (bool isSimple=false) : DefaultDOTGraphTraits(isSimple) {}
1687
1688  // FIXME: Since we do not cache error nodes in ExprEngine now, this does not
1689  // work.
1690  static std::string getNodeAttributes(const ExplodedNode *N, void*) {
1691
1692#if 0
1693      // FIXME: Replace with a general scheme to tell if the node is
1694      // an error node.
1695    if (GraphPrintCheckerState->isImplicitNullDeref(N) ||
1696        GraphPrintCheckerState->isExplicitNullDeref(N) ||
1697        GraphPrintCheckerState->isUndefDeref(N) ||
1698        GraphPrintCheckerState->isUndefStore(N) ||
1699        GraphPrintCheckerState->isUndefControlFlow(N) ||
1700        GraphPrintCheckerState->isUndefResult(N) ||
1701        GraphPrintCheckerState->isBadCall(N) ||
1702        GraphPrintCheckerState->isUndefArg(N))
1703      return "color=\"red\",style=\"filled\"";
1704
1705    if (GraphPrintCheckerState->isNoReturnCall(N))
1706      return "color=\"blue\",style=\"filled\"";
1707#endif
1708    return "";
1709  }
1710
1711  static std::string getNodeLabel(const ExplodedNode *N, void*){
1712
1713    std::string sbuf;
1714    llvm::raw_string_ostream Out(sbuf);
1715
1716    // Program Location.
1717    ProgramPoint Loc = N->getLocation();
1718
1719    switch (Loc.getKind()) {
1720      case ProgramPoint::BlockEntranceKind:
1721        Out << "Block Entrance: B"
1722            << cast<BlockEntrance>(Loc).getBlock()->getBlockID();
1723        break;
1724
1725      case ProgramPoint::BlockExitKind:
1726        assert (false);
1727        break;
1728
1729      case ProgramPoint::CallEnterKind:
1730        Out << "CallEnter";
1731        break;
1732
1733      case ProgramPoint::CallExitKind:
1734        Out << "CallExit";
1735        break;
1736
1737      default: {
1738        if (StmtPoint *L = dyn_cast<StmtPoint>(&Loc)) {
1739          const Stmt *S = L->getStmt();
1740          SourceLocation SLoc = S->getLocStart();
1741
1742          Out << S->getStmtClassName() << ' ' << (void*) S << ' ';
1743          LangOptions LO; // FIXME.
1744          S->printPretty(Out, 0, PrintingPolicy(LO));
1745
1746          if (SLoc.isFileID()) {
1747            Out << "\\lline="
1748              << GraphPrintSourceManager->getExpansionLineNumber(SLoc)
1749              << " col="
1750              << GraphPrintSourceManager->getExpansionColumnNumber(SLoc)
1751              << "\\l";
1752          }
1753
1754          if (isa<PreStmt>(Loc))
1755            Out << "\\lPreStmt\\l;";
1756          else if (isa<PostLoad>(Loc))
1757            Out << "\\lPostLoad\\l;";
1758          else if (isa<PostStore>(Loc))
1759            Out << "\\lPostStore\\l";
1760          else if (isa<PostLValue>(Loc))
1761            Out << "\\lPostLValue\\l";
1762
1763#if 0
1764            // FIXME: Replace with a general scheme to determine
1765            // the name of the check.
1766          if (GraphPrintCheckerState->isImplicitNullDeref(N))
1767            Out << "\\|Implicit-Null Dereference.\\l";
1768          else if (GraphPrintCheckerState->isExplicitNullDeref(N))
1769            Out << "\\|Explicit-Null Dereference.\\l";
1770          else if (GraphPrintCheckerState->isUndefDeref(N))
1771            Out << "\\|Dereference of undefialied value.\\l";
1772          else if (GraphPrintCheckerState->isUndefStore(N))
1773            Out << "\\|Store to Undefined Loc.";
1774          else if (GraphPrintCheckerState->isUndefResult(N))
1775            Out << "\\|Result of operation is undefined.";
1776          else if (GraphPrintCheckerState->isNoReturnCall(N))
1777            Out << "\\|Call to function marked \"noreturn\".";
1778          else if (GraphPrintCheckerState->isBadCall(N))
1779            Out << "\\|Call to NULL/Undefined.";
1780          else if (GraphPrintCheckerState->isUndefArg(N))
1781            Out << "\\|Argument in call is undefined";
1782#endif
1783
1784          break;
1785        }
1786
1787        const BlockEdge &E = cast<BlockEdge>(Loc);
1788        Out << "Edge: (B" << E.getSrc()->getBlockID() << ", B"
1789            << E.getDst()->getBlockID()  << ')';
1790
1791        if (const Stmt *T = E.getSrc()->getTerminator()) {
1792
1793          SourceLocation SLoc = T->getLocStart();
1794
1795          Out << "\\|Terminator: ";
1796          LangOptions LO; // FIXME.
1797          E.getSrc()->printTerminator(Out, LO);
1798
1799          if (SLoc.isFileID()) {
1800            Out << "\\lline="
1801              << GraphPrintSourceManager->getExpansionLineNumber(SLoc)
1802              << " col="
1803              << GraphPrintSourceManager->getExpansionColumnNumber(SLoc);
1804          }
1805
1806          if (isa<SwitchStmt>(T)) {
1807            const Stmt *Label = E.getDst()->getLabel();
1808
1809            if (Label) {
1810              if (const CaseStmt *C = dyn_cast<CaseStmt>(Label)) {
1811                Out << "\\lcase ";
1812                LangOptions LO; // FIXME.
1813                C->getLHS()->printPretty(Out, 0, PrintingPolicy(LO));
1814
1815                if (const Stmt *RHS = C->getRHS()) {
1816                  Out << " .. ";
1817                  RHS->printPretty(Out, 0, PrintingPolicy(LO));
1818                }
1819
1820                Out << ":";
1821              }
1822              else {
1823                assert (isa<DefaultStmt>(Label));
1824                Out << "\\ldefault:";
1825              }
1826            }
1827            else
1828              Out << "\\l(implicit) default:";
1829          }
1830          else if (isa<IndirectGotoStmt>(T)) {
1831            // FIXME
1832          }
1833          else {
1834            Out << "\\lCondition: ";
1835            if (*E.getSrc()->succ_begin() == E.getDst())
1836              Out << "true";
1837            else
1838              Out << "false";
1839          }
1840
1841          Out << "\\l";
1842        }
1843
1844#if 0
1845          // FIXME: Replace with a general scheme to determine
1846          // the name of the check.
1847        if (GraphPrintCheckerState->isUndefControlFlow(N)) {
1848          Out << "\\|Control-flow based on\\lUndefined value.\\l";
1849        }
1850#endif
1851      }
1852    }
1853
1854    ProgramStateRef state = N->getState();
1855    Out << "\\|StateID: " << (void*) state.getPtr()
1856        << " NodeID: " << (void*) N << "\\|";
1857    state->printDOT(Out);
1858
1859    Out << "\\l";
1860
1861    if (const ProgramPointTag *tag = Loc.getTag()) {
1862      Out << "\\|Tag: " << tag->getTagDescription();
1863      Out << "\\l";
1864    }
1865    return Out.str();
1866  }
1867};
1868} // end llvm namespace
1869#endif
1870
1871#ifndef NDEBUG
1872template <typename ITERATOR>
1873ExplodedNode *GetGraphNode(ITERATOR I) { return *I; }
1874
1875template <> ExplodedNode*
1876GetGraphNode<llvm::DenseMap<ExplodedNode*, Expr*>::iterator>
1877  (llvm::DenseMap<ExplodedNode*, Expr*>::iterator I) {
1878  return I->first;
1879}
1880#endif
1881
1882void ExprEngine::ViewGraph(bool trim) {
1883#ifndef NDEBUG
1884  if (trim) {
1885    std::vector<ExplodedNode*> Src;
1886
1887    // Flush any outstanding reports to make sure we cover all the nodes.
1888    // This does not cause them to get displayed.
1889    for (BugReporter::iterator I=BR.begin(), E=BR.end(); I!=E; ++I)
1890      const_cast<BugType*>(*I)->FlushReports(BR);
1891
1892    // Iterate through the reports and get their nodes.
1893    for (BugReporter::EQClasses_iterator
1894           EI = BR.EQClasses_begin(), EE = BR.EQClasses_end(); EI != EE; ++EI) {
1895      BugReportEquivClass& EQ = *EI;
1896      const BugReport &R = **EQ.begin();
1897      ExplodedNode *N = const_cast<ExplodedNode*>(R.getErrorNode());
1898      if (N) Src.push_back(N);
1899    }
1900
1901    ViewGraph(&Src[0], &Src[0]+Src.size());
1902  }
1903  else {
1904    GraphPrintCheckerState = this;
1905    GraphPrintSourceManager = &getContext().getSourceManager();
1906
1907    llvm::ViewGraph(*G.roots_begin(), "ExprEngine");
1908
1909    GraphPrintCheckerState = NULL;
1910    GraphPrintSourceManager = NULL;
1911  }
1912#endif
1913}
1914
1915void ExprEngine::ViewGraph(ExplodedNode** Beg, ExplodedNode** End) {
1916#ifndef NDEBUG
1917  GraphPrintCheckerState = this;
1918  GraphPrintSourceManager = &getContext().getSourceManager();
1919
1920  std::auto_ptr<ExplodedGraph> TrimmedG(G.Trim(Beg, End).first);
1921
1922  if (!TrimmedG.get())
1923    llvm::errs() << "warning: Trimmed ExplodedGraph is empty.\n";
1924  else
1925    llvm::ViewGraph(*TrimmedG->roots_begin(), "TrimmedExprEngine");
1926
1927  GraphPrintCheckerState = NULL;
1928  GraphPrintSourceManager = NULL;
1929#endif
1930}
1931