1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | #include "clang/AST/ASTContext.h" |
19 | #include "MatchVerifier.h" |
20 | #include "clang/ASTMatchers/ASTMatchFinder.h" |
21 | #include "clang/ASTMatchers/ASTMatchers.h" |
22 | #include "clang/Tooling/Tooling.h" |
23 | #include "gtest/gtest.h" |
24 | |
25 | namespace clang { |
26 | namespace ast_matchers { |
27 | |
28 | |
29 | |
30 | TEST(MatchVerifier, ParseError) { |
31 | LocationVerifier<VarDecl> Verifier; |
32 | Verifier.expectLocation(1, 1); |
33 | EXPECT_FALSE(Verifier.match("int i", varDecl())); |
34 | } |
35 | |
36 | TEST(MatchVerifier, NoMatch) { |
37 | LocationVerifier<VarDecl> Verifier; |
38 | Verifier.expectLocation(1, 1); |
39 | EXPECT_FALSE(Verifier.match("int i;", recordDecl())); |
40 | } |
41 | |
42 | TEST(MatchVerifier, WrongType) { |
43 | LocationVerifier<RecordDecl> Verifier; |
44 | Verifier.expectLocation(1, 1); |
45 | EXPECT_FALSE(Verifier.match("int i;", varDecl())); |
46 | } |
47 | |
48 | TEST(LocationVerifier, WrongLocation) { |
49 | LocationVerifier<VarDecl> Verifier; |
50 | Verifier.expectLocation(1, 1); |
51 | EXPECT_FALSE(Verifier.match("int i;", varDecl())); |
52 | } |
53 | |
54 | TEST(RangeVerifier, WrongRange) { |
55 | RangeVerifier<VarDecl> Verifier; |
56 | Verifier.expectRange(1, 1, 1, 1); |
57 | EXPECT_FALSE(Verifier.match("int i;", varDecl())); |
58 | } |
59 | |
60 | class LabelDeclRangeVerifier : public RangeVerifier<LabelStmt> { |
61 | protected: |
62 | SourceRange getRange(const LabelStmt &Node) override { |
63 | return Node.getDecl()->getSourceRange(); |
64 | } |
65 | }; |
66 | |
67 | TEST(LabelDecl, Range) { |
68 | LabelDeclRangeVerifier Verifier; |
69 | Verifier.expectRange(1, 12, 1, 12); |
70 | EXPECT_TRUE(Verifier.match("void f() { l: return; }", labelStmt())); |
71 | } |
72 | |
73 | TEST(LabelStmt, Range) { |
74 | RangeVerifier<LabelStmt> Verifier; |
75 | Verifier.expectRange(1, 12, 1, 15); |
76 | EXPECT_TRUE(Verifier.match("void f() { l: return; }", labelStmt())); |
77 | } |
78 | |
79 | TEST(ParmVarDecl, KNRLocation) { |
80 | LocationVerifier<ParmVarDecl> Verifier; |
81 | Verifier.expectLocation(1, 8); |
82 | EXPECT_TRUE(Verifier.match("void f(i) {}", varDecl(), Lang_C)); |
83 | } |
84 | |
85 | TEST(ParmVarDecl, KNRRange) { |
86 | RangeVerifier<ParmVarDecl> Verifier; |
87 | Verifier.expectRange(1, 8, 1, 8); |
88 | EXPECT_TRUE(Verifier.match("void f(i) {}", varDecl(), Lang_C)); |
89 | } |
90 | |
91 | TEST(CXXNewExpr, ArrayRange) { |
92 | RangeVerifier<CXXNewExpr> Verifier; |
93 | Verifier.expectRange(1, 12, 1, 22); |
94 | EXPECT_TRUE(Verifier.match("void f() { new int[10]; }", cxxNewExpr())); |
95 | } |
96 | |
97 | TEST(CXXNewExpr, ParenRange) { |
98 | RangeVerifier<CXXNewExpr> Verifier; |
99 | Verifier.expectRange(1, 12, 1, 20); |
100 | EXPECT_TRUE(Verifier.match("void f() { new int(); }", cxxNewExpr())); |
101 | } |
102 | |
103 | TEST(MemberExpr, ImplicitMemberRange) { |
104 | RangeVerifier<MemberExpr> Verifier; |
105 | Verifier.expectRange(2, 30, 2, 30); |
106 | EXPECT_TRUE(Verifier.match("struct S { operator int() const; };\n" |
107 | "int foo(const S& s) { return s; }", |
108 | memberExpr())); |
109 | } |
110 | |
111 | class MemberExprArrowLocVerifier : public RangeVerifier<MemberExpr> { |
112 | protected: |
113 | SourceRange getRange(const MemberExpr &Node) override { |
114 | return Node.getOperatorLoc(); |
115 | } |
116 | }; |
117 | |
118 | TEST(MemberExpr, ArrowRange) { |
119 | MemberExprArrowLocVerifier Verifier; |
120 | Verifier.expectRange(2, 19, 2, 19); |
121 | EXPECT_TRUE(Verifier.match("struct S { int x; };\n" |
122 | "void foo(S *s) { s->x = 0; }", |
123 | memberExpr())); |
124 | } |
125 | |
126 | TEST(MemberExpr, MacroArrowRange) { |
127 | MemberExprArrowLocVerifier Verifier; |
128 | Verifier.expectRange(1, 24, 1, 24); |
129 | EXPECT_TRUE(Verifier.match("#define MEMBER(a, b) (a->b)\n" |
130 | "struct S { int x; };\n" |
131 | "void foo(S *s) { MEMBER(s, x) = 0; }", |
132 | memberExpr())); |
133 | } |
134 | |
135 | TEST(MemberExpr, ImplicitArrowRange) { |
136 | MemberExprArrowLocVerifier Verifier; |
137 | Verifier.expectRange(0, 0, 0, 0); |
138 | EXPECT_TRUE(Verifier.match("struct S { int x; void Test(); };\n" |
139 | "void S::Test() { x = 1; }", |
140 | memberExpr())); |
141 | } |
142 | |
143 | TEST(VarDecl, VMTypeFixedVarDeclRange) { |
144 | RangeVerifier<VarDecl> Verifier; |
145 | Verifier.expectRange(1, 1, 1, 23); |
146 | EXPECT_TRUE(Verifier.match("int a[(int)(void*)1234];", |
147 | varDecl(), Lang_C89)); |
148 | } |
149 | |
150 | TEST(TypeLoc, IntRange) { |
151 | RangeVerifier<TypeLoc> Verifier; |
152 | Verifier.expectRange(1, 1, 1, 1); |
153 | EXPECT_TRUE(Verifier.match("int a;", typeLoc())); |
154 | } |
155 | |
156 | TEST(TypeLoc, LongRange) { |
157 | RangeVerifier<TypeLoc> Verifier; |
158 | Verifier.expectRange(1, 1, 1, 1); |
159 | EXPECT_TRUE(Verifier.match("long a;", typeLoc())); |
160 | } |
161 | |
162 | TEST(TypeLoc, LongDoubleRange) { |
163 | RangeVerifier<TypeLoc> Verifier; |
164 | Verifier.expectRange(1, 1, 1, 6); |
165 | EXPECT_TRUE(Verifier.match("long double a;", typeLoc())); |
166 | } |
167 | |
168 | TEST(TypeLoc, DoubleLongRange) { |
169 | RangeVerifier<TypeLoc> Verifier; |
170 | Verifier.expectRange(1, 1, 1, 8); |
171 | EXPECT_TRUE(Verifier.match("double long a;", typeLoc())); |
172 | } |
173 | |
174 | TEST(TypeLoc, LongIntRange) { |
175 | RangeVerifier<TypeLoc> Verifier; |
176 | Verifier.expectRange(1, 1, 1, 6); |
177 | EXPECT_TRUE(Verifier.match("long int a;", typeLoc())); |
178 | } |
179 | |
180 | TEST(TypeLoc, IntLongRange) { |
181 | RangeVerifier<TypeLoc> Verifier; |
182 | Verifier.expectRange(1, 1, 1, 5); |
183 | EXPECT_TRUE(Verifier.match("int long a;", typeLoc())); |
184 | } |
185 | |
186 | TEST(TypeLoc, UnsignedIntRange) { |
187 | RangeVerifier<TypeLoc> Verifier; |
188 | Verifier.expectRange(1, 1, 1, 10); |
189 | EXPECT_TRUE(Verifier.match("unsigned int a;", typeLoc())); |
190 | } |
191 | |
192 | TEST(TypeLoc, IntUnsignedRange) { |
193 | RangeVerifier<TypeLoc> Verifier; |
194 | Verifier.expectRange(1, 1, 1, 5); |
195 | EXPECT_TRUE(Verifier.match("int unsigned a;", typeLoc())); |
196 | } |
197 | |
198 | TEST(TypeLoc, LongLongRange) { |
199 | RangeVerifier<TypeLoc> Verifier; |
200 | Verifier.expectRange(1, 1, 1, 6); |
201 | EXPECT_TRUE(Verifier.match("long long a;", typeLoc())); |
202 | } |
203 | |
204 | TEST(TypeLoc, UnsignedLongLongRange) { |
205 | RangeVerifier<TypeLoc> Verifier; |
206 | Verifier.expectRange(1, 1, 1, 15); |
207 | EXPECT_TRUE(Verifier.match("unsigned long long a;", typeLoc())); |
208 | } |
209 | |
210 | TEST(TypeLoc, LongUnsignedLongRange) { |
211 | RangeVerifier<TypeLoc> Verifier; |
212 | Verifier.expectRange(1, 1, 1, 15); |
213 | EXPECT_TRUE(Verifier.match("long unsigned long a;", typeLoc())); |
214 | } |
215 | |
216 | TEST(TypeLoc, LongLongUnsignedRange) { |
217 | RangeVerifier<TypeLoc> Verifier; |
218 | Verifier.expectRange(1, 1, 1, 11); |
219 | EXPECT_TRUE(Verifier.match("long long unsigned a;", typeLoc())); |
220 | } |
221 | |
222 | TEST(TypeLoc, ConstLongLongRange) { |
223 | RangeVerifier<TypeLoc> Verifier; |
224 | Verifier.expectRange(1, 7, 1, 12); |
225 | EXPECT_TRUE(Verifier.match("const long long a = 0;", typeLoc())); |
226 | } |
227 | |
228 | TEST(TypeLoc, LongConstLongRange) { |
229 | RangeVerifier<TypeLoc> Verifier; |
230 | Verifier.expectRange(1, 1, 1, 12); |
231 | EXPECT_TRUE(Verifier.match("long const long a = 0;", typeLoc())); |
232 | } |
233 | |
234 | TEST(TypeLoc, LongLongConstRange) { |
235 | RangeVerifier<TypeLoc> Verifier; |
236 | Verifier.expectRange(1, 1, 1, 6); |
237 | EXPECT_TRUE(Verifier.match("long long const a = 0;", typeLoc())); |
238 | } |
239 | |
240 | TEST(CXXConstructorDecl, NoRetFunTypeLocRange) { |
241 | RangeVerifier<CXXConstructorDecl> Verifier; |
242 | Verifier.expectRange(1, 11, 1, 13); |
243 | EXPECT_TRUE(Verifier.match("class C { C(); };", functionDecl())); |
244 | } |
245 | |
246 | TEST(CXXConstructorDecl, DefaultedCtorLocRange) { |
247 | RangeVerifier<CXXConstructorDecl> Verifier; |
248 | Verifier.expectRange(1, 11, 1, 23); |
249 | EXPECT_TRUE(Verifier.match("class C { C() = default; };", functionDecl())); |
250 | } |
251 | |
252 | TEST(CXXConstructorDecl, DeletedCtorLocRange) { |
253 | RangeVerifier<CXXConstructorDecl> Verifier; |
254 | Verifier.expectRange(1, 11, 1, 22); |
255 | EXPECT_TRUE(Verifier.match("class C { C() = delete; };", functionDecl())); |
256 | } |
257 | |
258 | TEST(CompoundLiteralExpr, CompoundVectorLiteralRange) { |
259 | RangeVerifier<CompoundLiteralExpr> Verifier; |
260 | Verifier.expectRange(2, 11, 2, 22); |
261 | EXPECT_TRUE(Verifier.match( |
262 | "typedef int int2 __attribute__((ext_vector_type(2)));\n" |
263 | "int2 i2 = (int2){1, 2};", compoundLiteralExpr())); |
264 | } |
265 | |
266 | TEST(CompoundLiteralExpr, ParensCompoundVectorLiteralRange) { |
267 | RangeVerifier<CompoundLiteralExpr> Verifier; |
268 | Verifier.expectRange(2, 20, 2, 31); |
269 | EXPECT_TRUE(Verifier.match( |
270 | "typedef int int2 __attribute__((ext_vector_type(2)));\n" |
271 | "constant int2 i2 = (int2)(1, 2);", |
272 | compoundLiteralExpr(), Lang_OpenCL)); |
273 | } |
274 | |
275 | TEST(InitListExpr, VectorLiteralListBraceRange) { |
276 | RangeVerifier<InitListExpr> Verifier; |
277 | Verifier.expectRange(2, 17, 2, 22); |
278 | EXPECT_TRUE(Verifier.match( |
279 | "typedef int int2 __attribute__((ext_vector_type(2)));\n" |
280 | "int2 i2 = (int2){1, 2};", initListExpr())); |
281 | } |
282 | |
283 | TEST(InitListExpr, VectorLiteralInitListParens) { |
284 | RangeVerifier<InitListExpr> Verifier; |
285 | Verifier.expectRange(2, 26, 2, 31); |
286 | EXPECT_TRUE(Verifier.match( |
287 | "typedef int int2 __attribute__((ext_vector_type(2)));\n" |
288 | "constant int2 i2 = (int2)(1, 2);", initListExpr(), Lang_OpenCL)); |
289 | } |
290 | |
291 | class TemplateAngleBracketLocRangeVerifier : public RangeVerifier<TypeLoc> { |
292 | protected: |
293 | SourceRange getRange(const TypeLoc &Node) override { |
294 | TemplateSpecializationTypeLoc T = |
295 | Node.getUnqualifiedLoc().castAs<TemplateSpecializationTypeLoc>(); |
296 | assert(!T.isNull()); |
297 | return SourceRange(T.getLAngleLoc(), T.getRAngleLoc()); |
298 | } |
299 | }; |
300 | |
301 | TEST(TemplateSpecializationTypeLoc, AngleBracketLocations) { |
302 | TemplateAngleBracketLocRangeVerifier Verifier; |
303 | Verifier.expectRange(2, 8, 2, 10); |
304 | EXPECT_TRUE(Verifier.match( |
305 | "template<typename T> struct A {}; struct B{}; void f(\n" |
306 | "const A<B>&);", |
307 | loc(templateSpecializationType()))); |
308 | } |
309 | |
310 | TEST(CXXNewExpr, TypeParenRange) { |
311 | RangeVerifier<CXXNewExpr> Verifier; |
312 | Verifier.expectRange(1, 10, 1, 18); |
313 | EXPECT_TRUE(Verifier.match("int* a = new (int);", cxxNewExpr())); |
314 | } |
315 | |
316 | class UnaryTransformTypeLocParensRangeVerifier : public RangeVerifier<TypeLoc> { |
317 | protected: |
318 | SourceRange getRange(const TypeLoc &Node) override { |
319 | UnaryTransformTypeLoc T = |
320 | Node.getUnqualifiedLoc().castAs<UnaryTransformTypeLoc>(); |
321 | assert(!T.isNull()); |
322 | return SourceRange(T.getLParenLoc(), T.getRParenLoc()); |
323 | } |
324 | }; |
325 | |
326 | TEST(UnaryTransformTypeLoc, ParensRange) { |
327 | UnaryTransformTypeLocParensRangeVerifier Verifier; |
328 | Verifier.expectRange(3, 26, 3, 28); |
329 | EXPECT_TRUE(Verifier.match( |
330 | "template <typename T>\n" |
331 | "struct S {\n" |
332 | "typedef __underlying_type(T) type;\n" |
333 | "};", |
334 | loc(unaryTransformType()))); |
335 | } |
336 | |
337 | TEST(CXXFunctionalCastExpr, SourceRange) { |
338 | RangeVerifier<CXXFunctionalCastExpr> Verifier; |
339 | Verifier.expectRange(2, 10, 2, 14); |
340 | EXPECT_TRUE(Verifier.match( |
341 | "int foo() {\n" |
342 | " return int{};\n" |
343 | "}", |
344 | cxxFunctionalCastExpr(), Lang_CXX11)); |
345 | } |
346 | |
347 | TEST(CXXConstructExpr, SourceRange) { |
348 | RangeVerifier<CXXConstructExpr> Verifier; |
349 | Verifier.expectRange(3, 14, 3, 19); |
350 | EXPECT_TRUE(Verifier.match( |
351 | "struct A { A(int, int); };\n" |
352 | "void f(A a);\n" |
353 | "void g() { f({0, 0}); }", |
354 | cxxConstructExpr(), Lang_CXX11)); |
355 | } |
356 | |
357 | TEST(CXXTemporaryObjectExpr, SourceRange) { |
358 | RangeVerifier<CXXTemporaryObjectExpr> Verifier; |
359 | Verifier.expectRange(2, 6, 2, 12); |
360 | EXPECT_TRUE(Verifier.match( |
361 | "struct A { A(int, int); };\n" |
362 | "A a( A{0, 0} );", |
363 | cxxTemporaryObjectExpr(), Lang_CXX11)); |
364 | } |
365 | |
366 | TEST(CXXUnresolvedConstructExpr, SourceRange) { |
367 | RangeVerifier<CXXUnresolvedConstructExpr> Verifier; |
368 | Verifier.expectRange(3, 10, 3, 12); |
369 | std::vector<std::string> Args; |
370 | Args.push_back("-fno-delayed-template-parsing"); |
371 | EXPECT_TRUE(Verifier.match( |
372 | "template <typename U>\n" |
373 | "U foo() {\n" |
374 | " return U{};\n" |
375 | "}", |
376 | cxxUnresolvedConstructExpr(), Args, Lang_CXX11)); |
377 | } |
378 | |
379 | TEST(UsingDecl, SourceRange) { |
380 | RangeVerifier<UsingDecl> Verifier; |
381 | Verifier.expectRange(2, 22, 2, 25); |
382 | EXPECT_TRUE(Verifier.match( |
383 | "class B { protected: int i; };\n" |
384 | "class D : public B { B::i; };", |
385 | usingDecl())); |
386 | } |
387 | |
388 | TEST(UnresolvedUsingValueDecl, SourceRange) { |
389 | RangeVerifier<UnresolvedUsingValueDecl> Verifier; |
390 | Verifier.expectRange(3, 3, 3, 6); |
391 | EXPECT_TRUE(Verifier.match( |
392 | "template <typename B>\n" |
393 | "class D : public B {\n" |
394 | " B::i;\n" |
395 | "};", |
396 | unresolvedUsingValueDecl())); |
397 | } |
398 | |
399 | TEST(FriendDecl, FriendNonMemberFunctionLocation) { |
400 | LocationVerifier<FriendDecl> Verifier; |
401 | Verifier.expectLocation(2, 13); |
402 | EXPECT_TRUE(Verifier.match("struct A {\n" |
403 | "friend void f();\n" |
404 | "};\n", |
405 | friendDecl())); |
406 | } |
407 | |
408 | TEST(FriendDecl, FriendNonMemberFunctionRange) { |
409 | RangeVerifier<FriendDecl> Verifier; |
410 | Verifier.expectRange(2, 1, 2, 15); |
411 | EXPECT_TRUE(Verifier.match("struct A {\n" |
412 | "friend void f();\n" |
413 | "};\n", |
414 | friendDecl())); |
415 | } |
416 | |
417 | TEST(FriendDecl, FriendNonMemberFunctionDefinitionLocation) { |
418 | LocationVerifier<FriendDecl> Verifier; |
419 | Verifier.expectLocation(2, 12); |
420 | EXPECT_TRUE(Verifier.match("struct A {\n" |
421 | "friend int f() { return 0; }\n" |
422 | "};\n", |
423 | friendDecl())); |
424 | } |
425 | |
426 | TEST(FriendDecl, FriendNonMemberFunctionDefinitionRange) { |
427 | RangeVerifier<FriendDecl> Verifier; |
428 | Verifier.expectRange(2, 1, 2, 28); |
429 | EXPECT_TRUE(Verifier.match("struct A {\n" |
430 | "friend int f() { return 0; }\n" |
431 | "};\n", |
432 | friendDecl())); |
433 | } |
434 | |
435 | TEST(FriendDecl, FriendElaboratedTypeLocation) { |
436 | LocationVerifier<FriendDecl> Verifier; |
437 | Verifier.expectLocation(2, 8); |
438 | EXPECT_TRUE(Verifier.match("struct A {\n" |
439 | "friend class B;\n" |
440 | "};\n", |
441 | friendDecl())); |
442 | } |
443 | |
444 | TEST(FriendDecl, FriendElaboratedTypeRange) { |
445 | RangeVerifier<FriendDecl> Verifier; |
446 | Verifier.expectRange(2, 1, 2, 14); |
447 | EXPECT_TRUE(Verifier.match("struct A {\n" |
448 | "friend class B;\n" |
449 | "};\n", |
450 | friendDecl())); |
451 | } |
452 | |
453 | TEST(FriendDecl, FriendSimpleTypeLocation) { |
454 | LocationVerifier<FriendDecl> Verifier; |
455 | Verifier.expectLocation(3, 8); |
456 | EXPECT_TRUE(Verifier.match("class B;\n" |
457 | "struct A {\n" |
458 | "friend B;\n" |
459 | "};\n", |
460 | friendDecl(), Lang_CXX11)); |
461 | } |
462 | |
463 | TEST(FriendDecl, FriendSimpleTypeRange) { |
464 | RangeVerifier<FriendDecl> Verifier; |
465 | Verifier.expectRange(3, 1, 3, 8); |
466 | EXPECT_TRUE(Verifier.match("class B;\n" |
467 | "struct A {\n" |
468 | "friend B;\n" |
469 | "};\n", |
470 | friendDecl(), Lang_CXX11)); |
471 | } |
472 | |
473 | TEST(FriendDecl, FriendTemplateParameterLocation) { |
474 | LocationVerifier<FriendDecl> Verifier; |
475 | Verifier.expectLocation(3, 8); |
476 | EXPECT_TRUE(Verifier.match("template <typename T>\n" |
477 | "struct A {\n" |
478 | "friend T;\n" |
479 | "};\n", |
480 | friendDecl(), Lang_CXX11)); |
481 | } |
482 | |
483 | TEST(FriendDecl, FriendTemplateParameterRange) { |
484 | RangeVerifier<FriendDecl> Verifier; |
485 | Verifier.expectRange(3, 1, 3, 8); |
486 | EXPECT_TRUE(Verifier.match("template <typename T>\n" |
487 | "struct A {\n" |
488 | "friend T;\n" |
489 | "};\n", |
490 | friendDecl(), Lang_CXX11)); |
491 | } |
492 | |
493 | TEST(FriendDecl, FriendDecltypeLocation) { |
494 | LocationVerifier<FriendDecl> Verifier; |
495 | Verifier.expectLocation(4, 8); |
496 | EXPECT_TRUE(Verifier.match("struct A;\n" |
497 | "A foo();\n" |
498 | "struct A {\n" |
499 | "friend decltype(foo());\n" |
500 | "};\n", |
501 | friendDecl(), Lang_CXX11)); |
502 | } |
503 | |
504 | TEST(FriendDecl, FriendDecltypeRange) { |
505 | RangeVerifier<FriendDecl> Verifier; |
506 | Verifier.expectRange(4, 1, 4, 8); |
507 | EXPECT_TRUE(Verifier.match("struct A;\n" |
508 | "A foo();\n" |
509 | "struct A {\n" |
510 | "friend decltype(foo());\n" |
511 | "};\n", |
512 | friendDecl(), Lang_CXX11)); |
513 | } |
514 | |
515 | TEST(FriendDecl, FriendConstructorDestructorLocation) { |
516 | const std::string Code = "struct B {\n" |
517 | "B();\n" |
518 | "~B();\n" |
519 | "};\n" |
520 | "struct A {\n" |
521 | "friend B::B(), B::~B();\n" |
522 | "};\n"; |
523 | LocationVerifier<FriendDecl> ConstructorVerifier; |
524 | ConstructorVerifier.expectLocation(6, 11); |
525 | EXPECT_TRUE(ConstructorVerifier.match( |
526 | Code, friendDecl(has(cxxConstructorDecl(ofClass(hasName("B"))))))); |
527 | LocationVerifier<FriendDecl> DestructorVerifier; |
528 | DestructorVerifier.expectLocation(6, 19); |
529 | EXPECT_TRUE(DestructorVerifier.match( |
530 | Code, friendDecl(has(cxxDestructorDecl(ofClass(hasName("B"))))))); |
531 | } |
532 | |
533 | TEST(FriendDecl, FriendConstructorDestructorRange) { |
534 | const std::string Code = "struct B {\n" |
535 | "B();\n" |
536 | "~B();\n" |
537 | "};\n" |
538 | "struct A {\n" |
539 | "friend B::B(), B::~B();\n" |
540 | "};\n"; |
541 | RangeVerifier<FriendDecl> ConstructorVerifier; |
542 | ConstructorVerifier.expectRange(6, 1, 6, 13); |
543 | EXPECT_TRUE(ConstructorVerifier.match( |
544 | Code, friendDecl(has(cxxConstructorDecl(ofClass(hasName("B"))))))); |
545 | RangeVerifier<FriendDecl> DestructorVerifier; |
546 | DestructorVerifier.expectRange(6, 1, 6, 22); |
547 | EXPECT_TRUE(DestructorVerifier.match( |
548 | Code, friendDecl(has(cxxDestructorDecl(ofClass(hasName("B"))))))); |
549 | } |
550 | |
551 | TEST(FriendDecl, FriendTemplateFunctionLocation) { |
552 | LocationVerifier<FriendDecl> Verifier; |
553 | Verifier.expectLocation(3, 13); |
554 | EXPECT_TRUE(Verifier.match("struct A {\n" |
555 | "template <typename T>\n" |
556 | "friend void f();\n" |
557 | "};\n", |
558 | friendDecl())); |
559 | } |
560 | |
561 | TEST(FriendDecl, FriendTemplateFunctionRange) { |
562 | RangeVerifier<FriendDecl> Verifier; |
563 | Verifier.expectRange(2, 1, 3, 15); |
564 | EXPECT_TRUE(Verifier.match("struct A {\n" |
565 | "template <typename T>\n" |
566 | "friend void f();\n" |
567 | "};\n", |
568 | friendDecl())); |
569 | } |
570 | |
571 | TEST(FriendDecl, FriendTemplateClassLocation) { |
572 | LocationVerifier<FriendDecl> Verifier; |
573 | Verifier.expectLocation(3, 14); |
574 | EXPECT_TRUE(Verifier.match("struct A {\n" |
575 | "template <typename T>\n" |
576 | "friend class B;\n" |
577 | "};\n", |
578 | friendDecl())); |
579 | } |
580 | |
581 | TEST(FriendDecl, FriendTemplateClassRange) { |
582 | RangeVerifier<FriendDecl> Verifier; |
583 | Verifier.expectRange(2, 1, 3, 14); |
584 | EXPECT_TRUE(Verifier.match("struct A {\n" |
585 | "template <typename T>\n" |
586 | "friend class B;\n" |
587 | "};\n", |
588 | friendDecl())); |
589 | } |
590 | |
591 | TEST(FriendDecl, FriendInlineFunctionLocation) { |
592 | LocationVerifier<FriendDecl> Verifier; |
593 | Verifier.expectLocation(2, 19); |
594 | EXPECT_TRUE(Verifier.match("struct A {\n" |
595 | "int inline friend f() { return 0; }" |
596 | "};\n", |
597 | friendDecl())); |
598 | } |
599 | |
600 | TEST(FriendDecl, FriendInlineFunctionRange) { |
601 | RangeVerifier<FriendDecl> Verifier; |
602 | Verifier.expectRange(2, 1, 2, 35); |
603 | EXPECT_TRUE(Verifier.match("struct A {\n" |
604 | "int inline friend f() { return 0; }" |
605 | "};\n", |
606 | friendDecl(), Lang_CXX11)); |
607 | } |
608 | |
609 | TEST(FriendDecl, InstantiationSourceRange) { |
610 | RangeVerifier<FriendDecl> Verifier; |
611 | Verifier.expectRange(4, 3, 4, 35); |
612 | EXPECT_TRUE(Verifier.match( |
613 | "template <typename T> class S;\n" |
614 | "template<class T> void operator+(S<T> x);\n" |
615 | "template<class T> struct S {\n" |
616 | " friend void operator+<>(S<T> src);\n" |
617 | "};\n" |
618 | "void test(S<double> s) { +s; }", |
619 | friendDecl(hasParent(cxxRecordDecl(isTemplateInstantiation()))))); |
620 | } |
621 | |
622 | TEST(ObjCMessageExpr, CXXConstructExprRange) { |
623 | RangeVerifier<CXXConstructExpr> Verifier; |
624 | Verifier.expectRange(5, 25, 5, 27); |
625 | EXPECT_TRUE(Verifier.match( |
626 | "struct A { int a; };\n" |
627 | "@interface B {}\n" |
628 | "+ (void) f1: (A)arg;\n" |
629 | "@end\n" |
630 | "void f2() { A a; [B f1: (a)]; }\n", |
631 | cxxConstructExpr(), Lang_OBJCXX)); |
632 | } |
633 | |
634 | TEST(FunctionDecl, FunctionDeclWithThrowSpecification) { |
635 | RangeVerifier<FunctionDecl> Verifier; |
636 | Verifier.expectRange(1, 1, 1, 16); |
637 | EXPECT_TRUE(Verifier.match( |
638 | "void f() throw();\n", |
639 | functionDecl())); |
640 | } |
641 | |
642 | TEST(FunctionDecl, FunctionDeclWithNoExceptSpecification) { |
643 | RangeVerifier<FunctionDecl> Verifier; |
644 | Verifier.expectRange(1, 1, 1, 24); |
645 | EXPECT_TRUE(Verifier.match( |
646 | "void f() noexcept(false);\n", |
647 | functionDecl(), |
648 | Language::Lang_CXX11)); |
649 | } |
650 | |
651 | TEST(CXXMethodDecl, CXXMethodDeclWithThrowSpecification) { |
652 | RangeVerifier<FunctionDecl> Verifier; |
653 | Verifier.expectRange(2, 1, 2, 16); |
654 | EXPECT_TRUE(Verifier.match( |
655 | "class A {\n" |
656 | "void f() throw();\n" |
657 | "};\n", |
658 | functionDecl())); |
659 | } |
660 | |
661 | TEST(CXXMethodDecl, CXXMethodDeclWithNoExceptSpecification) { |
662 | RangeVerifier<FunctionDecl> Verifier; |
663 | Verifier.expectRange(2, 1, 2, 24); |
664 | EXPECT_TRUE(Verifier.match( |
665 | "class A {\n" |
666 | "void f() noexcept(false);\n" |
667 | "};\n", |
668 | functionDecl(), |
669 | Language::Lang_CXX11)); |
670 | } |
671 | |
672 | class ExceptionSpecRangeVerifier : public RangeVerifier<TypeLoc> { |
673 | protected: |
674 | SourceRange getRange(const TypeLoc &Node) override { |
675 | auto T = |
676 | Node.getUnqualifiedLoc().castAs<FunctionProtoTypeLoc>(); |
677 | assert(!T.isNull()); |
678 | return T.getExceptionSpecRange(); |
679 | } |
680 | }; |
681 | |
682 | class ParmVarExceptionSpecRangeVerifier : public RangeVerifier<ParmVarDecl> { |
683 | protected: |
684 | SourceRange getRange(const ParmVarDecl &Node) override { |
685 | if (const TypeSourceInfo *TSI = Node.getTypeSourceInfo()) { |
686 | TypeLoc TL = TSI->getTypeLoc(); |
687 | if (TL.getType()->isPointerType()) { |
688 | TL = TL.getNextTypeLoc().IgnoreParens(); |
689 | if (auto FPTL = TL.getAs<FunctionProtoTypeLoc>()) { |
690 | return FPTL.getExceptionSpecRange(); |
691 | } |
692 | } |
693 | } |
694 | return SourceRange(); |
695 | } |
696 | }; |
697 | |
698 | TEST(FunctionDecl, ExceptionSpecifications) { |
699 | ExceptionSpecRangeVerifier Verifier; |
700 | |
701 | Verifier.expectRange(1, 10, 1, 16); |
702 | EXPECT_TRUE(Verifier.match("void f() throw();\n", loc(functionType()))); |
703 | |
704 | Verifier.expectRange(1, 10, 1, 34); |
705 | EXPECT_TRUE(Verifier.match("void f() throw(void(void) throw());\n", |
706 | loc(functionType()))); |
707 | |
708 | Verifier.expectRange(1, 10, 1, 19); |
709 | std::vector<std::string> Args; |
710 | Args.push_back("-fms-extensions"); |
711 | EXPECT_TRUE(Verifier.match("void f() throw(...);\n", loc(functionType()), |
712 | Args, Language::Lang_CXX)); |
713 | |
714 | Verifier.expectRange(1, 10, 1, 10); |
715 | EXPECT_TRUE(Verifier.match("void f() noexcept;\n", loc(functionType()), |
716 | Language::Lang_CXX11)); |
717 | |
718 | Verifier.expectRange(1, 10, 1, 24); |
719 | EXPECT_TRUE(Verifier.match("void f() noexcept(false);\n", loc(functionType()), |
720 | Language::Lang_CXX11)); |
721 | |
722 | Verifier.expectRange(1, 10, 1, 32); |
723 | EXPECT_TRUE(Verifier.match("void f() noexcept(noexcept(1+1));\n", |
724 | loc(functionType()), Language::Lang_CXX11)); |
725 | |
726 | ParmVarExceptionSpecRangeVerifier Verifier2; |
727 | Verifier2.expectRange(1, 25, 1, 31); |
728 | EXPECT_TRUE(Verifier2.match("void g(void (*fp)(void) throw());\n", |
729 | parmVarDecl(hasType(pointerType(pointee( |
730 | parenType(innerType(functionType())))))))); |
731 | |
732 | Verifier2.expectRange(1, 25, 1, 38); |
733 | EXPECT_TRUE(Verifier2.match("void g(void (*fp)(void) noexcept(true));\n", |
734 | parmVarDecl(hasType(pointerType(pointee( |
735 | parenType(innerType(functionType())))))), |
736 | Language::Lang_CXX11)); |
737 | } |
738 | |
739 | } |
740 | } |
741 | |