clang  10.0.0svn
BugReporter.h
Go to the documentation of this file.
1 //===- BugReporter.h - Generate PathDiagnostics -----------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file defines BugReporter, a utility class for generating
10 // PathDiagnostics for analyses based on ProgramState.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #ifndef LLVM_CLANG_STATICANALYZER_CORE_BUGREPORTER_BUGREPORTER_H
15 #define LLVM_CLANG_STATICANALYZER_CORE_BUGREPORTER_BUGREPORTER_H
16 
17 #include "clang/Basic/LLVM.h"
26 #include "llvm/ADT/ArrayRef.h"
27 #include "llvm/ADT/DenseSet.h"
28 #include "llvm/ADT/FoldingSet.h"
29 #include "llvm/ADT/ImmutableSet.h"
30 #include "llvm/ADT/None.h"
31 #include "llvm/ADT/SmallSet.h"
32 #include "llvm/ADT/SmallVector.h"
33 #include "llvm/ADT/StringMap.h"
34 #include "llvm/ADT/StringRef.h"
35 #include "llvm/ADT/ilist.h"
36 #include "llvm/ADT/ilist_node.h"
37 #include "llvm/ADT/iterator_range.h"
38 #include <cassert>
39 #include <memory>
40 #include <string>
41 #include <utility>
42 #include <vector>
43 
44 namespace clang {
45 
46 class AnalyzerOptions;
47 class ASTContext;
48 class Decl;
49 class DiagnosticsEngine;
50 class LocationContext;
51 class SourceManager;
52 class Stmt;
53 
54 namespace ento {
55 
56 class BugType;
57 class CheckerBase;
58 class ExplodedGraph;
59 class ExplodedNode;
60 class ExprEngine;
61 class MemRegion;
62 class SValBuilder;
63 
64 //===----------------------------------------------------------------------===//
65 // Interface for individual bug reports.
66 //===----------------------------------------------------------------------===//
67 
68 /// A mapping from diagnostic consumers to the diagnostics they should
69 /// consume.
71  llvm::DenseMap<PathDiagnosticConsumer *, std::unique_ptr<PathDiagnostic>>;
72 
73 /// This class provides an interface through which checkers can create
74 /// individual bug reports.
75 class BugReport : public llvm::ilist_node<BugReport> {
76 public:
77  class NodeResolver {
78  virtual void anchor();
79 
80  public:
81  virtual ~NodeResolver() = default;
82 
83  virtual const ExplodedNode*
84  getOriginalNode(const ExplodedNode *N) = 0;
85  };
86 
87  using ranges_iterator = const SourceRange *;
89  using visitor_iterator = VisitorList::iterator;
92 
93 protected:
94  friend class BugReportEquivClass;
95  friend class BugReporter;
96 
97  const BugType& BT;
98  const Decl *DeclWithIssue = nullptr;
99  std::string ShortDescription;
100  std::string Description;
104 
105  const ExplodedNode *ErrorNode = nullptr;
109 
112 
113  /// A (stack of) a set of symbols that are registered with this
114  /// report as being "interesting", and thus used to help decide which
115  /// diagnostics to include when constructing the final path diagnostic.
116  /// The stack is largely used by BugReporter when generating PathDiagnostics
117  /// for multiple PathDiagnosticConsumers.
119 
120  /// A (stack of) set of regions that are registered with this report as being
121  /// "interesting", and thus used to help decide which diagnostics
122  /// to include when constructing the final path diagnostic.
123  /// The stack is largely used by BugReporter when generating PathDiagnostics
124  /// for multiple PathDiagnosticConsumers.
126 
127  /// A set of location contexts that correspoind to call sites which should be
128  /// considered "interesting".
129  llvm::SmallSet<const LocationContext *, 2> InterestingLocationContexts;
130 
131  /// A set of custom visitors which generate "event" diagnostics at
132  /// interesting points in the path.
134 
135  /// Used for ensuring the visitors are only added once.
136  llvm::FoldingSet<BugReporterVisitor> CallbacksSet;
137 
138  /// When set, this flag disables all callstack pruning from a diagnostic
139  /// path. This is useful for some reports that want maximum fidelty
140  /// when reporting an issue.
141  bool DoNotPrunePath = false;
142 
143  /// Used to track unique reasons why a bug report might be invalid.
144  ///
145  /// \sa markInvalid
146  /// \sa removeInvalidation
147  using InvalidationRecord = std::pair<const void *, const void *>;
148 
149  /// If non-empty, this bug report is likely a false positive and should not be
150  /// shown to the user.
151  ///
152  /// \sa markInvalid
153  /// \sa removeInvalidation
154  llvm::SmallSet<InvalidationRecord, 4> Invalidations;
155 
156  /// Conditions we're already tracking.
157  llvm::SmallSet<const ExplodedNode *, 4> TrackedConditions;
158 
159 private:
160  // Used internally by BugReporter.
161  Symbols &getInterestingSymbols();
162  Regions &getInterestingRegions();
163 
164  void lazyInitializeInterestingSets();
165  void pushInterestingSymbolsAndRegions();
166  void popInterestingSymbolsAndRegions();
167 
168 public:
169  BugReport(const BugType& bt, StringRef desc, const ExplodedNode *errornode)
170  : BT(bt), Description(desc), ErrorNode(errornode) {}
171 
172  BugReport(const BugType& bt, StringRef shortDesc, StringRef desc,
173  const ExplodedNode *errornode)
174  : BT(bt), ShortDescription(shortDesc), Description(desc),
175  ErrorNode(errornode) {}
176 
177  BugReport(const BugType &bt, StringRef desc, PathDiagnosticLocation l)
178  : BT(bt), Description(desc), Location(l) {}
179 
180  /// Create a BugReport with a custom uniqueing location.
181  ///
182  /// The reports that have the same report location, description, bug type, and
183  /// ranges are uniqued - only one of the equivalent reports will be presented
184  /// to the user. This method allows to rest the location which should be used
185  /// for uniquing reports. For example, memory leaks checker, could set this to
186  /// the allocation site, rather then the location where the bug is reported.
187  BugReport(BugType& bt, StringRef desc, const ExplodedNode *errornode,
188  PathDiagnosticLocation LocationToUnique, const Decl *DeclToUnique)
189  : BT(bt), Description(desc), UniqueingLocation(LocationToUnique),
190  UniqueingDecl(DeclToUnique), ErrorNode(errornode) {}
191 
192  virtual ~BugReport();
193 
194  const BugType& getBugType() const { return BT; }
195  //BugType& getBugType() { return BT; }
196 
197  /// True when the report has an execution path associated with it.
198  ///
199  /// A report is said to be path-sensitive if it was thrown against a
200  /// particular exploded node in the path-sensitive analysis graph.
201  /// Path-sensitive reports have their intermediate path diagnostics
202  /// auto-generated, perhaps with the help of checker-defined visitors,
203  /// and may contain extra notes.
204  /// Path-insensitive reports consist only of a single warning message
205  /// in a specific location, and perhaps extra notes.
206  /// Path-sensitive checkers are allowed to throw path-insensitive reports.
207  bool isPathSensitive() const { return ErrorNode != nullptr; }
208 
209  const ExplodedNode *getErrorNode() const { return ErrorNode; }
210 
211  StringRef getDescription() const { return Description; }
212 
213  StringRef getShortDescription(bool UseFallback = true) const {
214  if (ShortDescription.empty() && UseFallback)
215  return Description;
216  return ShortDescription;
217  }
218 
219  /// Indicates whether or not any path pruning should take place
220  /// when generating a PathDiagnostic from this BugReport.
221  bool shouldPrunePath() const { return !DoNotPrunePath; }
222 
223  /// Disable all path pruning when generating a PathDiagnostic.
224  void disablePathPruning() { DoNotPrunePath = true; }
225 
226  void markInteresting(SymbolRef sym);
227  void markInteresting(const MemRegion *R);
228  void markInteresting(SVal V);
229  void markInteresting(const LocationContext *LC);
230 
231  bool isInteresting(SymbolRef sym);
232  bool isInteresting(const MemRegion *R);
233  bool isInteresting(SVal V);
234  bool isInteresting(const LocationContext *LC);
235 
236  /// Returns whether or not this report should be considered valid.
237  ///
238  /// Invalid reports are those that have been classified as likely false
239  /// positives after the fact.
240  bool isValid() const {
241  return Invalidations.empty();
242  }
243 
244  /// Marks the current report as invalid, meaning that it is probably a false
245  /// positive and should not be reported to the user.
246  ///
247  /// The \p Tag and \p Data arguments are intended to be opaque identifiers for
248  /// this particular invalidation, where \p Tag represents the visitor
249  /// responsible for invalidation, and \p Data represents the reason this
250  /// visitor decided to invalidate the bug report.
251  ///
252  /// \sa removeInvalidation
253  void markInvalid(const void *Tag, const void *Data) {
254  Invalidations.insert(std::make_pair(Tag, Data));
255  }
256 
257  /// Return the canonical declaration, be it a method or class, where
258  /// this issue semantically occurred.
259  const Decl *getDeclWithIssue() const;
260 
261  /// Specifically set the Decl where an issue occurred. This isn't necessary
262  /// for BugReports that cover a path as it will be automatically inferred.
263  void setDeclWithIssue(const Decl *declWithIssue) {
264  DeclWithIssue = declWithIssue;
265  }
266 
267  /// Add new item to the list of additional notes that need to be attached to
268  /// this path-insensitive report. If you want to add extra notes to a
269  /// path-sensitive report, you need to use a BugReporterVisitor because it
270  /// allows you to specify where exactly in the auto-generated path diagnostic
271  /// the extra note should appear.
272  void addNote(StringRef Msg, const PathDiagnosticLocation &Pos,
273  ArrayRef<SourceRange> Ranges) {
274  auto P = std::make_shared<PathDiagnosticNotePiece>(Pos, Msg);
275 
276  for (const auto &R : Ranges)
277  P->addRange(R);
278 
279  Notes.push_back(std::move(P));
280  }
281 
282  // FIXME: Instead of making an override, we could have default-initialized
283  // Ranges with {}, however it crashes the MSVC 2013 compiler.
284  void addNote(StringRef Msg, const PathDiagnosticLocation &Pos) {
285  std::vector<SourceRange> Ranges;
286  addNote(Msg, Pos, Ranges);
287  }
288 
289  virtual const NoteList &getNotes() {
290  return Notes;
291  }
292 
293  /// This allows for addition of meta data to the diagnostic.
294  ///
295  /// Currently, only the HTMLDiagnosticClient knows how to display it.
296  void addExtraText(StringRef S) {
297  ExtraText.push_back(S);
298  }
299 
300  virtual const ExtraTextList &getExtraText() {
301  return ExtraText;
302  }
303 
304  /// Return the "definitive" location of the reported bug.
305  ///
306  /// While a bug can span an entire path, usually there is a specific
307  /// location that can be used to identify where the key issue occurred.
308  /// This location is used by clients rendering diagnostics.
309  virtual PathDiagnosticLocation getLocation(const SourceManager &SM) const;
310 
311  /// Get the location on which the report should be uniqued.
313  return UniqueingLocation;
314  }
315 
316  /// Get the declaration containing the uniqueing location.
317  const Decl *getUniqueingDecl() const {
318  return UniqueingDecl;
319  }
320 
321  const Stmt *getStmt() const;
322 
323  /// Add a range to a bug report.
324  ///
325  /// Ranges are used to highlight regions of interest in the source code.
326  /// They should be at the same source code line as the BugReport location.
327  /// By default, the source range of the statement corresponding to the error
328  /// node will be used; add a single invalid range to specify absence of
329  /// ranges.
331  assert((R.isValid() || Ranges.empty()) && "Invalid range can only be used "
332  "to specify that the report does not have a range.");
333  Ranges.push_back(R);
334  }
335 
336  /// Get the SourceRanges associated with the report.
337  virtual llvm::iterator_range<ranges_iterator> getRanges();
338 
339  /// Add custom or predefined bug report visitors to this report.
340  ///
341  /// The visitors should be used when the default trace is not sufficient.
342  /// For example, they allow constructing a more elaborate trace.
343  /// \sa registerConditionVisitor(), registerTrackNullOrUndefValue(),
344  /// registerFindLastStore(), registerNilReceiverVisitor(), and
345  /// registerVarDeclsLastStore().
346  void addVisitor(std::unique_ptr<BugReporterVisitor> visitor);
347 
348  /// Remove all visitors attached to this bug report.
349  void clearVisitors();
350 
351  /// Iterators through the custom diagnostic visitors.
352  visitor_iterator visitor_begin() { return Callbacks.begin(); }
353  visitor_iterator visitor_end() { return Callbacks.end(); }
354 
355  /// Notes that the condition of the CFGBlock associated with \p Cond is
356  /// being tracked.
357  /// \returns false if the condition is already being tracked.
358  bool addTrackedCondition(const ExplodedNode *Cond) {
359  return TrackedConditions.insert(Cond).second;
360  }
361 
362  /// Profile to identify equivalent bug reports for error report coalescing.
363  /// Reports are uniqued to ensure that we do not emit multiple diagnostics
364  /// for each bug.
365  virtual void Profile(llvm::FoldingSetNodeID& hash) const;
366 };
367 
368 //===----------------------------------------------------------------------===//
369 // BugTypes (collections of related reports).
370 //===----------------------------------------------------------------------===//
371 
372 class BugReportEquivClass : public llvm::FoldingSetNode {
373  friend class BugReporter;
374 
375  /// List of *owned* BugReport objects.
376  llvm::ilist<BugReport> Reports;
377 
378  void AddReport(std::unique_ptr<BugReport> R) {
379  Reports.push_back(R.release());
380  }
381 
382 public:
383  BugReportEquivClass(std::unique_ptr<BugReport> R) { AddReport(std::move(R)); }
385 
386  void Profile(llvm::FoldingSetNodeID& ID) const {
387  assert(!Reports.empty());
388  Reports.front().Profile(ID);
389  }
390 
391  using iterator = llvm::ilist<BugReport>::iterator;
392  using const_iterator = llvm::ilist<BugReport>::const_iterator;
393 
394  iterator begin() { return Reports.begin(); }
395  iterator end() { return Reports.end(); }
396 
397  const_iterator begin() const { return Reports.begin(); }
398  const_iterator end() const { return Reports.end(); }
399 };
400 
401 //===----------------------------------------------------------------------===//
402 // BugReporter and friends.
403 //===----------------------------------------------------------------------===//
404 
406 public:
407  virtual ~BugReporterData();
408 
409  virtual DiagnosticsEngine& getDiagnostic() = 0;
410  virtual ArrayRef<PathDiagnosticConsumer*> getPathDiagnosticConsumers() = 0;
411  virtual ASTContext &getASTContext() = 0;
412  virtual SourceManager &getSourceManager() = 0;
413  virtual AnalyzerOptions &getAnalyzerOptions() = 0;
414 };
415 
416 /// BugReporter is a utility class for generating PathDiagnostics for analysis.
417 /// It collects the BugReports and BugTypes and knows how to generate
418 /// and flush the corresponding diagnostics.
419 ///
420 /// The base class is used for generating path-insensitive
421 class BugReporter {
422 public:
423  enum Kind { BaseBRKind, GRBugReporterKind };
424 
425 private:
426  using BugTypesTy = llvm::ImmutableSet<BugType *>;
427 
428  BugTypesTy::Factory F;
429  BugTypesTy BugTypes;
430 
431  const Kind kind;
432  BugReporterData& D;
433 
434  /// Generate and flush the diagnostics for the given bug report.
435  void FlushReport(BugReportEquivClass& EQ);
436 
437  /// Generate the diagnostics for the given bug report.
438  std::unique_ptr<DiagnosticForConsumerMapTy>
439  generateDiagnosticForConsumerMap(BugReport *exampleReport,
441  ArrayRef<BugReport *> bugReports);
442 
443  /// The set of bug reports tracked by the BugReporter.
444  llvm::FoldingSet<BugReportEquivClass> EQClasses;
445 
446  /// A vector of BugReports for tracking the allocated pointers and cleanup.
447  std::vector<BugReportEquivClass *> EQClassesVector;
448 
449 protected:
451  : BugTypes(F.getEmptySet()), kind(k), D(d) {}
452 
453 public:
455  : BugTypes(F.getEmptySet()), kind(BaseBRKind), D(d) {}
456  virtual ~BugReporter();
457 
458  /// Generate and flush diagnostics for all bug reports.
459  void FlushReports();
460 
461  Kind getKind() const { return kind; }
462 
464  return D.getDiagnostic();
465  }
466 
468  return D.getPathDiagnosticConsumers();
469  }
470 
471  /// Iterator over the set of BugTypes tracked by the BugReporter.
472  using iterator = BugTypesTy::iterator;
473  iterator begin() { return BugTypes.begin(); }
474  iterator end() { return BugTypes.end(); }
475 
476  /// Iterator over the set of BugReports tracked by the BugReporter.
477  using EQClasses_iterator = llvm::FoldingSet<BugReportEquivClass>::iterator;
478  EQClasses_iterator EQClasses_begin() { return EQClasses.begin(); }
479  EQClasses_iterator EQClasses_end() { return EQClasses.end(); }
480 
482 
484 
486 
487  virtual std::unique_ptr<DiagnosticForConsumerMapTy>
489  ArrayRef<BugReport *> &bugReports) {
490  return {};
491  }
492 
493  void Register(const BugType *BT);
494 
495  /// Add the given report to the set of reports tracked by BugReporter.
496  ///
497  /// The reports are usually generated by the checkers. Further, they are
498  /// folded based on the profile value, which is done to coalesce similar
499  /// reports.
500  void emitReport(std::unique_ptr<BugReport> R);
501 
502  void EmitBasicReport(const Decl *DeclWithIssue, const CheckerBase *Checker,
503  StringRef BugName, StringRef BugCategory,
504  StringRef BugStr, PathDiagnosticLocation Loc,
506 
507  void EmitBasicReport(const Decl *DeclWithIssue, CheckName CheckName,
508  StringRef BugName, StringRef BugCategory,
509  StringRef BugStr, PathDiagnosticLocation Loc,
511 
512 private:
513  llvm::StringMap<BugType *> StrBugTypes;
514 
515  /// Returns a BugType that is associated with the given name and
516  /// category.
517  BugType *getBugTypeForName(CheckName CheckName, StringRef name,
518  StringRef category);
519 };
520 
521 /// GRBugReporter is used for generating path-sensitive reports.
522 class GRBugReporter : public BugReporter {
523  ExprEngine& Eng;
524 
525 public:
527  : BugReporter(d, GRBugReporterKind), Eng(eng) {}
528 
529  ~GRBugReporter() override;
530 
531  /// getGraph - Get the exploded graph created by the analysis engine
532  /// for the analyzed method or function.
533  ExplodedGraph &getGraph();
534 
535  /// getStateManager - Return the state manager used by the analysis
536  /// engine.
537  ProgramStateManager &getStateManager();
538 
539  /// \p bugReports A set of bug reports within a *single* equivalence class
540  ///
541  /// \return A mapping from consumers to the corresponding diagnostics.
542  /// Iterates through the bug reports within a single equivalence class,
543  /// stops at a first non-invalidated report.
544  std::unique_ptr<DiagnosticForConsumerMapTy>
545  generatePathDiagnostics(ArrayRef<PathDiagnosticConsumer *> consumers,
546  ArrayRef<BugReport *> &bugReports) override;
547 
548  /// classof - Used by isa<>, cast<>, and dyn_cast<>.
549  static bool classof(const BugReporter* R) {
550  return R->getKind() == GRBugReporterKind;
551  }
552 };
553 
554 
557 
558 public:
560 
561  const ExplodedNode *getOriginalNode(const ExplodedNode *N) override {
562  return M.lookup(N);
563  }
564 };
565 
567  GRBugReporter &BR;
568  NodeMapClosure NMC;
569 
570  virtual void anchor();
571 
572 public:
574  : BR(br), NMC(Backmap) {}
575 
576  virtual ~BugReporterContext() = default;
577 
578  GRBugReporter& getBugReporter() { return BR; }
579 
580  ExplodedGraph &getGraph() { return BR.getGraph(); }
581 
583  return BR.getStateManager();
584  }
585 
587  return getStateManager().getSValBuilder();
588  }
589 
591  return BR.getContext();
592  }
593 
595  return BR.getSourceManager();
596  }
597 
599  return BR.getAnalyzerOptions();
600  }
601 
602  NodeMapClosure& getNodeResolver() { return NMC; }
603 };
604 
605 
606 /// The tag upon which the TagVisitor reacts. Add these in order to display
607 /// additional PathDiagnosticEventPieces along the path.
608 class NoteTag : public ProgramPointTag {
609 public:
610  using Callback =
611  std::function<std::string(BugReporterContext &, BugReport &)>;
612 
613 private:
614  static int Kind;
615 
616  const Callback Cb;
617  const bool IsPrunable;
618 
619  NoteTag(Callback &&Cb, bool IsPrunable)
620  : ProgramPointTag(&Kind), Cb(std::move(Cb)), IsPrunable(IsPrunable) {}
621 
622 public:
623  static bool classof(const ProgramPointTag *T) {
624  return T->getTagKind() == &Kind;
625  }
626 
628  BugReport &R) const {
629  std::string Msg = Cb(BRC, R);
630  if (Msg.empty())
631  return None;
632 
633  return std::move(Msg);
634  }
635 
636  StringRef getTagDescription() const override {
637  // TODO: Remember a few examples of generated messages
638  // and display them in the ExplodedGraph dump by
639  // returning them from this function.
640  return "Note Tag";
641  }
642 
643  bool isPrunable() const { return IsPrunable; }
644 
645  // Manage memory for NoteTag objects.
646  class Factory {
647  std::vector<std::unique_ptr<NoteTag>> Tags;
648 
649  public:
650  const NoteTag *makeNoteTag(Callback &&Cb, bool IsPrunable = false) {
651  // We cannot use make_unique because we cannot access the private
652  // constructor from inside it.
653  std::unique_ptr<NoteTag> T(new NoteTag(std::move(Cb), IsPrunable));
654  Tags.push_back(std::move(T));
655  return Tags.back().get();
656  }
657  };
658 
659  friend class TagVisitor;
660 };
661 
662 } // namespace ento
663 
664 } // namespace clang
665 
666 #endif // LLVM_CLANG_STATICANALYZER_CORE_BUGREPORTER_BUGREPORTER_H
const ExplodedNode * getOriginalNode(const ExplodedNode *N) override
Definition: BugReporter.h:561
BugReporter(BugReporterData &d)
Definition: BugReporter.h:454
bool shouldPrunePath() const
Indicates whether or not any path pruning should take place when generating a PathDiagnostic from thi...
Definition: BugReporter.h:221
MemRegion - The root abstract class for all memory regions.
Definition: MemRegion.h:94
PathDiagnosticLocation getUniqueingLocation() const
Get the location on which the report should be uniqued.
Definition: BugReporter.h:312
bool isInteresting(SymbolRef sym)
AnalyzerOptions & getAnalyzerOptions()
Definition: BugReporter.h:598
Stmt - This represents one statement.
Definition: Stmt.h:66
const NoteTag * makeNoteTag(Callback &&Cb, bool IsPrunable=false)
Definition: BugReporter.h:650
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:88
StringRef getDescription() const
Definition: BugReporter.h:211
StringRef P
ArrayRef< PathDiagnosticConsumer * > getPathDiagnosticConsumers()
Definition: BugReporter.h:467
The l-value was an access to a declared entity or something equivalently strong, like the address of ...
RangeSelector name(std::string ID)
Given a node with a "name", (like NamedDecl, DeclRefExpr or CxxCtorInitializer) selects the name&#39;s to...
virtual PathDiagnosticLocation getLocation(const SourceManager &SM) const
Return the "definitive" location of the reported bug.
virtual std::unique_ptr< DiagnosticForConsumerMapTy > generatePathDiagnostics(ArrayRef< PathDiagnosticConsumer *> consumers, ArrayRef< BugReport *> &bugReports)
Definition: BugReporter.h:488
NodeMapClosure(InterExplodedGraphMap &m)
Definition: BugReporter.h:559
void addNote(StringRef Msg, const PathDiagnosticLocation &Pos)
Definition: BugReporter.h:284
void disablePathPruning()
Disable all path pruning when generating a PathDiagnostic.
Definition: BugReporter.h:224
SmallVector< SourceRange, 4 > Ranges
Definition: BugReporter.h:106
virtual AnalyzerOptions & getAnalyzerOptions()=0
const BugType & BT
Definition: BugReporter.h:97
llvm::DenseMap< PathDiagnosticConsumer *, std::unique_ptr< PathDiagnostic > > DiagnosticForConsumerMapTy
A mapping from diagnostic consumers to the diagnostics they should consume.
Definition: BugReporter.h:71
void clearVisitors()
Remove all visitors attached to this bug report.
Symbolic value.
Definition: SymExpr.h:29
void addRange(SourceRange R)
Add a range to a bug report.
Definition: BugReporter.h:330
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:154
BugReport(BugType &bt, StringRef desc, const ExplodedNode *errornode, PathDiagnosticLocation LocationToUnique, const Decl *DeclToUnique)
Create a BugReport with a custom uniqueing location.
Definition: BugReporter.h:187
bool isValid() const
Returns whether or not this report should be considered valid.
Definition: BugReporter.h:240
std::function< std::string(BugReporterContext &, BugReport &)> Callback
Definition: BugReporter.h:611
Definition: Format.h:2274
llvm::SmallSet< const ExplodedNode *, 4 > TrackedConditions
Conditions we&#39;re already tracking.
Definition: BugReporter.h:157
std::string ShortDescription
Definition: BugReporter.h:99
virtual DiagnosticsEngine & getDiagnostic()=0
llvm::SmallSet< InvalidationRecord, 4 > Invalidations
If non-empty, this bug report is likely a false positive and should not be shown to the user...
Definition: BugReporter.h:154
SmallVector< Regions *, 2 > interestingRegions
A (stack of) set of regions that are registered with this report as being "interesting", and thus used to help decide which diagnostics to include when constructing the final path diagnostic.
Definition: BugReporter.h:125
virtual llvm::iterator_range< ranges_iterator > getRanges()
Get the SourceRanges associated with the report.
llvm::FoldingSet< BugReporterVisitor > CallbacksSet
Used for ensuring the visitors are only added once.
Definition: BugReporter.h:136
const Stmt * getStmt() const
llvm::SmallSet< const LocationContext *, 2 > InterestingLocationContexts
A set of location contexts that correspoind to call sites which should be considered "interesting"...
Definition: BugReporter.h:129
const BugType & getBugType() const
Definition: BugReporter.h:194
BugReporter(BugReporterData &d, Kind k)
Definition: BugReporter.h:450
Forward-declares and imports various common LLVM datatypes that clang wants to use unqualified...
ASTContext & getContext()
Definition: BugReporter.h:481
Concrete class used by the front-end to report problems and issues.
Definition: Diagnostic.h:149
void Profile(llvm::FoldingSetNodeID &ID) const
Definition: BugReporter.h:386
GRBugReporter(BugReporterData &d, ExprEngine &eng)
Definition: BugReporter.h:526
const Decl * getDeclWithIssue() const
Return the canonical declaration, be it a method or class, where this issue semantically occurred...
static bool classof(const ProgramPointTag *T)
Definition: BugReporter.h:623
void addVisitor(std::unique_ptr< BugReporterVisitor > visitor)
Add custom or predefined bug report visitors to this report.
virtual const NoteList & getNotes()
Definition: BugReporter.h:289
const_iterator begin() const
Definition: BugReporter.h:397
NodeMapClosure & getNodeResolver()
Definition: BugReporter.h:602
const Decl * UniqueingDecl
Definition: BugReporter.h:103
VisitorList::iterator visitor_iterator
Definition: BugReporter.h:89
BugReportEquivClass(std::unique_ptr< BugReport > R)
Definition: BugReporter.h:383
bool DoNotPrunePath
When set, this flag disables all callstack pruning from a diagnostic path.
Definition: BugReporter.h:141
__v2du d
Definition: emmintrin.h:413
virtual const ExtraTextList & getExtraText()
Definition: BugReporter.h:300
BugTypesTy::iterator iterator
Iterator over the set of BugTypes tracked by the BugReporter.
Definition: BugReporter.h:472
visitor_iterator visitor_end()
Definition: BugReporter.h:353
visitor_iterator visitor_begin()
Iterators through the custom diagnostic visitors.
Definition: BugReporter.h:352
#define V(N, I)
Definition: ASTContext.h:2907
virtual SourceManager & getSourceManager()=0
const Decl * getUniqueingDecl() const
Get the declaration containing the uniqueing location.
Definition: BugReporter.h:317
void addNote(StringRef Msg, const PathDiagnosticLocation &Pos, ArrayRef< SourceRange > Ranges)
Add new item to the list of additional notes that need to be attached to this path-insensitive report...
Definition: BugReporter.h:272
BugReporterContext(GRBugReporter &br, InterExplodedGraphMap &Backmap)
Definition: BugReporter.h:573
void markInteresting(SymbolRef sym)
The tag upon which the TagVisitor reacts.
Definition: BugReporter.h:608
std::pair< const void *, const void * > InvalidationRecord
Used to track unique reasons why a bug report might be invalid.
Definition: BugReporter.h:147
const SourceManager & SM
Definition: Format.cpp:1572
AnalyzerOptions & getAnalyzerOptions()
Definition: BugReporter.h:485
virtual ArrayRef< PathDiagnosticConsumer * > getPathDiagnosticConsumers()=0
BugReporter is a utility class for generating PathDiagnostics for analysis.
Definition: BugReporter.h:421
PathDiagnosticLocation UniqueingLocation
Definition: BugReporter.h:102
static bool classof(const BugReporter *R)
classof - Used by isa<>, cast<>, and dyn_cast<>.
Definition: BugReporter.h:549
Kind
EQClasses_iterator EQClasses_begin()
Definition: BugReporter.h:478
const ExplodedNode * ErrorNode
Definition: BugReporter.h:105
ProgramPoints can be "tagged" as representing points specific to a given analysis entity...
Definition: ProgramPoint.h:39
ExplodedGraph & getGraph()
getGraph - Get the exploded graph created by the analysis engine for the analyzed method or function...
std::string Description
Definition: BugReporter.h:100
SVal - This represents a symbolic expression, which can be either an L-value or an R-value...
Definition: SVals.h:75
PathDiagnosticLocation Location
Definition: BugReporter.h:101
bool isPrunable() const
Definition: BugReporter.h:643
const Decl * DeclWithIssue
Definition: BugReporter.h:98
VisitorList Callbacks
A set of custom visitors which generate "event" diagnostics at interesting points in the path...
Definition: BugReporter.h:133
SmallVector< Symbols *, 2 > interestingSymbols
A (stack of) a set of symbols that are registered with this report as being "interesting", and thus used to help decide which diagnostics to include when constructing the final path diagnostic.
Definition: BugReporter.h:118
Dataflow Directional Tag Classes.
ExtraTextList ExtraText
Definition: BugReporter.h:107
bool addTrackedCondition(const ExplodedNode *Cond)
Notes that the condition of the CFGBlock associated with Cond is being tracked.
Definition: BugReporter.h:358
BugReport(const BugType &bt, StringRef desc, const ExplodedNode *errornode)
Definition: BugReporter.h:169
Optional< std::string > generateMessage(BugReporterContext &BRC, BugReport &R) const
Definition: BugReporter.h:627
BugReport(const BugType &bt, StringRef desc, PathDiagnosticLocation l)
Definition: BugReporter.h:177
GRBugReporter & getBugReporter()
Definition: BugReporter.h:578
BugReport(const BugType &bt, StringRef shortDesc, StringRef desc, const ExplodedNode *errornode)
Definition: BugReporter.h:172
llvm::DenseMap< const ExplodedNode *, const ExplodedNode * > InterExplodedGraphMap
StringRef getTagDescription() const override
Definition: BugReporter.h:636
DiagnosticsEngine & getDiagnostic()
Definition: BugReporter.h:463
const_iterator end() const
Definition: BugReporter.h:398
ProgramStateManager & getStateManager()
Definition: BugReporter.h:582
const ExplodedNode * getErrorNode() const
Definition: BugReporter.h:209
virtual void Profile(llvm::FoldingSetNodeID &hash) const
Profile to identify equivalent bug reports for error report coalescing.
EQClasses_iterator EQClasses_end()
Definition: BugReporter.h:479
StringRef getShortDescription(bool UseFallback=true) const
Definition: BugReporter.h:213
llvm::FoldingSet< BugReportEquivClass >::iterator EQClasses_iterator
Iterator over the set of BugReports tracked by the BugReporter.
Definition: BugReporter.h:477
Stores options for the analyzer from the command line.
llvm::ilist< BugReport >::iterator iterator
Definition: BugReporter.h:391
SourceManager & getSourceManager()
Definition: BugReporter.h:483
ProgramStateManager & getStateManager()
getStateManager - Return the state manager used by the analysis engine.
Defines the clang::SourceLocation class and associated facilities.
bool isValid() const
void addExtraText(StringRef S)
This allows for addition of meta data to the diagnostic.
Definition: BugReporter.h:296
GRBugReporter is used for generating path-sensitive reports.
Definition: BugReporter.h:522
void markInvalid(const void *Tag, const void *Data)
Marks the current report as invalid, meaning that it is probably a false positive and should not be r...
Definition: BugReporter.h:253
unsigned kind
All of the diagnostics that can be emitted by the frontend.
Definition: DiagnosticIDs.h:60
virtual const ExplodedNode * getOriginalNode(const ExplodedNode *N)=0
A trivial tuple used to represent a source range.
This class provides an interface through which checkers can create individual bug reports...
Definition: BugReporter.h:75
llvm::ilist< BugReport >::const_iterator const_iterator
Definition: BugReporter.h:392
This class handles loading and caching of source files into memory.
const void * getTagKind() const
Used to implement &#39;isKind&#39; in subclasses.
Definition: ProgramPoint.h:46
virtual ASTContext & getASTContext()=0
SourceManager & getSourceManager()
Definition: BugReporter.h:594
void setDeclWithIssue(const Decl *declWithIssue)
Specifically set the Decl where an issue occurred.
Definition: BugReporter.h:263
bool isPathSensitive() const
True when the report has an execution path associated with it.
Definition: BugReporter.h:207