• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //===- unittest/Tooling/LookupTest.cpp ------------------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #include "TestVisitor.h"
11 #include "clang/Tooling/Core/Lookup.h"
12 using namespace clang;
13 
14 namespace {
15 struct GetDeclsVisitor : TestVisitor<GetDeclsVisitor> {
16   std::function<void(CallExpr *)> OnCall;
17   SmallVector<Decl *, 4> DeclStack;
18 
VisitCallExpr__anonba4e0e290111::GetDeclsVisitor19   bool VisitCallExpr(CallExpr *Expr) {
20     OnCall(Expr);
21     return true;
22   }
23 
TraverseDecl__anonba4e0e290111::GetDeclsVisitor24   bool TraverseDecl(Decl *D) {
25     DeclStack.push_back(D);
26     bool Ret = TestVisitor::TraverseDecl(D);
27     DeclStack.pop_back();
28     return Ret;
29   }
30 };
31 
TEST(LookupTest,replaceNestedName)32 TEST(LookupTest, replaceNestedName) {
33   GetDeclsVisitor Visitor;
34 
35   auto replaceCallExpr = [&](const CallExpr *Expr,
36                              StringRef ReplacementString) {
37     const auto *Callee = cast<DeclRefExpr>(Expr->getCallee()->IgnoreImplicit());
38     const ValueDecl *FD = Callee->getDecl();
39     return tooling::replaceNestedName(
40         Callee->getQualifier(), Visitor.DeclStack.back()->getDeclContext(), FD,
41         ReplacementString);
42   };
43 
44   Visitor.OnCall = [&](CallExpr *Expr) {
45     EXPECT_EQ("bar", replaceCallExpr(Expr, "::bar"));
46   };
47   Visitor.runOver("namespace a { void foo(); }\n"
48                   "namespace a { void f() { foo(); } }\n");
49 
50   Visitor.OnCall = [&](CallExpr *Expr) {
51     EXPECT_EQ("bar", replaceCallExpr(Expr, "::a::bar"));
52   };
53   Visitor.runOver("namespace a { void foo(); }\n"
54                   "namespace a { void f() { foo(); } }\n");
55 
56   Visitor.OnCall = [&](CallExpr *Expr) {
57     EXPECT_EQ("a::bar", replaceCallExpr(Expr, "::a::bar"));
58   };
59   Visitor.runOver("namespace a { void foo(); }\n"
60                   "namespace b { void f() { a::foo(); } }\n");
61 
62   Visitor.OnCall = [&](CallExpr *Expr) {
63     EXPECT_EQ("a::bar", replaceCallExpr(Expr, "::a::bar"));
64   };
65   Visitor.runOver("namespace a { void foo(); }\n"
66                   "namespace b { namespace a { void foo(); }\n"
67                   "void f() { a::foo(); } }\n");
68 
69   Visitor.OnCall = [&](CallExpr *Expr) {
70     EXPECT_EQ("c::bar", replaceCallExpr(Expr, "::a::c::bar"));
71   };
72   Visitor.runOver("namespace a { namespace b { void foo(); }\n"
73                   "void f() { b::foo(); } }\n");
74 
75   Visitor.OnCall = [&](CallExpr *Expr) {
76     EXPECT_EQ("bar", replaceCallExpr(Expr, "::a::bar"));
77   };
78   Visitor.runOver("namespace a { namespace b { void foo(); }\n"
79                   "void f() { b::foo(); } }\n");
80 
81   Visitor.OnCall = [&](CallExpr *Expr) {
82     EXPECT_EQ("bar", replaceCallExpr(Expr, "::bar"));
83   };
84   Visitor.runOver("void foo(); void f() { foo(); }\n");
85 
86   Visitor.OnCall = [&](CallExpr *Expr) {
87     EXPECT_EQ("::bar", replaceCallExpr(Expr, "::bar"));
88   };
89   Visitor.runOver("void foo(); void f() { ::foo(); }\n");
90 
91   Visitor.OnCall = [&](CallExpr *Expr) {
92     EXPECT_EQ("a::bar", replaceCallExpr(Expr, "::a::bar"));
93   };
94   Visitor.runOver("namespace a { void foo(); }\nvoid f() { a::foo(); }\n");
95 
96   Visitor.OnCall = [&](CallExpr *Expr) {
97     EXPECT_EQ("a::bar", replaceCallExpr(Expr, "::a::bar"));
98   };
99   Visitor.runOver("namespace a { int foo(); }\nauto f = a::foo();\n");
100 
101   Visitor.OnCall = [&](CallExpr *Expr) {
102     EXPECT_EQ("bar", replaceCallExpr(Expr, "::a::bar"));
103   };
104   Visitor.runOver(
105       "namespace a { int foo(); }\nusing a::foo;\nauto f = foo();\n");
106 }
107 
108 } // end anonymous namespace
109