1//===-- FindTargetTests.cpp --------------------------*- C++ -*------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8#include "FindTarget.h"
9
10#include "Selection.h"
11#include "TestTU.h"
12#include "clang/AST/Decl.h"
13#include "clang/AST/DeclTemplate.h"
14#include "clang/Basic/SourceLocation.h"
15#include "llvm/ADT/StringRef.h"
16#include "llvm/Support/Casting.h"
17#include "llvm/Support/raw_ostream.h"
18#include "llvm/Testing/Annotations/Annotations.h"
19#include "gmock/gmock.h"
20#include "gtest/gtest.h"
21#include <initializer_list>
22
23namespace clang {
24namespace clangd {
25namespace {
26
27// A referenced Decl together with its DeclRelationSet, for assertions.
28//
29// There's no great way to assert on the "content" of a Decl in the general case
30// that's both expressive and unambiguous (e.g. clearly distinguishes between
31// templated decls and their specializations).
32//
33// We use the result of pretty-printing the decl, with the {body} truncated.
34struct PrintedDecl {
35 PrintedDecl(const char *Name, DeclRelationSet Relations = {})
36 : Name(Name), Relations(Relations) {}
37 PrintedDecl(const NamedDecl *D, DeclRelationSet Relations = {})
38 : Relations(Relations) {
39 std::string S;
40 llvm::raw_string_ostream OS(S);
41 D->print(OS);
42 llvm::StringRef FirstLine =
43 llvm::StringRef(OS.str()).take_until(F: [](char C) { return C == '\n'; });
44 FirstLine = FirstLine.rtrim(Chars: " {");
45 Name = std::string(FirstLine.rtrim(Chars: " {"));
46 }
47
48 std::string Name;
49 DeclRelationSet Relations;
50};
51bool operator==(const PrintedDecl &L, const PrintedDecl &R) {
52 return std::tie(args: L.Name, args: L.Relations) == std::tie(args: R.Name, args: R.Relations);
53}
54llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const PrintedDecl &D) {
55 return OS << D.Name << " Rel=" << D.Relations;
56}
57
58// The test cases in for targetDecl() take the form
59// - a piece of code (Code = "...")
60// - Code should have a single AST node marked as a [[range]]
61// - an EXPECT_DECLS() assertion that verify the type of node selected, and
62// all the decls that targetDecl() considers it to reference
63// Despite the name, these cases actually test allTargetDecls() for brevity.
64class TargetDeclTest : public ::testing::Test {
65protected:
66 using Rel = DeclRelation;
67 std::string Code;
68 std::vector<std::string> Flags;
69
70 // Asserts that `Code` has a marked selection of a node `NodeType`,
71 // and returns allTargetDecls() as PrintedDecl structs.
72 // Use via EXPECT_DECLS().
73 std::vector<PrintedDecl> assertNodeAndPrintDecls(const char *NodeType) {
74 llvm::Annotations A(Code);
75 auto TU = TestTU::withCode(Code: A.code());
76 TU.ExtraArgs = Flags;
77 auto AST = TU.build();
78 llvm::Annotations::Range R = A.range();
79 auto Selection = SelectionTree::createRight(
80 AST&: AST.getASTContext(), Tokens: AST.getTokens(), Begin: R.Begin, End: R.End);
81 const SelectionTree::Node *N = Selection.commonAncestor();
82 if (!N) {
83 ADD_FAILURE() << "No node selected!\n" << Code;
84 return {};
85 }
86 EXPECT_EQ(N->kind(), NodeType) << Selection;
87
88 std::vector<PrintedDecl> ActualDecls;
89 for (const auto &Entry :
90 allTargetDecls(N->ASTNode, AST.getHeuristicResolver()))
91 ActualDecls.emplace_back(Entry.first, Entry.second);
92 return ActualDecls;
93 }
94};
95
96// This is a macro to preserve line numbers in assertion failures.
97// It takes the expected decls as varargs to work around comma-in-macro issues.
98#define EXPECT_DECLS(NodeType, ...) \
99 EXPECT_THAT(assertNodeAndPrintDecls(NodeType), \
100 ::testing::UnorderedElementsAreArray( \
101 std::vector<PrintedDecl>({__VA_ARGS__}))) \
102 << Code
103using ExpectedDecls = std::vector<PrintedDecl>;
104
105TEST_F(TargetDeclTest, Exprs) {
106 Code = R"cpp(
107 int f();
108 int x = [[f]]();
109 )cpp";
110 EXPECT_DECLS("DeclRefExpr", "int f()");
111
112 Code = R"cpp(
113 struct S { S operator+(S) const; };
114 auto X = S() [[+]] S();
115 )cpp";
116 EXPECT_DECLS("DeclRefExpr", "S operator+(S) const");
117
118 Code = R"cpp(
119 int foo();
120 int s = foo[[()]];
121 )cpp";
122 EXPECT_DECLS("CallExpr", "int foo()");
123
124 Code = R"cpp(
125 struct X {
126 void operator()(int n);
127 };
128 void test() {
129 X x;
130 x[[(123)]];
131 }
132 )cpp";
133 EXPECT_DECLS("CXXOperatorCallExpr", "void operator()(int n)");
134
135 Code = R"cpp(
136 void test() {
137 goto [[label]];
138 label:
139 return;
140 }
141 )cpp";
142 EXPECT_DECLS("GotoStmt", "label:");
143 Code = R"cpp(
144 void test() {
145 [[label]]:
146 return;
147 }
148 )cpp";
149 EXPECT_DECLS("LabelStmt", "label:");
150}
151
152TEST_F(TargetDeclTest, RecoveryForC) {
153 Flags = {"-xc", "-Xclang", "-frecovery-ast"};
154 Code = R"cpp(
155 // error-ok: testing behavior on broken code
156 // int f();
157 int f(int);
158 int x = [[f]]();
159 )cpp";
160 EXPECT_DECLS("DeclRefExpr", "int f(int)");
161}
162
163TEST_F(TargetDeclTest, Recovery) {
164 Code = R"cpp(
165 // error-ok: testing behavior on broken code
166 int f();
167 int f(int, int);
168 int x = [[f]](42);
169 )cpp";
170 EXPECT_DECLS("UnresolvedLookupExpr", "int f()", "int f(int, int)");
171}
172
173TEST_F(TargetDeclTest, RecoveryType) {
174 Code = R"cpp(
175 // error-ok: testing behavior on broken code
176 struct S { int member; };
177 S overloaded(int);
178 void foo() {
179 // No overload matches, but we have recovery-expr with the correct type.
180 overloaded().[[member]];
181 }
182 )cpp";
183 EXPECT_DECLS("MemberExpr", "int member");
184}
185
186TEST_F(TargetDeclTest, UsingDecl) {
187 Code = R"cpp(
188 namespace foo {
189 int f(int);
190 int f(char);
191 }
192 using foo::f;
193 int x = [[f]](42);
194 )cpp";
195 // f(char) is not referenced!
196 EXPECT_DECLS("DeclRefExpr", {"using foo::f", Rel::Alias}, {"int f(int)"});
197
198 Code = R"cpp(
199 namespace foo {
200 int f(int);
201 int f(char);
202 }
203 [[using foo::f]];
204 )cpp";
205 // All overloads are referenced.
206 EXPECT_DECLS("UsingDecl", {"using foo::f", Rel::Alias}, {"int f(int)"},
207 {"int f(char)"});
208
209 Code = R"cpp(
210 struct X {
211 int foo();
212 };
213 struct Y : X {
214 using X::foo;
215 };
216 int x = Y().[[foo]]();
217 )cpp";
218 EXPECT_DECLS("MemberExpr", {"using X::foo", Rel::Alias}, {"int foo()"});
219
220 Code = R"cpp(
221 template <typename T>
222 struct Base {
223 void waldo() {}
224 };
225 template <typename T>
226 struct Derived : Base<T> {
227 using Base<T>::[[waldo]];
228 };
229 )cpp";
230 EXPECT_DECLS("UnresolvedUsingValueDecl", {"using Base<T>::waldo", Rel::Alias},
231 {"void waldo()"});
232
233 Code = R"cpp(
234 namespace ns {
235 template<typename T> class S {};
236 }
237
238 using ns::S;
239
240 template<typename T>
241 using A = [[S]]<T>;
242 )cpp";
243 EXPECT_DECLS("TemplateSpecializationTypeLoc", {"using ns::S", Rel::Alias},
244 {"template <typename T> class S"},
245 {"class S", Rel::TemplatePattern});
246
247 Code = R"cpp(
248 namespace ns {
249 template<typename T> class S {};
250 }
251
252 using ns::S;
253 template <template <typename> class T> class X {};
254 using B = X<[[S]]>;
255 )cpp";
256 EXPECT_DECLS("TemplateArgumentLoc", {"using ns::S", Rel::Alias},
257 {"template <typename T> class S"});
258
259 Code = R"cpp(
260 namespace ns {
261 template<typename T> class S { public: S(T); };
262 }
263
264 using ns::S;
265 [[S]] s(123);
266 )cpp";
267 Flags.push_back(x: "-std=c++17"); // For CTAD feature.
268 EXPECT_DECLS("DeducedTemplateSpecializationTypeLoc",
269 {"using ns::S", Rel::Alias}, {"template <typename T> class S"},
270 {"class S", Rel::TemplatePattern});
271
272 Code = R"cpp(
273 template<typename T>
274 class Foo { public: class foo {}; };
275 template <class T> class A : public Foo<T> {
276 using typename Foo<T>::foo;
277 [[foo]] abc;
278 };
279 )cpp";
280 EXPECT_DECLS("UnresolvedUsingTypeLoc",
281 {"using typename Foo<T>::foo", Rel::Alias});
282
283 // Using enum.
284 Flags.push_back(x: "-std=c++20");
285 Code = R"cpp(
286 namespace ns { enum class A { X }; }
287 [[using enum ns::A]];
288 )cpp";
289 EXPECT_DECLS("UsingEnumDecl", "enum class A : int");
290
291 Code = R"cpp(
292 namespace ns { enum class A { X }; }
293 using enum ns::A;
294 auto m = [[X]];
295 )cpp";
296 EXPECT_DECLS("DeclRefExpr", "X");
297}
298
299TEST_F(TargetDeclTest, BaseSpecifier) {
300 Code = R"cpp(
301 struct X {};
302 struct Y : [[private]] X {};
303 )cpp";
304 EXPECT_DECLS("CXXBaseSpecifier", "struct X");
305 Code = R"cpp(
306 struct X {};
307 struct Y : [[private X]] {};
308 )cpp";
309 EXPECT_DECLS("CXXBaseSpecifier", "struct X");
310 Code = R"cpp(
311 struct X {};
312 struct Y : private [[X]] {};
313 )cpp";
314 EXPECT_DECLS("RecordTypeLoc", "struct X");
315}
316
317TEST_F(TargetDeclTest, ConstructorInitList) {
318 Code = R"cpp(
319 struct X {
320 int a;
321 X() : [[a]](42) {}
322 };
323 )cpp";
324 EXPECT_DECLS("CXXCtorInitializer", "int a");
325
326 Code = R"cpp(
327 struct X {
328 X() : [[X]](1) {}
329 X(int);
330 };
331 )cpp";
332 EXPECT_DECLS("RecordTypeLoc", "struct X");
333}
334
335TEST_F(TargetDeclTest, DesignatedInit) {
336 Flags = {"-xc"}; // array designators are a C99 extension.
337 Code = R"c(
338 struct X { int a; };
339 struct Y { int b; struct X c[2]; };
340 struct Y y = { .c[0].[[a]] = 1 };
341 )c";
342 EXPECT_DECLS("DesignatedInitExpr", "int a");
343}
344
345TEST_F(TargetDeclTest, NestedNameSpecifier) {
346 Code = R"cpp(
347 namespace a { namespace b { int c; } }
348 int x = a::[[b::]]c;
349 )cpp";
350 EXPECT_DECLS("NestedNameSpecifierLoc", "namespace b");
351
352 Code = R"cpp(
353 namespace a { struct X { enum { y }; }; }
354 int x = a::[[X::]]y;
355 )cpp";
356 EXPECT_DECLS("NestedNameSpecifierLoc", "struct X");
357
358 Code = R"cpp(
359 template <typename T>
360 int x = [[T::]]y;
361 )cpp";
362 EXPECT_DECLS("NestedNameSpecifierLoc", "typename T");
363
364 Code = R"cpp(
365 namespace a { int x; }
366 namespace b = a;
367 int y = [[b]]::x;
368 )cpp";
369 EXPECT_DECLS("NestedNameSpecifierLoc", {"namespace b = a", Rel::Alias},
370 {"namespace a", Rel::Underlying});
371}
372
373TEST_F(TargetDeclTest, Types) {
374 Code = R"cpp(
375 struct X{};
376 [[X]] x;
377 )cpp";
378 EXPECT_DECLS("RecordTypeLoc", "struct X");
379
380 Code = R"cpp(
381 struct S{};
382 typedef S X;
383 [[X]] x;
384 )cpp";
385 EXPECT_DECLS("TypedefTypeLoc", {"typedef S X", Rel::Alias},
386 {"struct S", Rel::Underlying});
387 Code = R"cpp(
388 namespace ns { struct S{}; }
389 typedef ns::S X;
390 [[X]] x;
391 )cpp";
392 EXPECT_DECLS("TypedefTypeLoc", {"typedef ns::S X", Rel::Alias},
393 {"struct S", Rel::Underlying});
394
395 Code = R"cpp(
396 template<class T>
397 void foo() { [[T]] x; }
398 )cpp";
399 EXPECT_DECLS("TemplateTypeParmTypeLoc", "class T");
400 Flags.clear();
401
402 Code = R"cpp(
403 template<template<typename> class T>
404 void foo() { [[T<int>]] x; }
405 )cpp";
406 EXPECT_DECLS("TemplateSpecializationTypeLoc", "template <typename> class T");
407 Flags.clear();
408
409 Code = R"cpp(
410 template<template<typename> class ...T>
411 class C {
412 C<[[T...]]> foo;
413 };
414 )cpp";
415 EXPECT_DECLS("TemplateArgumentLoc", {"template <typename> class ...T"});
416 Flags.clear();
417
418 Code = R"cpp(
419 struct S{};
420 S X;
421 [[decltype]](X) Y;
422 )cpp";
423 EXPECT_DECLS("DecltypeTypeLoc", {"struct S", Rel::Underlying});
424
425 Code = R"cpp(
426 struct S{};
427 [[auto]] X = S{};
428 )cpp";
429 // FIXME: deduced type missing in AST. https://llvm.org/PR42914
430 EXPECT_DECLS("AutoTypeLoc", );
431
432 Code = R"cpp(
433 template <typename... E>
434 struct S {
435 static const int size = sizeof...([[E]]);
436 };
437 )cpp";
438 EXPECT_DECLS("SizeOfPackExpr", "typename ...E");
439
440 Code = R"cpp(
441 template <typename T>
442 class Foo {
443 void f([[Foo]] x);
444 };
445 )cpp";
446 EXPECT_DECLS("InjectedClassNameTypeLoc", "class Foo");
447}
448
449TEST_F(TargetDeclTest, ClassTemplate) {
450 Code = R"cpp(
451 // Implicit specialization.
452 template<int x> class Foo{};
453 [[Foo<42>]] B;
454 )cpp";
455 EXPECT_DECLS("TemplateSpecializationTypeLoc",
456 {"template<> class Foo<42>", Rel::TemplateInstantiation},
457 {"class Foo", Rel::TemplatePattern});
458
459 Code = R"cpp(
460 template<typename T> class Foo {};
461 // The "Foo<int>" SpecializationDecl is incomplete, there is no
462 // instantiation happening.
463 void func([[Foo<int>]] *);
464 )cpp";
465 EXPECT_DECLS("TemplateSpecializationTypeLoc",
466 {"class Foo", Rel::TemplatePattern},
467 {"template<> class Foo<int>", Rel::TemplateInstantiation});
468
469 Code = R"cpp(
470 // Explicit specialization.
471 template<int x> class Foo{};
472 template<> class Foo<42>{};
473 [[Foo<42>]] B;
474 )cpp";
475 EXPECT_DECLS("TemplateSpecializationTypeLoc", "template<> class Foo<42>");
476
477 Code = R"cpp(
478 // Partial specialization.
479 template<typename T> class Foo{};
480 template<typename T> class Foo<T*>{};
481 [[Foo<int*>]] B;
482 )cpp";
483 EXPECT_DECLS("TemplateSpecializationTypeLoc",
484 {"template<> class Foo<int *>", Rel::TemplateInstantiation},
485 {"template <typename T> class Foo<T *>", Rel::TemplatePattern});
486
487 Code = R"cpp(
488 // Template template argument.
489 template<typename T> struct Vector {};
490 template <template <typename> class Container>
491 struct A {};
492 A<[[Vector]]> a;
493 )cpp";
494 EXPECT_DECLS("TemplateArgumentLoc", {"template <typename T> struct Vector"});
495
496 Flags.push_back(x: "-std=c++17"); // for CTAD tests
497
498 Code = R"cpp(
499 // Class template argument deduction
500 template <typename T>
501 struct Test {
502 Test(T);
503 };
504 void foo() {
505 [[Test]] a(5);
506 }
507 )cpp";
508 EXPECT_DECLS("DeducedTemplateSpecializationTypeLoc",
509 {"struct Test", Rel::TemplatePattern});
510
511 Code = R"cpp(
512 // Deduction guide
513 template <typename T>
514 struct Test {
515 template <typename I>
516 Test(I, I);
517 };
518 template <typename I>
519 [[Test]](I, I) -> Test<typename I::type>;
520 )cpp";
521 EXPECT_DECLS("CXXDeductionGuideDecl", {"template <typename T> struct Test"});
522}
523
524TEST_F(TargetDeclTest, Concept) {
525 Flags.push_back(x: "-std=c++20");
526
527 // FIXME: Should we truncate the pretty-printed form of a concept decl
528 // somewhere?
529
530 Code = R"cpp(
531 template <typename T>
532 concept Fooable = requires (T t) { t.foo(); };
533
534 template <typename T> requires [[Fooable]]<T>
535 void bar(T t) {
536 t.foo();
537 }
538 )cpp";
539 EXPECT_DECLS(
540 "ConceptReference",
541 {"template <typename T> concept Fooable = requires (T t) { t.foo(); }"});
542
543 // trailing requires clause
544 Code = R"cpp(
545 template <typename T>
546 concept Fooable = true;
547
548 template <typename T>
549 void foo() requires [[Fooable]]<T>;
550 )cpp";
551 EXPECT_DECLS("ConceptReference",
552 {"template <typename T> concept Fooable = true"});
553
554 // constrained-parameter
555 Code = R"cpp(
556 template <typename T>
557 concept Fooable = true;
558
559 template <[[Fooable]] T>
560 void bar(T t);
561 )cpp";
562 EXPECT_DECLS("ConceptReference",
563 {"template <typename T> concept Fooable = true"});
564
565 // partial-concept-id
566 Code = R"cpp(
567 template <typename T, typename U>
568 concept Fooable = true;
569
570 template <[[Fooable]]<int> T>
571 void bar(T t);
572 )cpp";
573 EXPECT_DECLS("ConceptReference",
574 {"template <typename T, typename U> concept Fooable = true"});
575}
576
577TEST_F(TargetDeclTest, Coroutine) {
578 Flags.push_back(x: "-std=c++20");
579
580 Code = R"cpp(
581 namespace std {
582 template <typename, typename...> struct coroutine_traits;
583 template <typename> struct coroutine_handle {
584 template <typename U>
585 coroutine_handle(coroutine_handle<U>&&) noexcept;
586 static coroutine_handle from_address(void* __addr) noexcept;
587 };
588 } // namespace std
589
590 struct executor {};
591 struct awaitable {};
592 struct awaitable_frame {
593 awaitable get_return_object();
594 void return_void();
595 void unhandled_exception();
596 struct result_t {
597 ~result_t();
598 bool await_ready() const noexcept;
599 void await_suspend(std::coroutine_handle<void>) noexcept;
600 void await_resume() const noexcept;
601 };
602 result_t initial_suspend() noexcept;
603 result_t final_suspend() noexcept;
604 result_t await_transform(executor) noexcept;
605 };
606
607 namespace std {
608 template <>
609 struct coroutine_traits<awaitable> {
610 typedef awaitable_frame promise_type;
611 };
612 } // namespace std
613
614 awaitable foo() {
615 co_await [[executor]]();
616 }
617 )cpp";
618 EXPECT_DECLS("RecordTypeLoc", "struct executor");
619}
620
621TEST_F(TargetDeclTest, RewrittenBinaryOperator) {
622 Flags.push_back(x: "-std=c++20");
623
624 Code = R"cpp(
625 namespace std {
626 struct strong_ordering {
627 int n;
628 constexpr operator int() const { return n; }
629 static const strong_ordering equal, greater, less;
630 };
631 constexpr strong_ordering strong_ordering::equal = {0};
632 constexpr strong_ordering strong_ordering::greater = {1};
633 constexpr strong_ordering strong_ordering::less = {-1};
634 }
635
636 struct Foo
637 {
638 int x;
639 auto operator<=>(const Foo&) const = default;
640 };
641
642 bool x = (Foo(1) [[!=]] Foo(2));
643 )cpp";
644 EXPECT_DECLS("CXXRewrittenBinaryOperator",
645 {"std::strong_ordering operator<=>(const Foo &) const = default",
646 Rel::TemplatePattern},
647 {"bool operator==(const Foo &) const noexcept = default",
648 Rel::TemplateInstantiation});
649}
650
651TEST_F(TargetDeclTest, FunctionTemplate) {
652 Code = R"cpp(
653 // Implicit specialization.
654 template<typename T> bool foo(T) { return false; };
655 bool x = [[foo]](42);
656 )cpp";
657 EXPECT_DECLS("DeclRefExpr",
658 {"template<> bool foo<int>(int)", Rel::TemplateInstantiation},
659 {"bool foo(T)", Rel::TemplatePattern});
660
661 Code = R"cpp(
662 // Explicit specialization.
663 template<typename T> bool foo(T) { return false; };
664 template<> bool foo<int>(int) { return false; };
665 bool x = [[foo]](42);
666 )cpp";
667 EXPECT_DECLS("DeclRefExpr", "template<> bool foo<int>(int)");
668}
669
670TEST_F(TargetDeclTest, VariableTemplate) {
671 // Pretty-printer doesn't do a very good job of variable templates :-(
672 Code = R"cpp(
673 // Implicit specialization.
674 template<typename T> int foo;
675 int x = [[foo]]<char>;
676 )cpp";
677 EXPECT_DECLS("DeclRefExpr", {"int foo", Rel::TemplateInstantiation},
678 {"int foo", Rel::TemplatePattern});
679
680 Code = R"cpp(
681 // Explicit specialization.
682 template<typename T> int foo;
683 template <> bool foo<char>;
684 int x = [[foo]]<char>;
685 )cpp";
686 EXPECT_DECLS("DeclRefExpr", "bool foo");
687
688 Code = R"cpp(
689 // Partial specialization.
690 template<typename T> int foo;
691 template<typename T> bool foo<T*>;
692 bool x = [[foo]]<char*>;
693 )cpp";
694 EXPECT_DECLS("DeclRefExpr", {"bool foo", Rel::TemplateInstantiation},
695 {"bool foo", Rel::TemplatePattern});
696}
697
698TEST_F(TargetDeclTest, TypeAliasTemplate) {
699 Code = R"cpp(
700 template<typename T, int X> class SmallVector {};
701 template<typename U> using TinyVector = SmallVector<U, 1>;
702 [[TinyVector<int>]] X;
703 )cpp";
704 EXPECT_DECLS("TemplateSpecializationTypeLoc",
705 {"template<> class SmallVector<int, 1>",
706 Rel::TemplateInstantiation | Rel::Underlying},
707 {"class SmallVector", Rel::TemplatePattern | Rel::Underlying},
708 {"using TinyVector = SmallVector<U, 1>",
709 Rel::Alias | Rel::TemplatePattern});
710}
711
712TEST_F(TargetDeclTest, BuiltinTemplates) {
713 Code = R"cpp(
714 template <class T, T... Index> struct integer_sequence {};
715 [[__make_integer_seq]]<integer_sequence, int, 3> X;
716 )cpp";
717 EXPECT_DECLS(
718 "TemplateSpecializationTypeLoc",
719 {"struct integer_sequence", Rel::TemplatePattern | Rel::Underlying},
720 {"template<> struct integer_sequence<int, <0, 1, 2>>",
721 Rel::TemplateInstantiation | Rel::Underlying});
722
723 // Dependent context.
724 Code = R"cpp(
725 template <class T, T... Index> struct integer_sequence;
726
727 template <class T, int N>
728 using make_integer_sequence = [[__make_integer_seq]]<integer_sequence, T, N>;
729 )cpp";
730 EXPECT_DECLS("TemplateSpecializationTypeLoc", );
731
732 Code = R"cpp(
733 template <int N, class... Pack>
734 using type_pack_element = [[__type_pack_element]]<N, Pack...>;
735 )cpp";
736 EXPECT_DECLS("TemplateSpecializationTypeLoc", );
737}
738
739TEST_F(TargetDeclTest, MemberOfTemplate) {
740 Code = R"cpp(
741 template <typename T> struct Foo {
742 int x(T);
743 };
744 int y = Foo<int>().[[x]](42);
745 )cpp";
746 EXPECT_DECLS("MemberExpr", {"int x(int)", Rel::TemplateInstantiation},
747 {"int x(T)", Rel::TemplatePattern});
748
749 Code = R"cpp(
750 template <typename T> struct Foo {
751 template <typename U>
752 int x(T, U);
753 };
754 int y = Foo<char>().[[x]]('c', 42);
755 )cpp";
756 EXPECT_DECLS("MemberExpr",
757 {"template<> int x<int>(char, int)", Rel::TemplateInstantiation},
758 {"int x(T, U)", Rel::TemplatePattern});
759}
760
761TEST_F(TargetDeclTest, Lambda) {
762 Code = R"cpp(
763 void foo(int x = 42) {
764 auto l = [ [[x]] ]{ return x + 1; };
765 };
766 )cpp";
767 EXPECT_DECLS("DeclRefExpr", "int x = 42");
768
769 // It seems like this should refer to another var, with the outer param being
770 // an underlying decl. But it doesn't seem to exist.
771 Code = R"cpp(
772 void foo(int x = 42) {
773 auto l = [x]{ return [[x]] + 1; };
774 };
775 )cpp";
776 EXPECT_DECLS("DeclRefExpr", "int x = 42");
777
778 Code = R"cpp(
779 void foo() {
780 auto l = [x = 1]{ return [[x]] + 1; };
781 };
782 )cpp";
783 // FIXME: why both auto and int?
784 EXPECT_DECLS("DeclRefExpr", "auto int x = 1");
785}
786
787TEST_F(TargetDeclTest, OverloadExpr) {
788 Flags.push_back(x: "--target=x86_64-pc-linux-gnu");
789
790 Code = R"cpp(
791 void func(int*);
792 void func(char*);
793
794 template <class T>
795 void foo(T t) {
796 [[func]](t);
797 };
798 )cpp";
799 EXPECT_DECLS("UnresolvedLookupExpr", "void func(int *)", "void func(char *)");
800
801 Code = R"cpp(
802 struct X {
803 void func(int*);
804 void func(char*);
805 };
806
807 template <class T>
808 void foo(X x, T t) {
809 x.[[func]](t);
810 };
811 )cpp";
812 EXPECT_DECLS("UnresolvedMemberExpr", "void func(int *)", "void func(char *)");
813
814 Code = R"cpp(
815 struct X {
816 static void *operator new(unsigned long);
817 };
818 auto* k = [[new]] X();
819 )cpp";
820 EXPECT_DECLS("CXXNewExpr", "static void *operator new(unsigned long)");
821 Code = R"cpp(
822 void *operator new(unsigned long);
823 auto* k = [[new]] int();
824 )cpp";
825 EXPECT_DECLS("CXXNewExpr", "void *operator new(unsigned long)");
826
827 Code = R"cpp(
828 struct X {
829 static void operator delete(void *) noexcept;
830 };
831 void k(X* x) {
832 [[delete]] x;
833 }
834 )cpp";
835 EXPECT_DECLS("CXXDeleteExpr", "static void operator delete(void *) noexcept");
836 Code = R"cpp(
837 void operator delete(void *) noexcept;
838 void k(int* x) {
839 [[delete]] x;
840 }
841 )cpp";
842 EXPECT_DECLS("CXXDeleteExpr", "void operator delete(void *) noexcept");
843}
844
845TEST_F(TargetDeclTest, DependentExprs) {
846 // Heuristic resolution of method of dependent field
847 Code = R"cpp(
848 struct A { void foo() {} };
849 template <typename T>
850 struct B {
851 A a;
852 void bar() {
853 this->a.[[foo]]();
854 }
855 };
856 )cpp";
857 EXPECT_DECLS("CXXDependentScopeMemberExpr", "void foo()");
858
859 // Similar to above but base expression involves a function call.
860 Code = R"cpp(
861 struct A {
862 void foo() {}
863 };
864 struct B {
865 A getA();
866 };
867 template <typename T>
868 struct C {
869 B c;
870 void bar() {
871 this->c.getA().[[foo]]();
872 }
873 };
874 )cpp";
875 EXPECT_DECLS("CXXDependentScopeMemberExpr", "void foo()");
876
877 // Similar to above but uses a function pointer.
878 Code = R"cpp(
879 struct A {
880 void foo() {}
881 };
882 struct B {
883 using FPtr = A(*)();
884 FPtr fptr;
885 };
886 template <typename T>
887 struct C {
888 B c;
889 void bar() {
890 this->c.fptr().[[foo]]();
891 }
892 };
893 )cpp";
894 EXPECT_DECLS("CXXDependentScopeMemberExpr", "void foo()");
895
896 // Base expression involves a member access into this.
897 Code = R"cpp(
898 struct Bar {
899 int aaaa;
900 };
901 template <typename T> struct Foo {
902 Bar func(int);
903 void test() {
904 func(1).[[aaaa]];
905 }
906 };
907 )cpp";
908 EXPECT_DECLS("CXXDependentScopeMemberExpr", "int aaaa");
909
910 Code = R"cpp(
911 class Foo {
912 public:
913 static Foo k(int);
914 template <typename T> T convert() const;
915 };
916 template <typename T>
917 void test() {
918 Foo::k(T()).template [[convert]]<T>();
919 }
920 )cpp";
921 EXPECT_DECLS("CXXDependentScopeMemberExpr",
922 "template <typename T> T convert() const");
923
924 Code = R"cpp(
925 template <typename T>
926 struct Waldo {
927 void find();
928 };
929 template <typename T>
930 using Wally = Waldo<T>;
931 template <typename T>
932 void foo(Wally<T> w) {
933 w.[[find]]();
934 }
935 )cpp";
936 EXPECT_DECLS("CXXDependentScopeMemberExpr", "void find()");
937
938 Code = R"cpp(
939 template <typename T>
940 struct Waldo {
941 void find();
942 };
943 template <typename T>
944 struct MetaWaldo {
945 using Type = Waldo<T>;
946 };
947 template <typename T>
948 void foo(typename MetaWaldo<T>::Type w) {
949 w.[[find]]();
950 }
951 )cpp";
952 EXPECT_DECLS("CXXDependentScopeMemberExpr", "void find()");
953
954 Code = R"cpp(
955 struct Waldo {
956 void find();
957 };
958 template <typename T>
959 using Wally = Waldo;
960 template <typename>
961 struct S : Wally<int> {
962 void Foo() { this->[[find]](); }
963 };
964 )cpp";
965 EXPECT_DECLS("CXXDependentScopeMemberExpr", "void find()");
966}
967
968TEST_F(TargetDeclTest, DependentTypes) {
969 // Heuristic resolution of dependent type name
970 Code = R"cpp(
971 template <typename>
972 struct A { struct B {}; };
973
974 template <typename T>
975 void foo(typename A<T>::[[B]]);
976 )cpp";
977 EXPECT_DECLS("DependentNameTypeLoc", "struct B");
978
979 // Heuristic resolution of dependent type name which doesn't get a TypeLoc
980 Code = R"cpp(
981 template <typename>
982 struct A { struct B { struct C {}; }; };
983
984 template <typename T>
985 void foo(typename A<T>::[[B]]::C);
986 )cpp";
987 EXPECT_DECLS("NestedNameSpecifierLoc", "struct B");
988
989 // Heuristic resolution of dependent type name whose qualifier is also
990 // dependent
991 Code = R"cpp(
992 template <typename>
993 struct A { struct B { struct C {}; }; };
994
995 template <typename T>
996 void foo(typename A<T>::B::[[C]]);
997 )cpp";
998 EXPECT_DECLS("DependentNameTypeLoc", "struct C");
999
1000 // Heuristic resolution of dependent template name
1001 Code = R"cpp(
1002 template <typename>
1003 struct A {
1004 template <typename> struct B {};
1005 };
1006
1007 template <typename T>
1008 void foo(typename A<T>::template [[B]]<int>);
1009 )cpp";
1010 EXPECT_DECLS("DependentTemplateSpecializationTypeLoc",
1011 "template <typename> struct B");
1012
1013 // Dependent name with recursive definition. We don't expect a
1014 // result, but we shouldn't get into a stack overflow either.
1015 Code = R"cpp(
1016 template <int N>
1017 struct waldo {
1018 typedef typename waldo<N - 1>::type::[[next]] type;
1019 };
1020 )cpp";
1021 EXPECT_DECLS("DependentNameTypeLoc", );
1022
1023 // Similar to above but using mutually recursive templates.
1024 Code = R"cpp(
1025 template <int N>
1026 struct odd;
1027
1028 template <int N>
1029 struct even {
1030 using type = typename odd<N - 1>::type::next;
1031 };
1032
1033 template <int N>
1034 struct odd {
1035 using type = typename even<N - 1>::type::[[next]];
1036 };
1037 )cpp";
1038 EXPECT_DECLS("DependentNameTypeLoc", );
1039}
1040
1041TEST_F(TargetDeclTest, TypedefCascade) {
1042 Code = R"cpp(
1043 struct C {
1044 using type = int;
1045 };
1046 struct B {
1047 using type = C::type;
1048 };
1049 struct A {
1050 using type = B::type;
1051 };
1052 A::[[type]] waldo;
1053 )cpp";
1054 EXPECT_DECLS("TypedefTypeLoc",
1055 {"using type = int", Rel::Alias | Rel::Underlying},
1056 {"using type = C::type", Rel::Alias | Rel::Underlying},
1057 {"using type = B::type", Rel::Alias});
1058}
1059
1060TEST_F(TargetDeclTest, RecursiveTemplate) {
1061 Flags.push_back(x: "-std=c++20"); // the test case uses concepts
1062
1063 Code = R"cpp(
1064 template <typename T>
1065 concept Leaf = false;
1066
1067 template <typename Tree>
1068 struct descend_left {
1069 using type = typename descend_left<typename Tree::left>::[[type]];
1070 };
1071
1072 template <Leaf Tree>
1073 struct descend_left<Tree> {
1074 using type = typename Tree::value;
1075 };
1076 )cpp";
1077 EXPECT_DECLS("DependentNameTypeLoc",
1078 {"using type = typename descend_left<typename Tree::left>::type",
1079 Rel::Alias | Rel::Underlying});
1080}
1081
1082TEST_F(TargetDeclTest, ObjC) {
1083 Flags = {"-xobjective-c"};
1084 Code = R"cpp(
1085 @interface Foo {}
1086 -(void)bar;
1087 @end
1088 void test(Foo *f) {
1089 [f [[bar]] ];
1090 }
1091 )cpp";
1092 EXPECT_DECLS("ObjCMessageExpr", "- (void)bar");
1093
1094 Code = R"cpp(
1095 @interface Foo { @public int bar; }
1096 @end
1097 int test(Foo *f) {
1098 return [[f->bar]];
1099 }
1100 )cpp";
1101 EXPECT_DECLS("ObjCIvarRefExpr", "int bar");
1102
1103 Code = R"cpp(
1104 @interface Foo {}
1105 -(int) x;
1106 -(void) setX:(int)x;
1107 @end
1108 void test(Foo *f) {
1109 [[f.x]] = 42;
1110 }
1111 )cpp";
1112 EXPECT_DECLS("ObjCPropertyRefExpr", "- (void)setX:(int)x");
1113
1114 Code = R"cpp(
1115 @interface I {}
1116 @property(retain) I* x;
1117 @property(retain) I* y;
1118 @end
1119 void test(I *f) {
1120 [[f.x]].y = 0;
1121 }
1122 )cpp";
1123 EXPECT_DECLS("ObjCPropertyRefExpr",
1124 "@property(atomic, retain, readwrite) I *x");
1125
1126 Code = R"cpp(
1127 @interface MYObject
1128 @end
1129 @interface Interface
1130 @property(retain) [[MYObject]] *x;
1131 @end
1132 )cpp";
1133 EXPECT_DECLS("ObjCInterfaceTypeLoc", "@interface MYObject");
1134
1135 Code = R"cpp(
1136 @interface MYObject2
1137 @end
1138 @interface Interface
1139 @property(retain, nonnull) [[MYObject2]] *x;
1140 @end
1141 )cpp";
1142 EXPECT_DECLS("ObjCInterfaceTypeLoc", "@interface MYObject2");
1143
1144 Code = R"cpp(
1145 @protocol Foo
1146 @end
1147 id test() {
1148 return [[@protocol(Foo)]];
1149 }
1150 )cpp";
1151 EXPECT_DECLS("ObjCProtocolExpr", "@protocol Foo");
1152
1153 Code = R"cpp(
1154 @interface Foo
1155 @end
1156 void test([[Foo]] *p);
1157 )cpp";
1158 EXPECT_DECLS("ObjCInterfaceTypeLoc", "@interface Foo");
1159
1160 Code = R"cpp(// Don't consider implicit interface as the target.
1161 @implementation [[Implicit]]
1162 @end
1163 )cpp";
1164 EXPECT_DECLS("ObjCImplementationDecl", "@implementation Implicit");
1165
1166 Code = R"cpp(
1167 @interface Foo
1168 @end
1169 @implementation [[Foo]]
1170 @end
1171 )cpp";
1172 EXPECT_DECLS("ObjCImplementationDecl", "@interface Foo");
1173
1174 Code = R"cpp(
1175 @interface Foo
1176 @end
1177 @interface Foo (Ext)
1178 @end
1179 @implementation [[Foo]] (Ext)
1180 @end
1181 )cpp";
1182 EXPECT_DECLS("ObjCCategoryImplDecl", "@interface Foo(Ext)");
1183
1184 Code = R"cpp(
1185 @interface Foo
1186 @end
1187 @interface Foo (Ext)
1188 @end
1189 @implementation Foo ([[Ext]])
1190 @end
1191 )cpp";
1192 EXPECT_DECLS("ObjCCategoryImplDecl", "@interface Foo(Ext)");
1193
1194 Code = R"cpp(
1195 void test(id</*error-ok*/[[InvalidProtocol]]> p);
1196 )cpp";
1197 EXPECT_DECLS("ParmVarDecl", "id p");
1198
1199 Code = R"cpp(
1200 @class C;
1201 @protocol Foo
1202 @end
1203 void test([[C]]<Foo> *p);
1204 )cpp";
1205 EXPECT_DECLS("ObjCInterfaceTypeLoc", "@class C;");
1206
1207 Code = R"cpp(
1208 @class C;
1209 @protocol Foo
1210 @end
1211 void test(C<[[Foo]]> *p);
1212 )cpp";
1213 EXPECT_DECLS("ObjCProtocolLoc", "@protocol Foo");
1214
1215 Code = R"cpp(
1216 @class C;
1217 @protocol Foo
1218 @end
1219 @protocol Bar
1220 @end
1221 void test(C<[[Foo]], Bar> *p);
1222 )cpp";
1223 EXPECT_DECLS("ObjCProtocolLoc", "@protocol Foo");
1224
1225 Code = R"cpp(
1226 @class C;
1227 @protocol Foo
1228 @end
1229 @protocol Bar
1230 @end
1231 void test(C<Foo, [[Bar]]> *p);
1232 )cpp";
1233 EXPECT_DECLS("ObjCProtocolLoc", "@protocol Bar");
1234
1235 Code = R"cpp(
1236 @interface Foo
1237 + (id)sharedInstance;
1238 @end
1239 @implementation Foo
1240 + (id)sharedInstance { return 0; }
1241 @end
1242 void test() {
1243 id value = [[Foo]].sharedInstance;
1244 }
1245 )cpp";
1246 EXPECT_DECLS("ObjCInterfaceTypeLoc", "@interface Foo");
1247
1248 Code = R"cpp(
1249 @interface Foo
1250 + (id)sharedInstance;
1251 @end
1252 @implementation Foo
1253 + (id)sharedInstance { return 0; }
1254 @end
1255 void test() {
1256 id value = Foo.[[sharedInstance]];
1257 }
1258 )cpp";
1259 EXPECT_DECLS("ObjCPropertyRefExpr", "+ (id)sharedInstance");
1260
1261 Code = R"cpp(
1262 @interface Foo
1263 + ([[id]])sharedInstance;
1264 @end
1265 )cpp";
1266 EXPECT_DECLS("TypedefTypeLoc", );
1267
1268 Code = R"cpp(
1269 @interface Foo
1270 + ([[instancetype]])sharedInstance;
1271 @end
1272 )cpp";
1273 EXPECT_DECLS("TypedefTypeLoc", );
1274}
1275
1276class FindExplicitReferencesTest : public ::testing::Test {
1277protected:
1278 struct AllRefs {
1279 std::string AnnotatedCode;
1280 std::string DumpedReferences;
1281 };
1282
1283 TestTU newTU(llvm::StringRef Code) {
1284 TestTU TU;
1285 TU.Code = std::string(Code);
1286
1287 // FIXME: Auto-completion in a template requires disabling delayed template
1288 // parsing.
1289 TU.ExtraArgs.push_back(x: "-std=c++20");
1290 TU.ExtraArgs.push_back(x: "-xobjective-c++");
1291
1292 return TU;
1293 }
1294
1295 AllRefs annotatedReferences(llvm::StringRef Code, ParsedAST &AST,
1296 std::vector<ReferenceLoc> Refs) {
1297 auto &SM = AST.getSourceManager();
1298 llvm::stable_sort(Range&: Refs, C: [&](const ReferenceLoc &L, const ReferenceLoc &R) {
1299 return SM.isBeforeInTranslationUnit(LHS: L.NameLoc, RHS: R.NameLoc);
1300 });
1301
1302 std::string AnnotatedCode;
1303 unsigned NextCodeChar = 0;
1304 for (unsigned I = 0; I < Refs.size(); ++I) {
1305 auto &R = Refs[I];
1306
1307 SourceLocation Pos = R.NameLoc;
1308 assert(Pos.isValid());
1309 if (Pos.isMacroID()) // FIXME: figure out how to show macro locations.
1310 Pos = SM.getExpansionLoc(Loc: Pos);
1311 assert(Pos.isFileID());
1312
1313 FileID File;
1314 unsigned Offset;
1315 std::tie(args&: File, args&: Offset) = SM.getDecomposedLoc(Loc: Pos);
1316 if (File == SM.getMainFileID()) {
1317 // Print the reference in a source code.
1318 assert(NextCodeChar <= Offset);
1319 AnnotatedCode += Code.substr(Start: NextCodeChar, N: Offset - NextCodeChar);
1320 AnnotatedCode += "$" + std::to_string(val: I) + "^";
1321
1322 NextCodeChar = Offset;
1323 }
1324 }
1325 AnnotatedCode += Code.substr(Start: NextCodeChar);
1326
1327 std::string DumpedReferences;
1328 for (unsigned I = 0; I < Refs.size(); ++I)
1329 DumpedReferences += std::string(llvm::formatv(Fmt: "{0}: {1}\n", Vals&: I, Vals&: Refs[I]));
1330
1331 return AllRefs{.AnnotatedCode: std::move(AnnotatedCode), .DumpedReferences: std::move(DumpedReferences)};
1332 }
1333
1334 /// Parses \p Code, and annotates its body with results of
1335 /// findExplicitReferences on all top level decls.
1336 /// See actual tests for examples of annotation format.
1337 AllRefs annotateAllReferences(llvm::StringRef Code) {
1338 TestTU TU = newTU(Code);
1339 auto AST = TU.build();
1340
1341 std::vector<ReferenceLoc> Refs;
1342 for (auto *TopLevel : AST.getLocalTopLevelDecls())
1343 findExplicitReferences(
1344 D: TopLevel, Out: [&Refs](ReferenceLoc R) { Refs.push_back(x: std::move(R)); },
1345 Resolver: AST.getHeuristicResolver());
1346 return annotatedReferences(Code, AST, Refs: std::move(Refs));
1347 }
1348
1349 /// Parses \p Code, finds function or namespace '::foo' and annotates its body
1350 /// with results of findExplicitReferences.
1351 /// See actual tests for examples of annotation format.
1352 AllRefs annotateReferencesInFoo(llvm::StringRef Code) {
1353 TestTU TU = newTU(Code);
1354 auto AST = TU.build();
1355 auto *TestDecl = &findDecl(AST, QName: "foo");
1356 if (auto *T = llvm::dyn_cast<FunctionTemplateDecl>(Val: TestDecl))
1357 TestDecl = T->getTemplatedDecl();
1358
1359 std::vector<ReferenceLoc> Refs;
1360 if (const auto *Func = llvm::dyn_cast<FunctionDecl>(Val: TestDecl))
1361 findExplicitReferences(
1362 S: Func->getBody(),
1363 Out: [&Refs](ReferenceLoc R) { Refs.push_back(x: std::move(R)); },
1364 Resolver: AST.getHeuristicResolver());
1365 else if (const auto *NS = llvm::dyn_cast<NamespaceDecl>(Val: TestDecl))
1366 findExplicitReferences(
1367 NS,
1368 [&Refs, &NS](ReferenceLoc R) {
1369 // Avoid adding the namespace foo decl to the results.
1370 if (R.Targets.size() == 1 && R.Targets.front() == NS)
1371 return;
1372 Refs.push_back(x: std::move(R));
1373 },
1374 AST.getHeuristicResolver());
1375 else if (const auto *OC = llvm::dyn_cast<ObjCContainerDecl>(Val: TestDecl))
1376 findExplicitReferences(
1377 OC, [&Refs](ReferenceLoc R) { Refs.push_back(x: std::move(R)); },
1378 AST.getHeuristicResolver());
1379 else
1380 ADD_FAILURE() << "Failed to find ::foo decl for test";
1381
1382 return annotatedReferences(Code, AST, Refs: std::move(Refs));
1383 }
1384};
1385
1386TEST_F(FindExplicitReferencesTest, AllRefsInFoo) {
1387 std::pair</*Code*/ llvm::StringRef, /*References*/ llvm::StringRef> Cases[] =
1388 {// Simple expressions.
1389 {R"cpp(
1390 int global;
1391 int func();
1392 void foo(int param) {
1393 $0^global = $1^param + $2^func();
1394 }
1395 )cpp",
1396 "0: targets = {global}\n"
1397 "1: targets = {param}\n"
1398 "2: targets = {func}\n"},
1399 {R"cpp(
1400 struct X { int a; };
1401 void foo(X x) {
1402 $0^x.$1^a = 10;
1403 }
1404 )cpp",
1405 "0: targets = {x}\n"
1406 "1: targets = {X::a}\n"},
1407 {R"cpp(
1408 // error-ok: testing with broken code
1409 int bar();
1410 int foo() {
1411 return $0^bar() + $1^bar(42);
1412 }
1413 )cpp",
1414 "0: targets = {bar}\n"
1415 "1: targets = {bar}\n"},
1416 // Namespaces and aliases.
1417 {R"cpp(
1418 namespace ns {}
1419 namespace alias = ns;
1420 void foo() {
1421 using namespace $0^ns;
1422 using namespace $1^alias;
1423 }
1424 )cpp",
1425 "0: targets = {ns}\n"
1426 "1: targets = {alias}\n"},
1427 // Using declarations.
1428 {R"cpp(
1429 namespace ns { int global; }
1430 void foo() {
1431 using $0^ns::$1^global;
1432 }
1433 )cpp",
1434 "0: targets = {ns}\n"
1435 "1: targets = {ns::global}, qualifier = 'ns::'\n"},
1436 // Using enum declarations.
1437 {R"cpp(
1438 namespace ns { enum class A {}; }
1439 void foo() {
1440 using enum $0^ns::$1^A;
1441 }
1442 )cpp",
1443 "0: targets = {ns}\n"
1444 "1: targets = {ns::A}, qualifier = 'ns::'\n"},
1445 // Simple types.
1446 {R"cpp(
1447 struct Struct { int a; };
1448 using Typedef = int;
1449 void foo() {
1450 $0^Struct $1^x;
1451 $2^Typedef $3^y;
1452 static_cast<$4^Struct*>(0);
1453 }
1454 )cpp",
1455 "0: targets = {Struct}\n"
1456 "1: targets = {x}, decl\n"
1457 "2: targets = {Typedef}\n"
1458 "3: targets = {y}, decl\n"
1459 "4: targets = {Struct}\n"},
1460 // Name qualifiers.
1461 {R"cpp(
1462 namespace a { namespace b { struct S { typedef int type; }; } }
1463 void foo() {
1464 $0^a::$1^b::$2^S $3^x;
1465 using namespace $4^a::$5^b;
1466 $6^S::$7^type $8^y;
1467 }
1468 )cpp",
1469 "0: targets = {a}\n"
1470 "1: targets = {a::b}, qualifier = 'a::'\n"
1471 "2: targets = {a::b::S}, qualifier = 'a::b::'\n"
1472 "3: targets = {x}, decl\n"
1473 "4: targets = {a}\n"
1474 "5: targets = {a::b}, qualifier = 'a::'\n"
1475 "6: targets = {a::b::S}\n"
1476 "7: targets = {a::b::S::type}, qualifier = 'struct S::'\n"
1477 "8: targets = {y}, decl\n"},
1478 {R"cpp(
1479 void foo() {
1480 $0^ten: // PRINT "HELLO WORLD!"
1481 goto $1^ten;
1482 }
1483 )cpp",
1484 "0: targets = {ten}, decl\n"
1485 "1: targets = {ten}\n"},
1486 // Simple templates.
1487 {R"cpp(
1488 template <class T> struct vector { using value_type = T; };
1489 template <> struct vector<bool> { using value_type = bool; };
1490 void foo() {
1491 $0^vector<int> $1^vi;
1492 $2^vector<bool> $3^vb;
1493 }
1494 )cpp",
1495 "0: targets = {vector<int>}\n"
1496 "1: targets = {vi}, decl\n"
1497 "2: targets = {vector<bool>}\n"
1498 "3: targets = {vb}, decl\n"},
1499 // Template type aliases.
1500 {R"cpp(
1501 template <class T> struct vector { using value_type = T; };
1502 template <> struct vector<bool> { using value_type = bool; };
1503 template <class T> using valias = vector<T>;
1504 void foo() {
1505 $0^valias<int> $1^vi;
1506 $2^valias<bool> $3^vb;
1507 }
1508 )cpp",
1509 "0: targets = {valias}\n"
1510 "1: targets = {vi}, decl\n"
1511 "2: targets = {valias}\n"
1512 "3: targets = {vb}, decl\n"},
1513 // Injected class name.
1514 {R"cpp(
1515 namespace foo {
1516 template <typename $0^T>
1517 class $1^Bar {
1518 ~$2^Bar();
1519 void $3^f($4^Bar);
1520 };
1521 }
1522 )cpp",
1523 "0: targets = {foo::Bar::T}, decl\n"
1524 "1: targets = {foo::Bar}, decl\n"
1525 "2: targets = {foo::Bar}\n"
1526 "3: targets = {foo::Bar::f}, decl\n"
1527 "4: targets = {foo::Bar}\n"},
1528 // MemberExpr should know their using declaration.
1529 {R"cpp(
1530 struct X { void func(int); };
1531 struct Y : X {
1532 using X::func;
1533 };
1534 void foo(Y y) {
1535 $0^y.$1^func(1);
1536 }
1537 )cpp",
1538 "0: targets = {y}\n"
1539 "1: targets = {Y::func}\n"},
1540 // DeclRefExpr should know their using declaration.
1541 {R"cpp(
1542 namespace ns { void bar(int); }
1543 using ns::bar;
1544
1545 void foo() {
1546 $0^bar(10);
1547 }
1548 )cpp",
1549 "0: targets = {bar}\n"},
1550 // References from a macro.
1551 {R"cpp(
1552 #define FOO a
1553 #define BAR b
1554
1555 void foo(int a, int b) {
1556 $0^FOO+$1^BAR;
1557 }
1558 )cpp",
1559 "0: targets = {a}\n"
1560 "1: targets = {b}\n"},
1561 // No references from implicit nodes.
1562 {R"cpp(
1563 struct vector {
1564 int *begin();
1565 int *end();
1566 };
1567
1568 void foo() {
1569 for (int $0^x : $1^vector()) {
1570 $2^x = 10;
1571 }
1572 }
1573 )cpp",
1574 "0: targets = {x}, decl\n"
1575 "1: targets = {vector}\n"
1576 "2: targets = {x}\n"},
1577 // Handle UnresolvedLookupExpr.
1578 {R"cpp(
1579 namespace ns1 { void func(char*); }
1580 namespace ns2 { void func(int*); }
1581 using namespace ns1;
1582 using namespace ns2;
1583
1584 template <class T>
1585 void foo(T t) {
1586 $0^func($1^t);
1587 }
1588 )cpp",
1589 "0: targets = {ns1::func, ns2::func}\n"
1590 "1: targets = {t}\n"},
1591 // Handle UnresolvedMemberExpr.
1592 {R"cpp(
1593 struct X {
1594 void func(char*);
1595 void func(int*);
1596 };
1597
1598 template <class T>
1599 void foo(X x, T t) {
1600 $0^x.$1^func($2^t);
1601 }
1602 )cpp",
1603 "0: targets = {x}\n"
1604 "1: targets = {X::func, X::func}\n"
1605 "2: targets = {t}\n"},
1606 // Handle DependentScopeDeclRefExpr.
1607 {R"cpp(
1608 template <class T>
1609 struct S {
1610 static int value;
1611 };
1612
1613 template <class T>
1614 void foo() {
1615 $0^S<$1^T>::$2^value;
1616 }
1617 )cpp",
1618 "0: targets = {S}\n"
1619 "1: targets = {T}\n"
1620 "2: targets = {S::value}, qualifier = 'S<T>::'\n"},
1621 // Handle CXXDependentScopeMemberExpr.
1622 {R"cpp(
1623 template <class T>
1624 struct S {
1625 int value;
1626 };
1627
1628 template <class T>
1629 void foo(S<T> t) {
1630 $0^t.$1^value;
1631 }
1632 )cpp",
1633 "0: targets = {t}\n"
1634 "1: targets = {S::value}\n"},
1635 // Type template parameters.
1636 {R"cpp(
1637 template <class T>
1638 void foo() {
1639 static_cast<$0^T>(0);
1640 $1^T();
1641 $2^T $3^t;
1642 }
1643 )cpp",
1644 "0: targets = {T}\n"
1645 "1: targets = {T}\n"
1646 "2: targets = {T}\n"
1647 "3: targets = {t}, decl\n"},
1648 // Non-type template parameters.
1649 {R"cpp(
1650 template <int I>
1651 void foo() {
1652 int $0^x = $1^I;
1653 }
1654 )cpp",
1655 "0: targets = {x}, decl\n"
1656 "1: targets = {I}\n"},
1657 // Template template parameters.
1658 {R"cpp(
1659 template <class T> struct vector {};
1660
1661 template <template<class> class TT, template<class> class ...TP>
1662 void foo() {
1663 $0^TT<int> $1^x;
1664 $2^foo<$3^TT>();
1665 $4^foo<$5^vector>();
1666 $6^foo<$7^TP...>();
1667 }
1668 )cpp",
1669 "0: targets = {TT}\n"
1670 "1: targets = {x}, decl\n"
1671 "2: targets = {foo}\n"
1672 "3: targets = {TT}\n"
1673 "4: targets = {foo}\n"
1674 "5: targets = {vector}\n"
1675 "6: targets = {foo}\n"
1676 "7: targets = {TP}\n"},
1677 // Non-type template parameters with declarations.
1678 {R"cpp(
1679 int func();
1680 template <int(*)()> struct wrapper {};
1681
1682 template <int(*FuncParam)()>
1683 void foo() {
1684 $0^wrapper<$1^func> $2^w;
1685 $3^FuncParam();
1686 }
1687 )cpp",
1688 "0: targets = {wrapper<&func>}\n"
1689 "1: targets = {func}\n"
1690 "2: targets = {w}, decl\n"
1691 "3: targets = {FuncParam}\n"},
1692 // declaration references.
1693 {R"cpp(
1694 namespace ns {}
1695 class S {};
1696 void foo() {
1697 class $0^Foo { $1^Foo(); ~$2^Foo(); int $3^field; };
1698 int $4^Var;
1699 enum $5^E { $6^ABC };
1700 typedef int $7^INT;
1701 using $8^INT2 = int;
1702 namespace $9^NS = $10^ns;
1703 }
1704 )cpp",
1705 "0: targets = {Foo}, decl\n"
1706 "1: targets = {foo()::Foo::Foo}, decl\n"
1707 "2: targets = {Foo}\n"
1708 "3: targets = {foo()::Foo::field}, decl\n"
1709 "4: targets = {Var}, decl\n"
1710 "5: targets = {E}, decl\n"
1711 "6: targets = {foo()::ABC}, decl\n"
1712 "7: targets = {INT}, decl\n"
1713 "8: targets = {INT2}, decl\n"
1714 "9: targets = {NS}, decl\n"
1715 "10: targets = {ns}\n"},
1716 // User-defined conversion operator.
1717 {R"cpp(
1718 void foo() {
1719 class $0^Bar {};
1720 class $1^Foo {
1721 public:
1722 // FIXME: This should have only one reference to Bar.
1723 $2^operator $3^$4^Bar();
1724 };
1725
1726 $5^Foo $6^f;
1727 $7^f.$8^operator $9^Bar();
1728 }
1729 )cpp",
1730 "0: targets = {Bar}, decl\n"
1731 "1: targets = {Foo}, decl\n"
1732 "2: targets = {foo()::Foo::operator Bar}, decl\n"
1733 "3: targets = {Bar}\n"
1734 "4: targets = {Bar}\n"
1735 "5: targets = {Foo}\n"
1736 "6: targets = {f}, decl\n"
1737 "7: targets = {f}\n"
1738 "8: targets = {foo()::Foo::operator Bar}\n"
1739 "9: targets = {Bar}\n"},
1740 // Destructor.
1741 {R"cpp(
1742 void foo() {
1743 class $0^Foo {
1744 public:
1745 ~$1^Foo() {}
1746
1747 void $2^destructMe() {
1748 this->~$3^Foo();
1749 }
1750 };
1751
1752 $4^Foo $5^f;
1753 $6^f.~ /*...*/ $7^Foo();
1754 }
1755 )cpp",
1756 "0: targets = {Foo}, decl\n"
1757 // FIXME: It's better to target destructor's FunctionDecl instead of
1758 // the type itself (similar to constructor).
1759 "1: targets = {Foo}\n"
1760 "2: targets = {foo()::Foo::destructMe}, decl\n"
1761 "3: targets = {Foo}\n"
1762 "4: targets = {Foo}\n"
1763 "5: targets = {f}, decl\n"
1764 "6: targets = {f}\n"
1765 "7: targets = {Foo}\n"},
1766 // cxx constructor initializer.
1767 {R"cpp(
1768 class Base {};
1769 void foo() {
1770 // member initializer
1771 class $0^X {
1772 int $1^abc;
1773 $2^X(): $3^abc() {}
1774 };
1775 // base initializer
1776 class $4^Derived : public $5^Base {
1777 $6^Base $7^B;
1778 $8^Derived() : $9^Base() {}
1779 };
1780 // delegating initializer
1781 class $10^Foo {
1782 $11^Foo(int);
1783 $12^Foo(): $13^Foo(111) {}
1784 };
1785 }
1786 )cpp",
1787 "0: targets = {X}, decl\n"
1788 "1: targets = {foo()::X::abc}, decl\n"
1789 "2: targets = {foo()::X::X}, decl\n"
1790 "3: targets = {foo()::X::abc}\n"
1791 "4: targets = {Derived}, decl\n"
1792 "5: targets = {Base}\n"
1793 "6: targets = {Base}\n"
1794 "7: targets = {foo()::Derived::B}, decl\n"
1795 "8: targets = {foo()::Derived::Derived}, decl\n"
1796 "9: targets = {Base}\n"
1797 "10: targets = {Foo}, decl\n"
1798 "11: targets = {foo()::Foo::Foo}, decl\n"
1799 "12: targets = {foo()::Foo::Foo}, decl\n"
1800 "13: targets = {Foo}\n"},
1801 // Anonymous entities should not be reported.
1802 {
1803 R"cpp(
1804 void foo() {
1805 $0^class {} $1^x;
1806 int (*$2^fptr)(int $3^a, int) = nullptr;
1807 }
1808 )cpp",
1809 "0: targets = {(unnamed)}\n"
1810 "1: targets = {x}, decl\n"
1811 "2: targets = {fptr}, decl\n"
1812 "3: targets = {a}, decl\n"},
1813 // Namespace aliases should be handled properly.
1814 {
1815 R"cpp(
1816 namespace ns { struct Type {}; }
1817 namespace alias = ns;
1818 namespace rec_alias = alias;
1819
1820 void foo() {
1821 $0^ns::$1^Type $2^a;
1822 $3^alias::$4^Type $5^b;
1823 $6^rec_alias::$7^Type $8^c;
1824 }
1825 )cpp",
1826 "0: targets = {ns}\n"
1827 "1: targets = {ns::Type}, qualifier = 'ns::'\n"
1828 "2: targets = {a}, decl\n"
1829 "3: targets = {alias}\n"
1830 "4: targets = {ns::Type}, qualifier = 'alias::'\n"
1831 "5: targets = {b}, decl\n"
1832 "6: targets = {rec_alias}\n"
1833 "7: targets = {ns::Type}, qualifier = 'rec_alias::'\n"
1834 "8: targets = {c}, decl\n"},
1835 // Handle SizeOfPackExpr.
1836 {
1837 R"cpp(
1838 template <typename... E>
1839 void foo() {
1840 constexpr int $0^size = sizeof...($1^E);
1841 };
1842 )cpp",
1843 "0: targets = {size}, decl\n"
1844 "1: targets = {E}\n"},
1845 // Class template argument deduction
1846 {
1847 R"cpp(
1848 template <typename T>
1849 struct Test {
1850 Test(T);
1851 };
1852 void foo() {
1853 $0^Test $1^a(5);
1854 }
1855 )cpp",
1856 "0: targets = {Test}\n"
1857 "1: targets = {a}, decl\n"},
1858 // Templates
1859 {R"cpp(
1860 namespace foo {
1861 template <typename $0^T>
1862 class $1^Bar {};
1863 }
1864 )cpp",
1865 "0: targets = {foo::Bar::T}, decl\n"
1866 "1: targets = {foo::Bar}, decl\n"},
1867 // Templates
1868 {R"cpp(
1869 namespace foo {
1870 template <typename $0^T>
1871 void $1^func();
1872 }
1873 )cpp",
1874 "0: targets = {T}, decl\n"
1875 "1: targets = {foo::func}, decl\n"},
1876 // Templates
1877 {R"cpp(
1878 namespace foo {
1879 template <typename $0^T>
1880 $1^T $2^x;
1881 }
1882 )cpp",
1883 "0: targets = {foo::T}, decl\n"
1884 "1: targets = {foo::T}\n"
1885 "2: targets = {foo::x}, decl\n"},
1886 // Templates
1887 {R"cpp(
1888 template<typename T> class vector {};
1889 namespace foo {
1890 template <typename $0^T>
1891 using $1^V = $2^vector<$3^T>;
1892 }
1893 )cpp",
1894 "0: targets = {foo::T}, decl\n"
1895 "1: targets = {foo::V}, decl\n"
1896 "2: targets = {vector}\n"
1897 "3: targets = {foo::T}\n"},
1898 // Concept
1899 {
1900 R"cpp(
1901 template <typename T>
1902 concept Drawable = requires (T t) { t.draw(); };
1903
1904 namespace foo {
1905 template <typename $0^T> requires $1^Drawable<$2^T>
1906 void $3^bar($4^T $5^t) {
1907 $6^t.$7^draw();
1908 }
1909 }
1910 )cpp",
1911 "0: targets = {T}, decl\n"
1912 "1: targets = {Drawable}\n"
1913 "2: targets = {T}\n"
1914 "3: targets = {foo::bar}, decl\n"
1915 "4: targets = {T}\n"
1916 "5: targets = {t}, decl\n"
1917 "6: targets = {t}\n"
1918 "7: targets = {}\n"},
1919 // Objective-C: instance variables
1920 {
1921 R"cpp(
1922 @interface I {
1923 @public
1924 I *_z;
1925 }
1926 @end
1927 I *f;
1928 void foo() {
1929 $0^f->$1^_z = 0;
1930 }
1931 )cpp",
1932 "0: targets = {f}\n"
1933 "1: targets = {I::_z}\n"},
1934 // Objective-C: properties
1935 {
1936 R"cpp(
1937 @interface I {}
1938 @property(retain) I* x;
1939 @property(retain) I* y;
1940 @end
1941 I *f;
1942 void foo() {
1943 $0^f.$1^x.$2^y = 0;
1944 }
1945 )cpp",
1946 "0: targets = {f}\n"
1947 "1: targets = {I::x}\n"
1948 "2: targets = {I::y}\n"},
1949 // Objective-C: implicit properties
1950 {
1951 R"cpp(
1952 @interface I {}
1953 -(I*)x;
1954 -(void)setY:(I*)y;
1955 @end
1956 I *f;
1957 void foo() {
1958 $0^f.$1^x.$2^y = 0;
1959 }
1960 )cpp",
1961 "0: targets = {f}\n"
1962 "1: targets = {I::x}\n"
1963 "2: targets = {I::setY:}\n"},
1964 // Objective-C: class properties
1965 {
1966 R"cpp(
1967 @interface I {}
1968 @property(class) I *x;
1969 @end
1970 id local;
1971 void foo() {
1972 $0^I.$1^x = 0;
1973 $2^local = $3^I.$4^x;
1974 }
1975 )cpp",
1976 "0: targets = {I}\n"
1977 "1: targets = {I::setX:}\n"
1978 "2: targets = {local}\n"
1979 "3: targets = {I}\n"
1980 "4: targets = {I::x}\n"},
1981 // Objective-C: implicit class properties
1982 {
1983 R"cpp(
1984 @interface I {}
1985 +(I*)x;
1986 +(void)setX:(I*)x;
1987 @end
1988 id local;
1989 void foo() {
1990 $0^I.$1^x = 0;
1991 $2^local = $3^I.$4^x;
1992 }
1993 )cpp",
1994 "0: targets = {I}\n"
1995 "1: targets = {I::setX:}\n"
1996 "2: targets = {local}\n"
1997 "3: targets = {I}\n"
1998 "4: targets = {I::x}\n"},
1999 {// Objective-C: methods
2000 R"cpp(
2001 @interface I
2002 -(void) a:(int)x b:(int)y;
2003 @end
2004 void foo(I *i) {
2005 [$0^i $1^a:1 b:2];
2006 }
2007 )cpp",
2008 "0: targets = {i}\n"
2009 "1: targets = {I::a:b:}\n"},
2010 {// Objective-C: protocols
2011 R"cpp(
2012 @interface I
2013 @end
2014 @protocol P
2015 @end
2016 void foo() {
2017 $0^I<$1^P> *$2^x;
2018 }
2019 )cpp",
2020 "0: targets = {I}\n"
2021 "1: targets = {P}\n"
2022 "2: targets = {x}, decl\n"},
2023
2024 // Designated initializers.
2025 {R"cpp(
2026 void foo() {
2027 struct $0^Foo {
2028 int $1^Bar;
2029 };
2030 $2^Foo $3^f { .$4^Bar = 42 };
2031 }
2032 )cpp",
2033 "0: targets = {Foo}, decl\n"
2034 "1: targets = {foo()::Foo::Bar}, decl\n"
2035 "2: targets = {Foo}\n"
2036 "3: targets = {f}, decl\n"
2037 "4: targets = {foo()::Foo::Bar}\n"},
2038 {R"cpp(
2039 void foo() {
2040 struct $0^Baz {
2041 int $1^Field;
2042 };
2043 struct $2^Bar {
2044 $3^Baz $4^Foo;
2045 };
2046 $5^Bar $6^bar { .$7^Foo.$8^Field = 42 };
2047 }
2048 )cpp",
2049 "0: targets = {Baz}, decl\n"
2050 "1: targets = {foo()::Baz::Field}, decl\n"
2051 "2: targets = {Bar}, decl\n"
2052 "3: targets = {Baz}\n"
2053 "4: targets = {foo()::Bar::Foo}, decl\n"
2054 "5: targets = {Bar}\n"
2055 "6: targets = {bar}, decl\n"
2056 "7: targets = {foo()::Bar::Foo}\n"
2057 "8: targets = {foo()::Baz::Field}\n"},
2058 {R"cpp(
2059 template<typename T>
2060 void crash(T);
2061 template<typename T>
2062 void foo() {
2063 $0^crash({.$1^x = $2^T()});
2064 }
2065 )cpp",
2066 "0: targets = {crash}\n"
2067 "1: targets = {}\n"
2068 "2: targets = {T}\n"},
2069 // unknown template name should not crash.
2070 {R"cpp(
2071 template <template <typename> typename T>
2072 struct Base {};
2073 namespace foo {
2074 template <typename $0^T>
2075 struct $1^Derive : $2^Base<$3^T::template $4^Unknown> {};
2076 }
2077 )cpp",
2078 "0: targets = {foo::Derive::T}, decl\n"
2079 "1: targets = {foo::Derive}, decl\n"
2080 "2: targets = {Base}\n"
2081 "3: targets = {foo::Derive::T}\n"
2082 "4: targets = {}, qualifier = 'T::'\n"},
2083 // deduction guide
2084 {R"cpp(
2085 namespace foo {
2086 template <typename $0^T>
2087 struct $1^Test {
2088 template <typename $2^I>
2089 $3^Test($4^I);
2090 };
2091 template <typename $5^I>
2092 $6^Test($7^I) -> $8^Test<typename $9^I::$10^type>;
2093 }
2094 )cpp",
2095 "0: targets = {T}, decl\n"
2096 "1: targets = {foo::Test}, decl\n"
2097 "2: targets = {I}, decl\n"
2098 "3: targets = {foo::Test::Test<T>}, decl\n"
2099 "4: targets = {I}\n"
2100 "5: targets = {I}, decl\n"
2101 "6: targets = {foo::Test}\n"
2102 "7: targets = {I}\n"
2103 "8: targets = {foo::Test}\n"
2104 "9: targets = {I}\n"
2105 "10: targets = {}, qualifier = 'I::'\n"}};
2106
2107 for (const auto &C : Cases) {
2108 llvm::StringRef ExpectedCode = C.first;
2109 llvm::StringRef ExpectedRefs = C.second;
2110
2111 auto Actual =
2112 annotateReferencesInFoo(Code: llvm::Annotations(ExpectedCode).code());
2113 EXPECT_EQ(ExpectedCode, Actual.AnnotatedCode);
2114 EXPECT_EQ(ExpectedRefs, Actual.DumpedReferences) << ExpectedCode;
2115 }
2116}
2117
2118TEST_F(FindExplicitReferencesTest, AllRefs) {
2119 std::pair</*Code*/ llvm::StringRef, /*References*/ llvm::StringRef> Cases[] =
2120 {{R"cpp(
2121 @interface $0^MyClass
2122 @end
2123 @implementation $1^$2^MyClass
2124 @end
2125 )cpp",
2126 "0: targets = {MyClass}, decl\n"
2127 "1: targets = {MyClass}\n"
2128 "2: targets = {MyClass}, decl\n"},
2129 {R"cpp(
2130 @interface $0^MyClass
2131 @end
2132 @interface $1^MyClass ($2^Category)
2133 @end
2134 @implementation $3^MyClass ($4^$5^Category)
2135 @end
2136 )cpp",
2137 "0: targets = {MyClass}, decl\n"
2138 "1: targets = {MyClass}\n"
2139 "2: targets = {Category}, decl\n"
2140 "3: targets = {MyClass}\n"
2141 "4: targets = {Category}\n"
2142 "5: targets = {Category}, decl\n"}};
2143
2144 for (const auto &C : Cases) {
2145 llvm::StringRef ExpectedCode = C.first;
2146 llvm::StringRef ExpectedRefs = C.second;
2147
2148 auto Actual = annotateAllReferences(Code: llvm::Annotations(ExpectedCode).code());
2149 EXPECT_EQ(ExpectedCode, Actual.AnnotatedCode);
2150 EXPECT_EQ(ExpectedRefs, Actual.DumpedReferences) << ExpectedCode;
2151 }
2152}
2153
2154} // namespace
2155} // namespace clangd
2156} // namespace clang
2157

source code of clang-tools-extra/clangd/unittests/FindTargetTests.cpp