Skip to content

Commit 2f3eee7

Browse files
committed
Fix false positive and negative
1 parent beb67d4 commit 2f3eee7

File tree

4 files changed

+28
-32
lines changed

4 files changed

+28
-32
lines changed

clang-tools-extra/clang-tidy/readability/RedundantTypenameCheck.cpp

Lines changed: 22 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,9 @@ using namespace clang::ast_matchers::internal;
2020
namespace clang::tidy::readability {
2121

2222
void RedundantTypenameCheck::registerMatchers(MatchFinder *Finder) {
23-
Finder->addMatcher(typedefTypeLoc().bind("typedefTypeLoc"), this);
23+
Finder->addMatcher(typeLoc(unless(hasAncestor(decl(isInstantiated()))))
24+
.bind("nonDependentTypeLoc"),
25+
this);
2426

2527
if (!getLangOpts().CPlusPlus20)
2628
return;
@@ -38,25 +40,32 @@ void RedundantTypenameCheck::registerMatchers(MatchFinder *Finder) {
3840
// Match return types.
3941
functionDecl(unless(cxxConversionDecl()))))),
4042
hasParent(expr(anyOf(cxxNamedCastExpr(), cxxNewExpr()))));
41-
Finder->addMatcher(typeLoc(InImplicitTypenameContext).bind("typeloc"), this);
43+
Finder->addMatcher(
44+
typeLoc(InImplicitTypenameContext).bind("dependentTypeLoc"), this);
4245
}
4346

4447
void RedundantTypenameCheck::check(const MatchFinder::MatchResult &Result) {
4548
const SourceLocation ElaboratedKeywordLoc = [&] {
46-
if (const auto *TTL =
47-
Result.Nodes.getNodeAs<TypedefTypeLoc>("typedefTypeLoc"))
48-
return TTL->getElaboratedKeywordLoc();
49+
if (const auto *NonDependentTypeLoc =
50+
Result.Nodes.getNodeAs<TypeLoc>("nonDependentTypeLoc")) {
51+
if (const auto TTL = NonDependentTypeLoc->getAs<TypedefTypeLoc>())
52+
return TTL.getElaboratedKeywordLoc();
4953

50-
TypeLoc InnermostTypeLoc = *Result.Nodes.getNodeAs<TypeLoc>("typeloc");
51-
while (const TypeLoc Next = InnermostTypeLoc.getNextTypeLoc())
52-
InnermostTypeLoc = Next;
54+
if (const auto TTL = NonDependentTypeLoc->getAs<TagTypeLoc>())
55+
return TTL.getElaboratedKeywordLoc();
56+
} else {
57+
TypeLoc InnermostTypeLoc =
58+
*Result.Nodes.getNodeAs<TypeLoc>("dependentTypeLoc");
59+
while (const TypeLoc Next = InnermostTypeLoc.getNextTypeLoc())
60+
InnermostTypeLoc = Next;
5361

54-
if (const auto DNTL = InnermostTypeLoc.getAs<DependentNameTypeLoc>())
55-
return DNTL.getElaboratedKeywordLoc();
62+
if (const auto DNTL = InnermostTypeLoc.getAs<DependentNameTypeLoc>())
63+
return DNTL.getElaboratedKeywordLoc();
5664

57-
if (const auto TSTL =
58-
InnermostTypeLoc.getAs<TemplateSpecializationTypeLoc>())
59-
return TSTL.getElaboratedKeywordLoc();
65+
if (const auto TSTL =
66+
InnermostTypeLoc.getAs<TemplateSpecializationTypeLoc>())
67+
return TSTL.getElaboratedKeywordLoc();
68+
}
6069

6170
return SourceLocation();
6271
}();

clang-tools-extra/test/clang-tidy/checkers/readability/redundant-typename.cpp

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,12 @@
55

66
struct NotDependent {
77
using R = int;
8+
struct S {};
89
};
910

10-
auto f(typename NotDependent::R)
11+
auto f(typename NotDependent::S)
1112
// CHECK-MESSAGES: :[[@LINE-1]]:8: warning: redundant 'typename' [readability-redundant-typename]
12-
// CHECK-FIXES: auto f(NotDependent::R)
13+
// CHECK-FIXES: auto f(NotDependent::S)
1314
-> typename NotDependent::R
1415
// CHECK-MESSAGES: :[[@LINE-1]]:6: warning: redundant 'typename' [readability-redundant-typename]
1516
// CHECK-FIXES: -> NotDependent::R
@@ -142,7 +143,9 @@ typename T::R f();
142143
// CHECK-FIXES-20: T::R f();
143144

144145
template <typename T>
145-
void n(typename T::R);
146+
void n(typename T::R *) {}
147+
148+
template void n<NotDependent>(int *);
146149

147150
namespace ns {
148151

clang/include/clang/ASTMatchers/ASTMatchers.h

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -7001,20 +7001,6 @@ extern const internal::VariadicDynCastAllOfMatcher<
70017001
TypeLoc, TemplateSpecializationTypeLoc>
70027002
templateSpecializationTypeLoc;
70037003

7004-
/// Matches `TypedefTypeLoc`s.
7005-
///
7006-
/// Given
7007-
/// \code
7008-
/// using t1 = int;
7009-
/// template <typename T> struct S { using t2 = int; };
7010-
/// t1 var1;
7011-
/// const S<char>::t2* var2;
7012-
/// \endcode
7013-
/// typedefTypeLoc()
7014-
/// matches `t1` (in the declaration of var1) and `S<char>::t2`.
7015-
extern const internal::VariadicDynCastAllOfMatcher<TypeLoc, TypedefTypeLoc>
7016-
typedefTypeLoc;
7017-
70187004
/// Matches template specialization `TypeLoc`s, class template specializations,
70197005
/// variable template specializations, and function template specializations
70207006
/// that have at least one `TemplateArgumentLoc` matching the given

clang/lib/ASTMatchers/ASTMatchersInternal.cpp

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -810,8 +810,6 @@ const internal::VariadicDynCastAllOfMatcher<TypeLoc, ReferenceTypeLoc>
810810
const internal::VariadicDynCastAllOfMatcher<TypeLoc,
811811
TemplateSpecializationTypeLoc>
812812
templateSpecializationTypeLoc;
813-
const internal::VariadicDynCastAllOfMatcher<TypeLoc, TypedefTypeLoc>
814-
typedefTypeLoc;
815813

816814
const internal::VariadicDynCastAllOfMatcher<Stmt, UnaryExprOrTypeTraitExpr>
817815
unaryExprOrTypeTraitExpr;

0 commit comments

Comments
 (0)