diff options
Diffstat (limited to 'lib/StaticAnalyzer')
-rw-r--r-- | lib/StaticAnalyzer/Core/BugReporter.cpp | 33 | ||||
-rw-r--r-- | lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp | 23 |
2 files changed, 36 insertions, 20 deletions
diff --git a/lib/StaticAnalyzer/Core/BugReporter.cpp b/lib/StaticAnalyzer/Core/BugReporter.cpp index 833c29165d..66eb52604d 100644 --- a/lib/StaticAnalyzer/Core/BugReporter.cpp +++ b/lib/StaticAnalyzer/Core/BugReporter.cpp @@ -564,7 +564,7 @@ public: // "Minimal" path diagnostic generation algorithm. //===----------------------------------------------------------------------===// -static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM); +static void CompactPathDiagnostic(PathPieces &path, const SourceManager& SM); static void GenerateMinimalPathDiagnostic(PathDiagnostic& PD, PathDiagnosticBuilder &PDB, @@ -877,7 +877,7 @@ static void GenerateMinimalPathDiagnostic(PathDiagnostic& PD, // After constructing the full PathDiagnostic, do a pass over it to compact // PathDiagnosticPieces that occur within a macro. - CompactPathDiagnostic(PD, PDB.getSourceManager()); + CompactPathDiagnostic(PD.getMutablePieces(), PDB.getSourceManager()); } //===----------------------------------------------------------------------===// @@ -1652,7 +1652,7 @@ MakeReportGraph(const ExplodedGraph* G, /// CompactPathDiagnostic - This function postprocesses a PathDiagnostic object /// and collapses PathDiagosticPieces that are expanded by macros. -static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM) { +static void CompactPathDiagnostic(PathPieces &path, const SourceManager& SM) { typedef std::vector<std::pair<IntrusiveRefCntPtr<PathDiagnosticMacroPiece>, SourceLocation> > MacroStackTy; @@ -1662,10 +1662,18 @@ static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM) { MacroStackTy MacroStack; PiecesTy Pieces; - for (PathPieces::const_iterator I = PD.path.begin(), E = PD.path.end(); + for (PathPieces::const_iterator I = path.begin(), E = path.end(); I!=E; ++I) { + + PathDiagnosticPiece *piece = I->getPtr(); + + // Recursively compact calls. + if (PathDiagnosticCallPiece *call=dyn_cast<PathDiagnosticCallPiece>(piece)){ + CompactPathDiagnostic(call->path, SM); + } + // Get the location of the PathDiagnosticPiece. - const FullSourceLoc Loc = (*I)->getLocation().asLocation(); + const FullSourceLoc Loc = piece->getLocation().asLocation(); // Determine the instantiation location, which is the location we group // related PathDiagnosticPieces. @@ -1675,7 +1683,7 @@ static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM) { if (Loc.isFileID()) { MacroStack.clear(); - Pieces.push_back(*I); + Pieces.push_back(piece); continue; } @@ -1683,7 +1691,7 @@ static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM) { // Is the PathDiagnosticPiece within the same macro group? if (!MacroStack.empty() && InstantiationLoc == MacroStack.back().second) { - MacroStack.back().first->subPieces.push_back(*I); + MacroStack.back().first->subPieces.push_back(piece); continue; } @@ -1714,7 +1722,7 @@ static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM) { // Create a new macro group and add it to the stack. PathDiagnosticMacroPiece *NewGroup = new PathDiagnosticMacroPiece( - PathDiagnosticLocation::createSingleLocation((*I)->getLocation())); + PathDiagnosticLocation::createSingleLocation(piece->getLocation())); if (MacroGroup) MacroGroup->subPieces.push_back(NewGroup); @@ -1728,15 +1736,14 @@ static void CompactPathDiagnostic(PathDiagnostic &PD, const SourceManager& SM) { } // Finally, add the PathDiagnosticPiece to the group. - MacroGroup->subPieces.push_back(*I); + MacroGroup->subPieces.push_back(piece); } // Now take the pieces and construct a new PathDiagnostic. - PD.getMutablePieces().clear(); + path.clear(); - for (PiecesTy::iterator I=Pieces.begin(), E=Pieces.end(); I!=E; ++I) { - PD.getMutablePieces().push_back(*I); - } + for (PiecesTy::iterator I=Pieces.begin(), E=Pieces.end(); I!=E; ++I) + path.push_back(*I); } void GRBugReporter::GeneratePathDiagnostic(PathDiagnostic& PD, diff --git a/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp b/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp index 3740ba1005..09c2f794d6 100644 --- a/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp +++ b/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp @@ -95,7 +95,8 @@ void HTMLDiagnostics::FlushDiagnosticsImpl( } } -static void flattenPath(PathPieces &path, const PathPieces &oldPath) { +static void flattenPath(PathPieces &primaryPath, PathPieces ¤tPath, + const PathPieces &oldPath) { for (PathPieces::const_iterator it = oldPath.begin(), et = oldPath.end(); it != et; ++it ) { PathDiagnosticPiece *piece = it->getPtr(); @@ -104,16 +105,24 @@ static void flattenPath(PathPieces &path, const PathPieces &oldPath) { IntrusiveRefCntPtr<PathDiagnosticEventPiece> callEnter = call->getCallEnterEvent(); if (callEnter) - path.push_back(callEnter); - flattenPath(path, call->path); + currentPath.push_back(callEnter); + flattenPath(primaryPath, primaryPath, call->path); IntrusiveRefCntPtr<PathDiagnosticEventPiece> callExit = call->getCallExitEvent(); if (callExit) - path.push_back(callExit); + currentPath.push_back(callExit); continue; } - - path.push_back(piece); + if (PathDiagnosticMacroPiece *macro = + dyn_cast<PathDiagnosticMacroPiece>(piece)) { + currentPath.push_back(piece); + PathPieces newPath; + flattenPath(primaryPath, newPath, macro->subPieces); + macro->subPieces = newPath; + continue; + } + + currentPath.push_back(piece); } } @@ -144,7 +153,7 @@ void HTMLDiagnostics::ReportDiag(const PathDiagnostic& D, // First flatten out the entire path to make it easier to use. PathPieces path; - flattenPath(path, D.path); + flattenPath(path, path, D.path); // The path as already been prechecked that all parts of the path are // from the same file and that it is non-empty. |