From 1a8d52d1aef01644b5597d410a3e450e293c12b3 Mon Sep 17 00:00:00 2001 From: Vitaly Buka Date: Tue, 4 Oct 2016 02:40:35 +0000 Subject: [PATCH] Revert "[analyzer] Improve CloneChecker diagnostics" as its depends on reverted r283092 This reverts commit r283094. llvm-svn: 283182 --- clang/include/clang/Analysis/CloneDetection.h | 10 +- clang/lib/Analysis/CloneDetection.cpp | 24 ++--- clang/lib/StaticAnalyzer/Checkers/CloneChecker.cpp | 106 ++++++++++----------- clang/test/Analysis/copypaste/blocks.cpp | 4 +- .../test/Analysis/copypaste/function-try-block.cpp | 4 +- clang/test/Analysis/copypaste/functions.cpp | 4 +- clang/test/Analysis/copypaste/macro-complexity.cpp | 8 +- clang/test/Analysis/copypaste/macros.cpp | 10 +- clang/test/Analysis/copypaste/objc-methods.m | 4 +- .../plist-diagnostics-notes-as-events.cpp | 97 ------------------- .../test/Analysis/copypaste/plist-diagnostics.cpp | 71 -------------- clang/test/Analysis/copypaste/sub-sequences.cpp | 4 +- .../test/Analysis/copypaste/suspicious-clones.cpp | 20 ++-- clang/test/Analysis/copypaste/text-diagnostics.cpp | 17 ---- 14 files changed, 92 insertions(+), 291 deletions(-) delete mode 100644 clang/test/Analysis/copypaste/plist-diagnostics-notes-as-events.cpp delete mode 100644 clang/test/Analysis/copypaste/plist-diagnostics.cpp delete mode 100644 clang/test/Analysis/copypaste/text-diagnostics.cpp diff --git a/clang/include/clang/Analysis/CloneDetection.h b/clang/include/clang/Analysis/CloneDetection.h index 51cad7a..693e4a0 100644 --- a/clang/include/clang/Analysis/CloneDetection.h +++ b/clang/include/clang/Analysis/CloneDetection.h @@ -128,10 +128,6 @@ public: /// This method should only be called on a non-empty StmtSequence object. SourceLocation getEndLoc() const; - /// Returns the source range of the whole sequence - from the beginning - /// of the first statement to the end of the last statement. - SourceRange getSourceRange() const; - bool operator==(const StmtSequence &Other) const { return std::tie(S, StartIndex, EndIndex) == std::tie(Other.S, Other.StartIndex, Other.EndIndex); @@ -254,14 +250,14 @@ public: /// The variable which referencing in this clone was against the pattern. const VarDecl *Variable; /// Where the variable was referenced. - const Stmt *Mention; + SourceRange VarRange; /// The variable that should have been referenced to follow the pattern. /// If Suggestion is a nullptr then it's not possible to fix the pattern /// by referencing a different variable in this clone. const VarDecl *Suggestion; - SuspiciousCloneInfo(const VarDecl *Variable, const Stmt *Mention, + SuspiciousCloneInfo(const VarDecl *Variable, SourceRange Range, const VarDecl *Suggestion) - : Variable(Variable), Mention(Mention), Suggestion(Suggestion) {} + : Variable(Variable), VarRange(Range), Suggestion(Suggestion) {} SuspiciousCloneInfo() {} }; /// The first clone in the pair which always has a suggested variable. diff --git a/clang/lib/Analysis/CloneDetection.cpp b/clang/lib/Analysis/CloneDetection.cpp index 4fdac5a..1b43cfb 100644 --- a/clang/lib/Analysis/CloneDetection.cpp +++ b/clang/lib/Analysis/CloneDetection.cpp @@ -82,10 +82,6 @@ SourceLocation StmtSequence::getStartLoc() const { SourceLocation StmtSequence::getEndLoc() const { return back()->getLocEnd(); } -SourceRange StmtSequence::getSourceRange() const { - return SourceRange(getStartLoc(), getEndLoc()); -} - namespace { /// \brief Analyzes the pattern of the referenced variables in a statement. @@ -95,11 +91,11 @@ class VariablePattern { struct VariableOccurence { /// The index of the associated VarDecl in the Variables vector. size_t KindID; - /// The statement in the code where the variable was referenced. - const Stmt *Mention; + /// The source range in the code where the variable was referenced. + SourceRange Range; - VariableOccurence(size_t KindID, const Stmt *Mention) - : KindID(KindID), Mention(Mention) {} + VariableOccurence(size_t KindID, SourceRange Range) + : KindID(KindID), Range(Range) {} }; /// All occurences of referenced variables in the order of appearance. @@ -111,19 +107,19 @@ class VariablePattern { /// \brief Adds a new variable referenced to this pattern. /// \param VarDecl The declaration of the variable that is referenced. /// \param Mention The statement in the code where the variable was referenced. - void addVariableOccurence(const VarDecl *VarDecl, const Stmt *Mention) { + void addVariableOccurence(const VarDecl *VarDecl, SourceRange Range) { // First check if we already reference this variable for (size_t KindIndex = 0; KindIndex < Variables.size(); ++KindIndex) { if (Variables[KindIndex] == VarDecl) { // If yes, add a new occurence that points to the existing entry in // the Variables vector. - Occurences.emplace_back(KindIndex, Mention); + Occurences.emplace_back(KindIndex, Range); return; } } // If this variable wasn't already referenced, add it to the list of // referenced variables and add a occurence that points to this new entry. - Occurences.emplace_back(Variables.size(), Mention); + Occurences.emplace_back(Variables.size(), Range); Variables.push_back(VarDecl); } @@ -138,7 +134,7 @@ class VariablePattern { // Check if S is a reference to a variable. If yes, add it to the pattern. if (auto D = dyn_cast(S)) { if (auto VD = dyn_cast(D->getDecl()->getCanonicalDecl())) - addVariableOccurence(VD, D); + addVariableOccurence(VD, D->getSourceRange()); } // Recursively check all children of the given statement. @@ -212,7 +208,7 @@ public: // Store information about the first clone. FirstMismatch->FirstCloneInfo = CloneDetector::SuspiciousClonePair::SuspiciousCloneInfo( - Variables[ThisOccurence.KindID], ThisOccurence.Mention, + Variables[ThisOccurence.KindID], ThisOccurence.Range, FirstSuggestion); // Same as above but with the other clone. We do this for both clones as @@ -225,7 +221,7 @@ public: // Store information about the second clone. FirstMismatch->SecondCloneInfo = CloneDetector::SuspiciousClonePair::SuspiciousCloneInfo( - Other.Variables[OtherOccurence.KindID], OtherOccurence.Mention, + Variables[ThisOccurence.KindID], OtherOccurence.Range, SecondSuggestion); // SuspiciousClonePair guarantees that the first clone always has a diff --git a/clang/lib/StaticAnalyzer/Checkers/CloneChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/CloneChecker.cpp index 6fa5732..b4ac223 100644 --- a/clang/lib/StaticAnalyzer/Checkers/CloneChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/CloneChecker.cpp @@ -16,10 +16,8 @@ #include "ClangSACheckers.h" #include "clang/Analysis/CloneDetection.h" #include "clang/Basic/Diagnostic.h" -#include "clang/StaticAnalyzer/Core/BugReporter/BugType.h" #include "clang/StaticAnalyzer/Core/Checker.h" #include "clang/StaticAnalyzer/Core/CheckerManager.h" -#include "clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h" #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h" using namespace clang; @@ -29,7 +27,6 @@ namespace { class CloneChecker : public Checker { mutable CloneDetector Detector; - mutable std::unique_ptr BT_Exact, BT_Suspicious; public: void checkASTCodeBody(const Decl *D, AnalysisManager &Mgr, @@ -39,12 +36,12 @@ public: AnalysisManager &Mgr, BugReporter &BR) const; /// \brief Reports all clones to the user. - void reportClones(BugReporter &BR, AnalysisManager &Mgr, + void reportClones(SourceManager &SM, AnalysisManager &Mgr, int MinComplexity) const; /// \brief Reports only suspicious clones to the user along with informaton /// that explain why they are suspicious. - void reportSuspiciousClones(BugReporter &BR, AnalysisManager &Mgr, + void reportSuspiciousClones(SourceManager &SM, AnalysisManager &Mgr, int MinComplexity) const; }; } // end anonymous namespace @@ -73,82 +70,79 @@ void CloneChecker::checkEndOfTranslationUnit(const TranslationUnitDecl *TU, "ReportNormalClones", true, this); if (ReportSuspiciousClones) - reportSuspiciousClones(BR, Mgr, MinComplexity); + reportSuspiciousClones(BR.getSourceManager(), Mgr, MinComplexity); if (ReportNormalClones) - reportClones(BR, Mgr, MinComplexity); + reportClones(BR.getSourceManager(), Mgr, MinComplexity); } -static PathDiagnosticLocation makeLocation(const StmtSequence &S, - AnalysisManager &Mgr) { - ASTContext &ACtx = Mgr.getASTContext(); - return PathDiagnosticLocation::createBegin( - S.front(), ACtx.getSourceManager(), - Mgr.getAnalysisDeclContext(ACtx.getTranslationUnitDecl())); -} - -void CloneChecker::reportClones(BugReporter &BR, AnalysisManager &Mgr, +void CloneChecker::reportClones(SourceManager &SM, AnalysisManager &Mgr, int MinComplexity) const { std::vector CloneGroups; Detector.findClones(CloneGroups, MinComplexity); - if (!BT_Exact) - BT_Exact.reset(new BugType(this, "Exact code clone", "Code clone")); + DiagnosticsEngine &DiagEngine = Mgr.getDiagnostic(); + + unsigned WarnID = DiagEngine.getCustomDiagID(DiagnosticsEngine::Warning, + "Detected code clone."); + + unsigned NoteID = DiagEngine.getCustomDiagID(DiagnosticsEngine::Note, + "Related code clone is here."); for (CloneDetector::CloneGroup &Group : CloneGroups) { // We group the clones by printing the first as a warning and all others // as a note. - auto R = llvm::make_unique( - *BT_Exact, "Duplicate code detected", - makeLocation(Group.Sequences.front(), Mgr)); - R->addRange(Group.Sequences.front().getSourceRange()); - - for (unsigned i = 1; i < Group.Sequences.size(); ++i) - R->addNote("Similar code here", - makeLocation(Group.Sequences[i], Mgr), - Group.Sequences[i].getSourceRange()); - BR.emitReport(std::move(R)); + DiagEngine.Report(Group.Sequences.front().getStartLoc(), WarnID); + for (unsigned i = 1; i < Group.Sequences.size(); ++i) { + DiagEngine.Report(Group.Sequences[i].getStartLoc(), NoteID); + } } } -void CloneChecker::reportSuspiciousClones(BugReporter &BR, +void CloneChecker::reportSuspiciousClones(SourceManager &SM, AnalysisManager &Mgr, int MinComplexity) const { std::vector Clones; Detector.findSuspiciousClones(Clones, MinComplexity); - if (!BT_Suspicious) - BT_Suspicious.reset( - new BugType(this, "Suspicious code clone", "Code clone")); + DiagnosticsEngine &DiagEngine = Mgr.getDiagnostic(); + + auto SuspiciousCloneWarning = DiagEngine.getCustomDiagID( + DiagnosticsEngine::Warning, "suspicious code clone detected; did you " + "mean to use %0?"); + + auto RelatedCloneNote = DiagEngine.getCustomDiagID( + DiagnosticsEngine::Note, "suggestion is based on the usage of this " + "variable in a similar piece of code"); - ASTContext &ACtx = BR.getContext(); - SourceManager &SM = ACtx.getSourceManager(); - AnalysisDeclContext *ADC = - Mgr.getAnalysisDeclContext(ACtx.getTranslationUnitDecl()); + auto RelatedSuspiciousCloneNote = DiagEngine.getCustomDiagID( + DiagnosticsEngine::Note, "suggestion is based on the usage of this " + "variable in a similar piece of code; did you " + "mean to use %0?"); for (CloneDetector::SuspiciousClonePair &Pair : Clones) { - // FIXME: We are ignoring the suggestions currently, because they are - // only 50% accurate (even if the second suggestion is unavailable), - // which may confuse the user. - // Think how to perform more accurate suggestions? - - auto R = llvm::make_unique( - *BT_Suspicious, - "Potential copy-paste error; did you really mean to use '" + - Pair.FirstCloneInfo.Variable->getNameAsString() + "' here?", - PathDiagnosticLocation::createBegin(Pair.FirstCloneInfo.Mention, SM, - ADC)); - R->addRange(Pair.FirstCloneInfo.Mention->getSourceRange()); - - R->addNote("Similar code using '" + - Pair.SecondCloneInfo.Variable->getNameAsString() + "' here", - PathDiagnosticLocation::createBegin(Pair.SecondCloneInfo.Mention, - SM, ADC), - Pair.SecondCloneInfo.Mention->getSourceRange()); - - BR.emitReport(std::move(R)); + // The first clone always has a suggestion and we report it to the user + // along with the place where the suggestion should be used. + DiagEngine.Report(Pair.FirstCloneInfo.VarRange.getBegin(), + SuspiciousCloneWarning) + << Pair.FirstCloneInfo.VarRange << Pair.FirstCloneInfo.Suggestion; + + // The second clone can have a suggestion and if there is one, we report + // that suggestion to the user. + if (Pair.SecondCloneInfo.Suggestion) { + DiagEngine.Report(Pair.SecondCloneInfo.VarRange.getBegin(), + RelatedSuspiciousCloneNote) + << Pair.SecondCloneInfo.VarRange << Pair.SecondCloneInfo.Suggestion; + continue; + } + + // If there isn't a suggestion in the second clone, we only inform the + // user where we got the idea that his code could contain an error. + DiagEngine.Report(Pair.SecondCloneInfo.VarRange.getBegin(), + RelatedCloneNote) + << Pair.SecondCloneInfo.VarRange; } } diff --git a/clang/test/Analysis/copypaste/blocks.cpp b/clang/test/Analysis/copypaste/blocks.cpp index 133b5cb..0bd9812 100644 --- a/clang/test/Analysis/copypaste/blocks.cpp +++ b/clang/test/Analysis/copypaste/blocks.cpp @@ -4,14 +4,14 @@ void log(); -auto BlockA = ^(int a, int b){ // expected-warning{{Duplicate code detected}} +auto BlockA = ^(int a, int b){ // expected-warning{{Detected code clone.}} log(); if (a > b) return a; return b; }; -auto BlockB = ^(int a, int b){ // expected-note{{Similar code here}} +auto BlockB = ^(int a, int b){ // expected-note{{Related code clone is here.}} log(); if (a > b) return a; diff --git a/clang/test/Analysis/copypaste/function-try-block.cpp b/clang/test/Analysis/copypaste/function-try-block.cpp index 7a69097..b13096d 100644 --- a/clang/test/Analysis/copypaste/function-try-block.cpp +++ b/clang/test/Analysis/copypaste/function-try-block.cpp @@ -3,7 +3,7 @@ // Tests if function try blocks are correctly handled. void nonCompoundStmt1(int& x) - try { x += 1; } catch(...) { x -= 1; } // expected-warning{{Duplicate code detected}} + try { x += 1; } catch(...) { x -= 1; } // expected-warning{{Detected code clone.}} void nonCompoundStmt2(int& x) - try { x += 1; } catch(...) { x -= 1; } // expected-note{{Similar code here}} + try { x += 1; } catch(...) { x -= 1; } // expected-note{{Related code clone is here.}} diff --git a/clang/test/Analysis/copypaste/functions.cpp b/clang/test/Analysis/copypaste/functions.cpp index c95443d..2a871f7 100644 --- a/clang/test/Analysis/copypaste/functions.cpp +++ b/clang/test/Analysis/copypaste/functions.cpp @@ -4,14 +4,14 @@ void log(); -int max(int a, int b) { // expected-warning{{Duplicate code detected}} +int max(int a, int b) { // expected-warning{{Detected code clone.}} log(); if (a > b) return a; return b; } -int maxClone(int x, int y) { // expected-note{{Similar code here}} +int maxClone(int x, int y) { // expected-note{{Related code clone is here.}} log(); if (x > y) return x; diff --git a/clang/test/Analysis/copypaste/macro-complexity.cpp b/clang/test/Analysis/copypaste/macro-complexity.cpp index aca4df1..58b884a 100644 --- a/clang/test/Analysis/copypaste/macro-complexity.cpp +++ b/clang/test/Analysis/copypaste/macro-complexity.cpp @@ -11,11 +11,11 @@ // This confirms that with the current configuration the macro body would be // considered large enough to pass the MinimumCloneComplexity constraint. -int manualMacro(int a, int b) { // expected-warning{{Duplicate code detected}} +int manualMacro(int a, int b) { // expected-warning{{Detected code clone.}} return a > b ? -a * a : -b * b; } -int manualMacroClone(int a, int b) { // expected-note{{Similar code here}} +int manualMacroClone(int a, int b) { // expected-note{{Related code clone is here.}} return a > b ? -a * a : -b * b; } @@ -41,10 +41,10 @@ int macroClone(int a, int b) { #define NEG(A) -(A) -int nestedMacros() { // expected-warning{{Duplicate code detected}} +int nestedMacros() { // expected-warning{{Detected code clone.}} return NEG(NEG(NEG(NEG(NEG(NEG(NEG(NEG(NEG(NEG(1)))))))))); } -int nestedMacrosClone() { // expected-note{{Similar code here}} +int nestedMacrosClone() { // expected-note{{Related code clone is here.}} return NEG(NEG(NEG(NEG(NEG(NEG(NEG(NEG(NEG(NEG(1)))))))))); } diff --git a/clang/test/Analysis/copypaste/macros.cpp b/clang/test/Analysis/copypaste/macros.cpp index db9b4c6..170e034 100644 --- a/clang/test/Analysis/copypaste/macros.cpp +++ b/clang/test/Analysis/copypaste/macros.cpp @@ -5,7 +5,7 @@ // to have the same complexity value. Macros have smaller complexity values // and need to be in their own hash group. -int foo(int a) { // expected-warning{{Duplicate code detected}} +int foo(int a) { // expected-warning{{Detected code clone.}} a = a + 1; a = a + 1 / 1; a = a + 1 + 1 + 1; @@ -15,7 +15,7 @@ int foo(int a) { // expected-warning{{Duplicate code detected}} return a; } -int fooClone(int a) { // expected-note{{Similar code here}} +int fooClone(int a) { // expected-note{{Related code clone is here.}} a = a + 1; a = a + 1 / 1; a = a + 1 + 1 + 1; @@ -30,7 +30,7 @@ int fooClone(int a) { // expected-note{{Similar code here}} #define ASSIGN(T, V) T = T + V -int macro(int a) { // expected-warning{{Duplicate code detected}} +int macro(int a) { // expected-warning{{Detected code clone.}} ASSIGN(a, 1); ASSIGN(a, 1 / 1); ASSIGN(a, 1 + 1 + 1); @@ -40,7 +40,7 @@ int macro(int a) { // expected-warning{{Duplicate code detected}} return a; } -int macroClone(int a) { // expected-note{{Similar code here}} +int macroClone(int a) { // expected-note{{Related code clone is here.}} ASSIGN(a, 1); ASSIGN(a, 1 / 1); ASSIGN(a, 1 + 1 + 1); @@ -54,7 +54,7 @@ int macroClone(int a) { // expected-note{{Similar code here}} #define EMPTY -int fooFalsePositiveClone(int a) { // expected-note{{Similar code here}} +int fooFalsePositiveClone(int a) { // expected-note{{Related code clone is here.}} a = EMPTY a + 1; a = a + 1 / 1; a = a + 1 + 1 + 1; diff --git a/clang/test/Analysis/copypaste/objc-methods.m b/clang/test/Analysis/copypaste/objc-methods.m index 9b8002c..0636447e 100644 --- a/clang/test/Analysis/copypaste/objc-methods.m +++ b/clang/test/Analysis/copypaste/objc-methods.m @@ -7,7 +7,7 @@ @end @implementation A -- (int) setOk : (int) a : (int) b { // expected-warning{{Duplicate code detected}} +- (int) setOk : (int) a : (int) b { // expected-warning{{Detected code clone.}} if (a > b) return a; return b; @@ -19,7 +19,7 @@ @end @implementation B -- (int) setOk : (int) a : (int) b { // expected-note{{Similar code here}} +- (int) setOk : (int) a : (int) b { // expected-note{{Related code clone is here.}} if (a > b) return a; return b; diff --git a/clang/test/Analysis/copypaste/plist-diagnostics-notes-as-events.cpp b/clang/test/Analysis/copypaste/plist-diagnostics-notes-as-events.cpp deleted file mode 100644 index 1180d44..0000000 --- a/clang/test/Analysis/copypaste/plist-diagnostics-notes-as-events.cpp +++ /dev/null @@ -1,97 +0,0 @@ -// RUN: %clang_cc1 -analyze -analyzer-output=plist -analyzer-config notes-as-events=true -o %t.plist -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s -// RUN: FileCheck --input-file=%t.plist %s - -void log(); - -int max(int a, int b) { // expected-warning{{Duplicate code detected}} - log(); - if (a > b) - return a; - return b; -} - -int maxClone(int a, int b) { // no-note (converted into event) - log(); - if (a > b) - return a; - return b; -} - -// CHECK: diagnostics -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: path -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: kindevent -// CHECK-NEXT: location -// CHECK-NEXT: -// CHECK-NEXT: line13 -// CHECK-NEXT: col28 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: ranges -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: line13 -// CHECK-NEXT: col28 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: line18 -// CHECK-NEXT: col1 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: depth0 -// CHECK-NEXT: extended_message -// CHECK-NEXT: Similar code here -// CHECK-NEXT: message -// CHECK-NEXT: Similar code here -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: kindevent -// CHECK-NEXT: location -// CHECK-NEXT: -// CHECK-NEXT: line6 -// CHECK-NEXT: col23 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: ranges -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: line6 -// CHECK-NEXT: col23 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: line11 -// CHECK-NEXT: col1 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: depth0 -// CHECK-NEXT: extended_message -// CHECK-NEXT: Duplicate code detected -// CHECK-NEXT: message -// CHECK-NEXT: Duplicate code detected -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: descriptionDuplicate code detected -// CHECK-NEXT: categoryCode clone -// CHECK-NEXT: typeExact code clone -// CHECK-NEXT: check_namealpha.clone.CloneChecker -// CHECK-NEXT: -// CHECK-NEXT: issue_hash_content_of_line_in_context3d15184f38c5fa57e479b744fe3f5035 -// CHECK-NEXT: location -// CHECK-NEXT: -// CHECK-NEXT: line6 -// CHECK-NEXT: col23 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: diff --git a/clang/test/Analysis/copypaste/plist-diagnostics.cpp b/clang/test/Analysis/copypaste/plist-diagnostics.cpp deleted file mode 100644 index 109d8e4..0000000 --- a/clang/test/Analysis/copypaste/plist-diagnostics.cpp +++ /dev/null @@ -1,71 +0,0 @@ -// RUN: %clang_cc1 -analyze -analyzer-output=plist -o %t.plist -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s -// RUN: FileCheck --input-file=%t.plist %s - -void log(); - -int max(int a, int b) { // expected-warning{{Duplicate code detected}} - log(); - if (a > b) - return a; - return b; -} - -int maxClone(int a, int b) { // expected-note{{Similar code here}} - log(); - if (a > b) - return a; - return b; -} - -// FIXME: This plist output doesn't include the extra note on line 13. -// It should be updated once the format for extra notes in plists is defined. - -// CHECK: diagnostics -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: path -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: kindevent -// CHECK-NEXT: location -// CHECK-NEXT: -// CHECK-NEXT: line6 -// CHECK-NEXT: col23 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: ranges -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: line6 -// CHECK-NEXT: col23 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: line11 -// CHECK-NEXT: col1 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: depth0 -// CHECK-NEXT: extended_message -// CHECK-NEXT: Duplicate code detected -// CHECK-NEXT: message -// CHECK-NEXT: Duplicate code detected -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: descriptionDuplicate code detected -// CHECK-NEXT: categoryCode clone -// CHECK-NEXT: typeExact code clone -// CHECK-NEXT: check_namealpha.clone.CloneChecker -// CHECK-NEXT: -// CHECK-NEXT: issue_hash_content_of_line_in_context3d15184f38c5fa57e479b744fe3f5035 -// CHECK-NEXT: location -// CHECK-NEXT: -// CHECK-NEXT: line6 -// CHECK-NEXT: col23 -// CHECK-NEXT: file0 -// CHECK-NEXT: -// CHECK-NEXT: -// CHECK-NEXT: diff --git a/clang/test/Analysis/copypaste/sub-sequences.cpp b/clang/test/Analysis/copypaste/sub-sequences.cpp index ff73632..59dc464 100644 --- a/clang/test/Analysis/copypaste/sub-sequences.cpp +++ b/clang/test/Analysis/copypaste/sub-sequences.cpp @@ -7,14 +7,14 @@ void log(); int max(int a, int b) { log2(a); - log(); // expected-warning{{Duplicate code detected}} + log(); // expected-warning{{Detected code clone.}} if (a > b) return a; return b; } int maxClone(int a, int b) { - log(); // expected-note{{Similar code here}} + log(); // expected-note{{Related code clone is here.}} if (a > b) return a; return b; diff --git a/clang/test/Analysis/copypaste/suspicious-clones.cpp b/clang/test/Analysis/copypaste/suspicious-clones.cpp index c64a1dc..fb22d38c8 100644 --- a/clang/test/Analysis/copypaste/suspicious-clones.cpp +++ b/clang/test/Analysis/copypaste/suspicious-clones.cpp @@ -8,14 +8,14 @@ int max(int a, int b) { log(); if (a > b) return a; - return b; // expected-note{{Similar code using 'b' here}} + return b; // expected-note{{suggestion is based on the usage of this variable in a similar piece of code}} } int maxClone(int x, int y, int z) { log(); if (x > y) return x; - return z; // expected-warning{{Potential copy-paste error; did you really mean to use 'z' here?}} + return z; // expected-warning{{suspicious code clone detected; did you mean to use 'y'?}} } // Tests finding a suspicious clone that references global variables. @@ -33,7 +33,7 @@ void busyIncrement() { while (true) { if (m1.try_lock()) { ++i; - m1.unlock(); // expected-note{{Similar code using 'm1' here}} + m1.unlock(); // expected-note{{suggestion is based on the usage of this variable in a similar piece of code}} if (i > 1000) { return; } @@ -45,7 +45,7 @@ void faultyBusyIncrement() { while (true) { if (m1.try_lock()) { ++i; - m2.unlock(); // expected-warning{{Potential copy-paste error; did you really mean to use 'm2' here?}} + m2.unlock(); // expected-warning{{suspicious code clone detected; did you mean to use 'm1'?}} if (i > 1000) { return; } @@ -58,14 +58,14 @@ void faultyBusyIncrement() { int foo(int a, int b, int c) { a += b + c; b /= a + b; - c -= b * a; // expected-warning{{Potential copy-paste error; did you really mean to use 'b' here?}} + c -= b * a; // expected-warning{{suspicious code clone detected; did you mean to use 'a'?}} return c; } int fooClone(int a, int b, int c) { a += b + c; b /= a + b; - c -= a * a; // expected-note{{Similar code using 'a' here}} + c -= a * a; // expected-note{{suggestion is based on the usage of this variable in a similar piece of code; did you mean to use 'b'?}} return c; } @@ -77,21 +77,21 @@ int fooClone(int a, int b, int c) { long bar1(long a, long b, long c, long d) { c = a - b; c = c / d * a; - d = b * b - c; // expected-warning{{Potential copy-paste error; did you really mean to use 'b' here?}} + d = b * b - c; // expected-warning{{suspicious code clone detected; did you mean to use 'c'?}} return d; } long bar2(long a, long b, long c, long d) { c = a - b; c = c / d * a; - d = c * b - c; // expected-note{{Similar code using 'c' here}} \ - // expected-warning{{Potential copy-paste error; did you really mean to use 'c' here?}} + d = c * b - c; // expected-note{{suggestion is based on the usage of this variable in a similar piece of code; did you mean to use 'b'?}} \ + // expected-warning{{suspicious code clone detected; did you mean to use 'a'?}} return d; } long bar3(long a, long b, long c, long d) { c = a - b; c = c / d * a; - d = a * b - c; // expected-note{{Similar code using 'a' here}} + d = a * b - c; // expected-note{{suggestion is based on the usage of this variable in a similar piece of code; did you mean to use 'c'?}} return d; } diff --git a/clang/test/Analysis/copypaste/text-diagnostics.cpp b/clang/test/Analysis/copypaste/text-diagnostics.cpp deleted file mode 100644 index a80afdb..0000000 --- a/clang/test/Analysis/copypaste/text-diagnostics.cpp +++ /dev/null @@ -1,17 +0,0 @@ -// RUN: %clang_cc1 -analyze -analyzer-output=text -std=c++11 -analyzer-checker=alpha.clone.CloneChecker -verify %s - -void log(); - -int max(int a, int b) { // expected-warning{{Duplicate code detected}} // expected-note{{Duplicate code detected}} - log(); - if (a > b) - return a; - return b; -} - -int maxClone(int a, int b) { // expected-note{{Similar code here}} - log(); - if (a > b) - return a; - return b; -} -- 2.7.4