[clang-tidy] readability-redundant-declaration: ignore friends and macros

llvm-svn: 309379
This commit is contained in:
Alexander Kornienko 2017-07-28 12:46:02 +00:00
parent 4dafd14d1a
commit f3321c5f68
4 changed files with 68 additions and 6 deletions

View File

@ -18,11 +18,16 @@ namespace clang {
namespace tidy {
namespace readability {
RedundantDeclarationCheck::RedundantDeclarationCheck(StringRef Name,
ClangTidyContext *Context)
: ClangTidyCheck(Name, Context),
IgnoreMacros(Options.getLocalOrGlobal("IgnoreMacros", true)) {}
void RedundantDeclarationCheck::registerMatchers(MatchFinder *Finder) {
Finder->addMatcher(
namedDecl(
anyOf(varDecl(unless(isDefinition())),
functionDecl(unless(anyOf(isDefinition(), isDefaulted())))))
namedDecl(anyOf(varDecl(unless(isDefinition())),
functionDecl(unless(anyOf(isDefinition(), isDefaulted(),
hasParent(friendDecl()))))))
.bind("Decl"),
this);
}
@ -36,6 +41,13 @@ void RedundantDeclarationCheck::check(const MatchFinder::MatchResult &Result) {
return;
if (Prev->getLocation() == D->getLocation())
return;
if (IgnoreMacros &&
(D->getLocation().isMacroID() || Prev->getLocation().isMacroID()))
return;
// Don't complain when the previous declaration is a friend declaration.
for (const auto &Parent : Result.Context->getParents(*Prev))
if (Parent.get<FriendDecl>())
return;
const SourceManager &SM = *Result.SourceManager;

View File

@ -22,10 +22,12 @@ namespace readability {
/// http://clang.llvm.org/extra/clang-tidy/checks/readability-redundant-declaration.html
class RedundantDeclarationCheck : public ClangTidyCheck {
public:
RedundantDeclarationCheck(StringRef Name, ClangTidyContext *Context)
: ClangTidyCheck(Name, Context) {}
RedundantDeclarationCheck(StringRef Name, ClangTidyContext *Context);
void registerMatchers(ast_matchers::MatchFinder *Finder) override;
void check(const ast_matchers::MatchFinder::MatchResult &Result) override;
private:
const bool IgnoreMacros;
};
} // namespace readability

View File

@ -0,0 +1,22 @@
// RUN: %check_clang_tidy %s readability-redundant-declaration %t -- \
// RUN: -config="{CheckOptions: \
// RUN: [{key: readability-redundant-declaration.IgnoreMacros, \
// RUN: value: 1}]}" \
// RUN: -- -std=c++11
extern int Xyz;
extern int Xyz; // Xyz
// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: redundant 'Xyz' declaration [readability-redundant-declaration]
// CHECK-FIXES: {{^}}// Xyz{{$}}
namespace macros {
#define DECLARE(x) extern int x
#define DEFINE(x) extern int x; int x = 42
DECLARE(test);
DEFINE(test);
// CHECK-FIXES: {{^}}#define DECLARE(x) extern int x{{$}}
// CHECK-FIXES: {{^}}#define DEFINE(x) extern int x; int x = 42{{$}}
// CHECK-FIXES: {{^}}DECLARE(test);{{$}}
// CHECK-FIXES: {{^}}DEFINE(test);{{$}}
} // namespace macros

View File

@ -1,4 +1,8 @@
// RUN: %check_clang_tidy %s readability-redundant-declaration %t
// RUN: %check_clang_tidy %s readability-redundant-declaration %t -- \
// RUN: -config="{CheckOptions: \
// RUN: [{key: readability-redundant-declaration.IgnoreMacros, \
// RUN: value: 0}]}" \
// RUN: -- -std=c++11
extern int Xyz;
extern int Xyz; // Xyz
@ -42,3 +46,25 @@ struct C2 {
template <class T>
C2<T>::C2() = default;
void best_friend();
struct Friendly {
friend void best_friend();
friend void enemy();
};
void enemy();
namespace macros {
#define DECLARE(x) extern int x
#define DEFINE(x) extern int x; int x = 42
DECLARE(test);
DEFINE(test);
// CHECK-MESSAGES: :[[@LINE-1]]:8: warning: redundant 'test' declaration
// CHECK-FIXES: {{^}}#define DECLARE(x) extern int x{{$}}
// CHECK-FIXES: {{^}}#define DEFINE(x) extern int x; int x = 42{{$}}
// CHECK-FIXES: {{^}}DECLARE(test);{{$}}
// CHECK-FIXES: {{^}}DEFINE(test);{{$}}
} // namespace macros