aboutsummaryrefslogtreecommitdiff
path: root/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
diff options
context:
space:
mode:
authorTed Kremenek <kremenek@apple.com>2012-09-07 22:24:24 +0000
committerTed Kremenek <kremenek@apple.com>2012-09-07 22:24:24 +0000
commitb4b4523cc52bebc5ed47cc501959ab31286a1065 (patch)
treed0e57c2103cb6cd3cc0121125559e56791236835 /lib/StaticAnalyzer/Core/PathDiagnostic.cpp
parent526b4a63cd567393fd43af837ac9d0f35fc267f7 (diff)
Attempt to make the PathDiagnostic emission order more deterministic by
looking at PathPieces. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@163427 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/StaticAnalyzer/Core/PathDiagnostic.cpp')
-rw-r--r--lib/StaticAnalyzer/Core/PathDiagnostic.cpp41
1 files changed, 38 insertions, 3 deletions
diff --git a/lib/StaticAnalyzer/Core/PathDiagnostic.cpp b/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
index d010a668d9..15a6635062 100644
--- a/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
+++ b/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
@@ -208,6 +208,41 @@ void PathDiagnosticConsumer::HandlePathDiagnostic(PathDiagnostic *D) {
namespace {
+
+static llvm::Optional<bool> comparePiece(PathDiagnosticPiece &X,
+ PathDiagnosticPiece &Y) {
+ PathDiagnosticPiece::Kind XK = X.getKind(), YK = Y.getKind();
+ if (XK != YK) {
+ return XK < YK;
+ }
+ FullSourceLoc XL = X.getLocation().asLocation();
+ FullSourceLoc YL = Y.getLocation().asLocation();
+ if (XL < YL)
+ return true;
+ if (YL < XL)
+ return false;
+ const std::string &XS = X.getString();
+ const std::string &YS = Y.getString();
+ if (XS != YS)
+ return XS < YS;
+ return llvm::Optional<bool>();
+}
+
+static bool comparePathPieces(const PathPieces &X, const PathPieces &Y) {
+ if (X.size() < Y.size())
+ return true;
+ if (X.size() > Y.size())
+ return false;
+ // Compare individual parts of the path.
+ assert(X.size() == Y.size());
+ for (unsigned i = 0, n = X.size(); i < n; ++i) {
+ llvm::Optional<bool> B = comparePiece(*X[i], *Y[i]);
+ if (B.hasValue())
+ return B.getValue();
+ }
+ return false;
+}
+
struct CompareDiagnostics {
// Compare if 'X' is "<" than 'Y'.
bool operator()(const PathDiagnostic *X, const PathDiagnostic *Y) const {
@@ -216,7 +251,7 @@ struct CompareDiagnostics {
const FullSourceLoc &YLoc = Y->getLocation().asLocation();
if (XLoc < YLoc)
return true;
- if (XLoc != YLoc)
+ if (YLoc < XLoc)
return false;
// Next, compare by bug type.
@@ -235,8 +270,8 @@ struct CompareDiagnostics {
if (XDesc != YDesc)
return false;
- // FIXME: Further refine by comparing PathDiagnosticPieces?
- return false;
+ // Fall back to comparing path pieces.
+ return comparePathPieces(X->path, Y->path);
}
};
}