forked from OSchip/llvm-project
[clangd] Have template template arguments target their referenced template decl
Fixes https://github.com/clangd/clangd/issues/473 Differential Revision: https://reviews.llvm.org/D85503
This commit is contained in:
parent
582fd474dd
commit
70d583ad12
|
@ -596,6 +596,19 @@ public:
|
||||||
add(CCI->getAnyMember(), Flags);
|
add(CCI->getAnyMember(), Flags);
|
||||||
// Constructor calls contain a TypeLoc node, so we don't handle them here.
|
// Constructor calls contain a TypeLoc node, so we don't handle them here.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void add(const TemplateArgument &Arg, RelSet Flags) {
|
||||||
|
// Only used for template template arguments.
|
||||||
|
// For type and non-type template arguments, SelectionTree
|
||||||
|
// will hit a more specific node (e.g. a TypeLoc or a
|
||||||
|
// DeclRefExpr).
|
||||||
|
if (Arg.getKind() == TemplateArgument::Template ||
|
||||||
|
Arg.getKind() == TemplateArgument::TemplateExpansion) {
|
||||||
|
if (TemplateDecl *TD = Arg.getAsTemplate().getAsTemplateDecl()) {
|
||||||
|
report(TD, Flags);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -619,6 +632,8 @@ allTargetDecls(const ast_type_traits::DynTypedNode &N) {
|
||||||
Finder.add(*QT, Flags);
|
Finder.add(*QT, Flags);
|
||||||
else if (const CXXCtorInitializer *CCI = N.get<CXXCtorInitializer>())
|
else if (const CXXCtorInitializer *CCI = N.get<CXXCtorInitializer>())
|
||||||
Finder.add(CCI, Flags);
|
Finder.add(CCI, Flags);
|
||||||
|
else if (const TemplateArgumentLoc *TAL = N.get<TemplateArgumentLoc>())
|
||||||
|
Finder.add(TAL->getArgument(), Flags);
|
||||||
|
|
||||||
return Finder.takeDecls();
|
return Finder.takeDecls();
|
||||||
}
|
}
|
||||||
|
|
|
@ -479,6 +479,10 @@ public:
|
||||||
bool TraverseTypeLoc(TypeLoc X) {
|
bool TraverseTypeLoc(TypeLoc X) {
|
||||||
return traverseNode(&X, [&] { return Base::TraverseTypeLoc(X); });
|
return traverseNode(&X, [&] { return Base::TraverseTypeLoc(X); });
|
||||||
}
|
}
|
||||||
|
bool TraverseTemplateArgumentLoc(const TemplateArgumentLoc &X) {
|
||||||
|
return traverseNode(&X,
|
||||||
|
[&] { return Base::TraverseTemplateArgumentLoc(X); });
|
||||||
|
}
|
||||||
bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc X) {
|
bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc X) {
|
||||||
return traverseNode(
|
return traverseNode(
|
||||||
&X, [&] { return Base::TraverseNestedNameSpecifierLoc(X); });
|
&X, [&] { return Base::TraverseNestedNameSpecifierLoc(X); });
|
||||||
|
|
|
@ -376,6 +376,15 @@ TEST_F(TargetDeclTest, ClassTemplate) {
|
||||||
{"template<> class Foo<int *>", Rel::TemplateInstantiation},
|
{"template<> class Foo<int *>", Rel::TemplateInstantiation},
|
||||||
{"template <typename T> class Foo<T *>", Rel::TemplatePattern});
|
{"template <typename T> class Foo<T *>", Rel::TemplatePattern});
|
||||||
|
|
||||||
|
Code = R"cpp(
|
||||||
|
// Template template argument.
|
||||||
|
template<typename T> struct Vector {};
|
||||||
|
template <template <typename> class Container>
|
||||||
|
struct A {};
|
||||||
|
A<[[Vector]]> a;
|
||||||
|
)cpp";
|
||||||
|
EXPECT_DECLS("TemplateArgumentLoc", {"template <typename T> struct Vector"});
|
||||||
|
|
||||||
Flags.push_back("-std=c++17"); // for CTAD tests
|
Flags.push_back("-std=c++17"); // for CTAD tests
|
||||||
|
|
||||||
Code = R"cpp(
|
Code = R"cpp(
|
||||||
|
|
|
@ -407,8 +407,16 @@ TEST(SelectionTest, CommonAncestor) {
|
||||||
s2[[-^>]]f();
|
s2[[-^>]]f();
|
||||||
}
|
}
|
||||||
)cpp",
|
)cpp",
|
||||||
"DeclRefExpr"} // DeclRefExpr to the "operator->" method.
|
"DeclRefExpr"}, // DeclRefExpr to the "operator->" method.
|
||||||
};
|
|
||||||
|
// Template template argument.
|
||||||
|
{R"cpp(
|
||||||
|
template <typename> class Vector {};
|
||||||
|
template <template <typename> class Container> class A {};
|
||||||
|
A<[[V^ector]]> a;
|
||||||
|
)cpp",
|
||||||
|
"TemplateArgumentLoc"}};
|
||||||
|
|
||||||
for (const Case &C : Cases) {
|
for (const Case &C : Cases) {
|
||||||
trace::TestTracer Tracer;
|
trace::TestTracer Tracer;
|
||||||
Annotations Test(C.Code);
|
Annotations Test(C.Code);
|
||||||
|
|
Loading…
Reference in New Issue