diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2012-08-19 10:33:04 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2012-08-19 10:33:04 +0000 |
commit | 657bc3d9848e3be92029b2416031340988cd0111 (patch) | |
tree | 5b9c2fa9d79942fbdce3d618e37e27c18263af9a /include/clang/StaticAnalyzer/Core | |
parent | 56d91b49b13fe55c918afbda19f6165b5fbff87a (diff) | |
download | src-657bc3d9848e3be92029b2416031340988cd0111.tar.gz src-657bc3d9848e3be92029b2416031340988cd0111.zip |
Vendor import of clang trunk r162107:vendor/clang/clang-trunk-r162107
Notes
Notes:
svn path=/vendor/clang/dist/; revision=239392
svn path=/vendor/clang/clang-trunk-r162107/; revision=239393; tag=vendor/clang/clang-trunk-r162107
Diffstat (limited to 'include/clang/StaticAnalyzer/Core')
7 files changed, 87 insertions, 65 deletions
diff --git a/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h b/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h index 5ee52cc61589..48393a379b39 100644 --- a/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h +++ b/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h @@ -81,15 +81,19 @@ protected: typedef llvm::DenseSet<SymbolRef> Symbols; typedef llvm::DenseSet<const MemRegion *> Regions; - /// A set of symbols that are registered with this report as being + /// 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. + /// The stack is largely used by BugReporter when generating PathDiagnostics + /// for multiple PathDiagnosticConsumers. + llvm::SmallVector<Symbols *, 2> interestingSymbols; + + /// 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. - Symbols interestingSymbols; - - /// A 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. - Regions interestingRegions; + /// The stack is largely used by BugReporter when generating PathDiagnostics + /// for multiple PathDiagnosticConsumers. + llvm::SmallVector<Regions *, 2> interestingRegions; /// A set of custom visitors which generate "event" diagnostics at /// interesting points in the path. @@ -107,6 +111,15 @@ protected: /// when reporting an issue. bool DoNotPrunePath; +private: + // Used internally by BugReporter. + Symbols &getInterestingSymbols(); + Regions &getInterestingRegions(); + + void lazyInitializeInterestingSets(); + void pushInterestingSymbolsAndRegions(); + void popInterestingSymbolsAndRegions(); + public: BugReport(BugType& bt, StringRef desc, const ExplodedNode *errornode) : BT(bt), DeclWithIssue(0), Description(desc), ErrorNode(errornode), @@ -160,9 +173,9 @@ public: void markInteresting(const MemRegion *R); void markInteresting(SVal V); - bool isInteresting(SymbolRef sym) const; - bool isInteresting(const MemRegion *R) const; - bool isInteresting(SVal V) const; + bool isInteresting(SymbolRef sym); + bool isInteresting(const MemRegion *R); + bool isInteresting(SVal V); unsigned getConfigurationChangeToken() const { return ConfigurationChangeToken; @@ -295,7 +308,7 @@ class BugReporterData { public: virtual ~BugReporterData(); virtual DiagnosticsEngine& getDiagnostic() = 0; - virtual PathDiagnosticConsumer* getPathDiagnosticConsumer() = 0; + virtual ArrayRef<PathDiagnosticConsumer*> getPathDiagnosticConsumers() = 0; virtual ASTContext &getASTContext() = 0; virtual SourceManager& getSourceManager() = 0; }; @@ -318,6 +331,12 @@ private: /// Generate and flush the diagnostics for the given bug report. void FlushReport(BugReportEquivClass& EQ); + /// Generate and flush the diagnostics for the given bug report + /// and PathDiagnosticConsumer. + void FlushReport(BugReport *exampleReport, + PathDiagnosticConsumer &PD, + ArrayRef<BugReport*> BugReports); + /// The set of bug reports tracked by the BugReporter. llvm::FoldingSet<BugReportEquivClass> EQClasses; /// A vector of BugReports for tracking the allocated pointers and cleanup. @@ -341,8 +360,8 @@ public: return D.getDiagnostic(); } - PathDiagnosticConsumer* getPathDiagnosticConsumer() { - return D.getPathDiagnosticConsumer(); + ArrayRef<PathDiagnosticConsumer*> getPathDiagnosticConsumers() { + return D.getPathDiagnosticConsumers(); } /// \brief Iterator over the set of BugTypes tracked by the BugReporter. @@ -360,7 +379,8 @@ public: SourceManager& getSourceManager() { return D.getSourceManager(); } virtual void GeneratePathDiagnostic(PathDiagnostic& pathDiagnostic, - SmallVectorImpl<BugReport *> &bugReports) {} + PathDiagnosticConsumer &PC, + ArrayRef<BugReport *> &bugReports) {} void Register(BugType *BT); @@ -421,7 +441,8 @@ public: ProgramStateManager &getStateManager(); virtual void GeneratePathDiagnostic(PathDiagnostic &pathDiagnostic, - SmallVectorImpl<BugReport*> &bugReports); + PathDiagnosticConsumer &PC, + ArrayRef<BugReport*> &bugReports); /// classof - Used by isa<>, cast<>, and dyn_cast<>. static bool classof(const BugReporter* R) { diff --git a/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h b/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h index 2e7abfa5cc3b..973cfb109c05 100644 --- a/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h +++ b/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h @@ -51,22 +51,25 @@ typedef const SymExpr* SymbolRef; class PathDiagnostic; class PathDiagnosticConsumer { +public: + typedef std::vector<std::pair<StringRef, std::string> > FilesMade; + +private: virtual void anchor(); public: PathDiagnosticConsumer() : flushed(false) {} virtual ~PathDiagnosticConsumer(); - void FlushDiagnostics(SmallVectorImpl<std::string> *FilesMade); + void FlushDiagnostics(FilesMade *FilesMade); virtual void FlushDiagnosticsImpl(std::vector<const PathDiagnostic *> &Diags, - SmallVectorImpl<std::string> *FilesMade) - = 0; + FilesMade *filesMade) = 0; virtual StringRef getName() const = 0; void HandlePathDiagnostic(PathDiagnostic *D); - enum PathGenerationScheme { Minimal, Extensive }; + enum PathGenerationScheme { None, Minimal, Extensive }; virtual PathGenerationScheme getGenerationScheme() const { return Minimal; } virtual bool supportsLogicalOpControlFlow() const { return false; } virtual bool supportsAllBlockEdges() const { return false; } @@ -332,15 +335,8 @@ public: ranges.push_back(SourceRange(B,E)); } - typedef const SourceRange* range_iterator; - - range_iterator ranges_begin() const { - return ranges.empty() ? NULL : &ranges[0]; - } - - range_iterator ranges_end() const { - return ranges_begin() + ranges.size(); - } + /// Return the SourceRanges associated with this PathDiagnosticPiece. + ArrayRef<SourceRange> getRanges() const { return ranges; } static inline bool classof(const PathDiagnosticPiece *P) { return true; diff --git a/include/clang/StaticAnalyzer/Core/PathDiagnosticConsumers.h b/include/clang/StaticAnalyzer/Core/PathDiagnosticConsumers.h index 65be3a406b43..3aab648dc574 100644 --- a/include/clang/StaticAnalyzer/Core/PathDiagnosticConsumers.h +++ b/include/clang/StaticAnalyzer/Core/PathDiagnosticConsumers.h @@ -15,6 +15,7 @@ #define LLVM_CLANG_GR_PATH_DIAGNOSTIC_CLIENTS_H #include <string> +#include <vector> namespace clang { @@ -23,24 +24,25 @@ class Preprocessor; namespace ento { class PathDiagnosticConsumer; +typedef std::vector<PathDiagnosticConsumer*> PathDiagnosticConsumers; -PathDiagnosticConsumer* -createHTMLDiagnosticConsumer(const std::string& prefix, const Preprocessor &PP); +void createHTMLDiagnosticConsumer(PathDiagnosticConsumers &C, + const std::string& prefix, + const Preprocessor &PP); -PathDiagnosticConsumer* -createPlistDiagnosticConsumer(const std::string& prefix, const Preprocessor &PP, - PathDiagnosticConsumer *SubPD = 0); +void createPlistDiagnosticConsumer(PathDiagnosticConsumers &C, + const std::string& prefix, + const Preprocessor &PP); -PathDiagnosticConsumer* -createPlistMultiFileDiagnosticConsumer(const std::string& prefix, - const Preprocessor &PP); +void createPlistMultiFileDiagnosticConsumer(PathDiagnosticConsumers &C, + const std::string& prefix, + const Preprocessor &PP); -PathDiagnosticConsumer* -createTextPathDiagnosticConsumer(const std::string& prefix, - const Preprocessor &PP); +void createTextPathDiagnosticConsumer(PathDiagnosticConsumers &C, + const std::string& prefix, + const Preprocessor &PP); -} // end GR namespace - -} // end clang namespace +} // end 'ento' namespace +} // end 'clang' namespace #endif diff --git a/include/clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h b/include/clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h index 1cc53d4423da..876196ba4f7f 100644 --- a/include/clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h +++ b/include/clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h @@ -19,6 +19,7 @@ #include "clang/Frontend/AnalyzerOptions.h" #include "clang/StaticAnalyzer/Core/BugReporter/BugReporter.h" #include "clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h" +#include "clang/StaticAnalyzer/Core/PathDiagnosticConsumers.h" namespace clang { @@ -32,8 +33,7 @@ class AnalysisManager : public BugReporterData { ASTContext &Ctx; DiagnosticsEngine &Diags; const LangOptions &LangOpts; - - OwningPtr<PathDiagnosticConsumer> PD; + PathDiagnosticConsumers PathConsumers; // Configurable components creators. StoreManagerCreator CreateStoreMgr; @@ -82,8 +82,9 @@ public: bool NoRetryExhausted; public: - AnalysisManager(ASTContext &ctx, DiagnosticsEngine &diags, - const LangOptions &lang, PathDiagnosticConsumer *pd, + AnalysisManager(ASTContext &ctx,DiagnosticsEngine &diags, + const LangOptions &lang, + const PathDiagnosticConsumers &Consumers, StoreManagerCreator storemgr, ConstraintManagerCreator constraintmgr, CheckerManager *checkerMgr, @@ -99,12 +100,7 @@ public: AnalysisInliningMode inliningMode, bool NoRetry); - /// Construct a clone of the given AnalysisManager with the given ASTContext - /// and DiagnosticsEngine. - AnalysisManager(ASTContext &ctx, DiagnosticsEngine &diags, - AnalysisManager &ParentAM); - - ~AnalysisManager() { FlushDiagnostics(); } + ~AnalysisManager(); void ClearContexts() { AnaCtxMgr.clear(); @@ -140,15 +136,12 @@ public: return LangOpts; } - virtual PathDiagnosticConsumer *getPathDiagnosticConsumer() { - return PD.get(); - } - - void FlushDiagnostics() { - if (PD.get()) - PD->FlushDiagnostics(0); + ArrayRef<PathDiagnosticConsumer*> getPathDiagnosticConsumers() { + return PathConsumers; } + void FlushDiagnostics(); + unsigned getMaxNodes() const { return MaxNodes; } unsigned getMaxVisit() const { return MaxVisit; } diff --git a/include/clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h b/include/clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h index 47edfe9fca91..f6c5830c2955 100644 --- a/include/clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h +++ b/include/clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h @@ -328,7 +328,7 @@ public: // For debugging purposes only void dump(raw_ostream &Out) const; - LLVM_ATTRIBUTE_USED void dump() const { dump(llvm::errs()); } + LLVM_ATTRIBUTE_USED void dump() const; static bool classof(const CallEvent *) { return true; } }; @@ -804,8 +804,12 @@ public: return getOriginExpr()->getReceiverInterface(); } + /// Returns how the message was written in the source (property access, + /// subscript, or explicit message send). ObjCMessageKind getMessageKind() const; + /// Returns true if this property access or subscript is a setter (has the + /// form of an assignment). bool isSetter() const { switch (getMessageKind()) { case OCM_Message: diff --git a/include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h b/include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h index 01218effff90..8044ed839a75 100644 --- a/include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h +++ b/include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h @@ -52,7 +52,9 @@ class RegionOffset { int64_t Offset; public: - enum { Symbolic = INT64_MAX }; + // We're using a const instead of an enumeration due to the size required; + // Visual Studio will only create enumerations of size int, not long long. + static const int64_t Symbolic = INT64_MAX; RegionOffset() : R(0) {} RegionOffset(const MemRegion *r, int64_t off) : R(r), Offset(off) {} diff --git a/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h b/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h index d36aa1bd1bcb..b0c51dd5b928 100644 --- a/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h +++ b/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h @@ -65,10 +65,14 @@ class DynamicTypeInfo { public: DynamicTypeInfo() : T(QualType()) {} - DynamicTypeInfo(QualType WithType, bool CanBeSub = true): - T(WithType), CanBeASubClass(CanBeSub) {} - QualType getType() { return T; } - bool canBeASubClass() { return CanBeASubClass; } + DynamicTypeInfo(QualType WithType, bool CanBeSub = true) + : T(WithType), CanBeASubClass(CanBeSub) {} + + bool isValid() const { return !T.isNull(); } + + QualType getType() const { return T; } + bool canBeASubClass() const { return CanBeASubClass; } + void Profile(llvm::FoldingSetNodeID &ID) const { T.Profile(ID); ID.AddInteger((unsigned)CanBeASubClass); |