• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //===- unittests/AST/DeclPrinterTest.cpp --- Declaration printer tests ----===//
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 // This file contains tests for Decl::print() and related methods.
11 //
12 // Search this file for WRONG to see test cases that are producing something
13 // completely wrong, invalid C++ or just misleading.
14 //
15 // These tests have a coding convention:
16 // * declaration to be printed is named 'A' unless it should have some special
17 // name (e.g., 'operator+');
18 // * additional helper declarations are 'Z', 'Y', 'X' and so on.
19 //
20 //===----------------------------------------------------------------------===//
21 
22 #include "clang/AST/ASTContext.h"
23 #include "clang/ASTMatchers/ASTMatchFinder.h"
24 #include "clang/Tooling/Tooling.h"
25 #include "llvm/ADT/SmallString.h"
26 #include "gtest/gtest.h"
27 
28 using namespace clang;
29 using namespace ast_matchers;
30 using namespace tooling;
31 
32 namespace {
33 
PrintDecl(raw_ostream & Out,const ASTContext * Context,const Decl * D)34 void PrintDecl(raw_ostream &Out, const ASTContext *Context, const Decl *D) {
35   PrintingPolicy Policy = Context->getPrintingPolicy();
36   Policy.TerseOutput = true;
37   D->print(Out, Policy, /*Indentation*/ 0, /*PrintInstantiation*/ false);
38 }
39 
40 class PrintMatch : public MatchFinder::MatchCallback {
41   SmallString<1024> Printed;
42   unsigned NumFoundDecls;
43 
44 public:
PrintMatch()45   PrintMatch() : NumFoundDecls(0) {}
46 
run(const MatchFinder::MatchResult & Result)47   void run(const MatchFinder::MatchResult &Result) override {
48     const Decl *D = Result.Nodes.getDeclAs<Decl>("id");
49     if (!D || D->isImplicit())
50       return;
51     NumFoundDecls++;
52     if (NumFoundDecls > 1)
53       return;
54 
55     llvm::raw_svector_ostream Out(Printed);
56     PrintDecl(Out, Result.Context, D);
57   }
58 
getPrinted() const59   StringRef getPrinted() const {
60     return Printed;
61   }
62 
getNumFoundDecls() const63   unsigned getNumFoundDecls() const {
64     return NumFoundDecls;
65   }
66 };
67 
PrintedDeclMatches(StringRef Code,const std::vector<std::string> & Args,const DeclarationMatcher & NodeMatch,StringRef ExpectedPrinted,StringRef FileName)68 ::testing::AssertionResult PrintedDeclMatches(
69                                   StringRef Code,
70                                   const std::vector<std::string> &Args,
71                                   const DeclarationMatcher &NodeMatch,
72                                   StringRef ExpectedPrinted,
73                                   StringRef FileName) {
74   PrintMatch Printer;
75   MatchFinder Finder;
76   Finder.addMatcher(NodeMatch, &Printer);
77   std::unique_ptr<FrontendActionFactory> Factory(
78       newFrontendActionFactory(&Finder));
79 
80   if (!runToolOnCodeWithArgs(Factory->create(), Code, Args, FileName))
81     return testing::AssertionFailure()
82       << "Parsing error in \"" << Code.str() << "\"";
83 
84   if (Printer.getNumFoundDecls() == 0)
85     return testing::AssertionFailure()
86         << "Matcher didn't find any declarations";
87 
88   if (Printer.getNumFoundDecls() > 1)
89     return testing::AssertionFailure()
90         << "Matcher should match only one declaration "
91            "(found " << Printer.getNumFoundDecls() << ")";
92 
93   if (Printer.getPrinted() != ExpectedPrinted)
94     return ::testing::AssertionFailure()
95       << "Expected \"" << ExpectedPrinted.str() << "\", "
96          "got \"" << Printer.getPrinted().str() << "\"";
97 
98   return ::testing::AssertionSuccess();
99 }
100 
PrintedDeclCXX98Matches(StringRef Code,StringRef DeclName,StringRef ExpectedPrinted)101 ::testing::AssertionResult PrintedDeclCXX98Matches(StringRef Code,
102                                                    StringRef DeclName,
103                                                    StringRef ExpectedPrinted) {
104   std::vector<std::string> Args(1, "-std=c++98");
105   return PrintedDeclMatches(Code,
106                             Args,
107                             namedDecl(hasName(DeclName)).bind("id"),
108                             ExpectedPrinted,
109                             "input.cc");
110 }
111 
PrintedDeclCXX98Matches(StringRef Code,const DeclarationMatcher & NodeMatch,StringRef ExpectedPrinted)112 ::testing::AssertionResult PrintedDeclCXX98Matches(
113                                   StringRef Code,
114                                   const DeclarationMatcher &NodeMatch,
115                                   StringRef ExpectedPrinted) {
116   std::vector<std::string> Args(1, "-std=c++98");
117   return PrintedDeclMatches(Code,
118                             Args,
119                             NodeMatch,
120                             ExpectedPrinted,
121                             "input.cc");
122 }
123 
PrintedDeclCXX11Matches(StringRef Code,StringRef DeclName,StringRef ExpectedPrinted)124 ::testing::AssertionResult PrintedDeclCXX11Matches(StringRef Code,
125                                                    StringRef DeclName,
126                                                    StringRef ExpectedPrinted) {
127   std::vector<std::string> Args(1, "-std=c++11");
128   return PrintedDeclMatches(Code,
129                             Args,
130                             namedDecl(hasName(DeclName)).bind("id"),
131                             ExpectedPrinted,
132                             "input.cc");
133 }
134 
PrintedDeclCXX11Matches(StringRef Code,const DeclarationMatcher & NodeMatch,StringRef ExpectedPrinted)135 ::testing::AssertionResult PrintedDeclCXX11Matches(
136                                   StringRef Code,
137                                   const DeclarationMatcher &NodeMatch,
138                                   StringRef ExpectedPrinted) {
139   std::vector<std::string> Args(1, "-std=c++11");
140   return PrintedDeclMatches(Code,
141                             Args,
142                             NodeMatch,
143                             ExpectedPrinted,
144                             "input.cc");
145 }
146 
PrintedDeclCXX11nonMSCMatches(StringRef Code,const DeclarationMatcher & NodeMatch,StringRef ExpectedPrinted)147 ::testing::AssertionResult PrintedDeclCXX11nonMSCMatches(
148                                   StringRef Code,
149                                   const DeclarationMatcher &NodeMatch,
150                                   StringRef ExpectedPrinted) {
151   std::vector<std::string> Args(1, "-std=c++11");
152   Args.push_back("-fno-delayed-template-parsing");
153   return PrintedDeclMatches(Code,
154                             Args,
155                             NodeMatch,
156                             ExpectedPrinted,
157                             "input.cc");
158 }
159 
160 ::testing::AssertionResult
PrintedDeclCXX1ZMatches(StringRef Code,const DeclarationMatcher & NodeMatch,StringRef ExpectedPrinted)161 PrintedDeclCXX1ZMatches(StringRef Code, const DeclarationMatcher &NodeMatch,
162                         StringRef ExpectedPrinted) {
163   std::vector<std::string> Args(1, "-std=c++1z");
164   return PrintedDeclMatches(Code,
165                             Args,
166                             NodeMatch,
167                             ExpectedPrinted,
168                             "input.cc");
169 }
170 
PrintedDeclObjCMatches(StringRef Code,const DeclarationMatcher & NodeMatch,StringRef ExpectedPrinted)171 ::testing::AssertionResult PrintedDeclObjCMatches(
172                                   StringRef Code,
173                                   const DeclarationMatcher &NodeMatch,
174                                   StringRef ExpectedPrinted) {
175   std::vector<std::string> Args(1, "");
176   return PrintedDeclMatches(Code,
177                             Args,
178                             NodeMatch,
179                             ExpectedPrinted,
180                             "input.m");
181 }
182 
183 } // unnamed namespace
184 
TEST(DeclPrinter,TestTypedef1)185 TEST(DeclPrinter, TestTypedef1) {
186   ASSERT_TRUE(PrintedDeclCXX98Matches(
187     "typedef int A;",
188     "A",
189     "typedef int A"));
190     // Should be: with semicolon
191 }
192 
TEST(DeclPrinter,TestTypedef2)193 TEST(DeclPrinter, TestTypedef2) {
194   ASSERT_TRUE(PrintedDeclCXX98Matches(
195     "typedef const char *A;",
196     "A",
197     "typedef const char *A"));
198     // Should be: with semicolon
199 }
200 
TEST(DeclPrinter,TestTypedef3)201 TEST(DeclPrinter, TestTypedef3) {
202   ASSERT_TRUE(PrintedDeclCXX98Matches(
203     "template <typename Y> class X {};"
204     "typedef X<int> A;",
205     "A",
206     "typedef X<int> A"));
207     // Should be: with semicolon
208 }
209 
TEST(DeclPrinter,TestTypedef4)210 TEST(DeclPrinter, TestTypedef4) {
211   ASSERT_TRUE(PrintedDeclCXX98Matches(
212     "namespace X { class Y {}; }"
213     "typedef X::Y A;",
214     "A",
215     "typedef X::Y A"));
216     // Should be: with semicolon
217 }
218 
TEST(DeclPrinter,TestNamespace1)219 TEST(DeclPrinter, TestNamespace1) {
220   ASSERT_TRUE(PrintedDeclCXX98Matches(
221     "namespace A { int B; }",
222     "A",
223     "namespace A {\n}"));
224     // Should be: with { ... }
225 }
226 
TEST(DeclPrinter,TestNamespace2)227 TEST(DeclPrinter, TestNamespace2) {
228   ASSERT_TRUE(PrintedDeclCXX11Matches(
229     "inline namespace A { int B; }",
230     "A",
231     "inline namespace A {\n}"));
232     // Should be: with { ... }
233 }
234 
TEST(DeclPrinter,TestNamespaceAlias1)235 TEST(DeclPrinter, TestNamespaceAlias1) {
236   ASSERT_TRUE(PrintedDeclCXX98Matches(
237     "namespace Z { }"
238     "namespace A = Z;",
239     "A",
240     "namespace A = Z"));
241     // Should be: with semicolon
242 }
243 
TEST(DeclPrinter,TestNamespaceAlias2)244 TEST(DeclPrinter, TestNamespaceAlias2) {
245   ASSERT_TRUE(PrintedDeclCXX98Matches(
246     "namespace X { namespace Y {} }"
247     "namespace A = X::Y;",
248     "A",
249     "namespace A = X::Y"));
250     // Should be: with semicolon
251 }
252 
TEST(DeclPrinter,TestCXXRecordDecl1)253 TEST(DeclPrinter, TestCXXRecordDecl1) {
254   ASSERT_TRUE(PrintedDeclCXX98Matches(
255     "class A { int a; };",
256     "A",
257     "class A {\n}"));
258     // Should be: with semicolon, with { ... }
259 }
260 
TEST(DeclPrinter,TestCXXRecordDecl2)261 TEST(DeclPrinter, TestCXXRecordDecl2) {
262   ASSERT_TRUE(PrintedDeclCXX98Matches(
263     "struct A { int a; };",
264     "A",
265     "struct A {\n}"));
266     // Should be: with semicolon, with { ... }
267 }
268 
TEST(DeclPrinter,TestCXXRecordDecl3)269 TEST(DeclPrinter, TestCXXRecordDecl3) {
270   ASSERT_TRUE(PrintedDeclCXX98Matches(
271     "union A { int a; };",
272     "A",
273     "union A {\n}"));
274     // Should be: with semicolon, with { ... }
275 }
276 
TEST(DeclPrinter,TestCXXRecordDecl4)277 TEST(DeclPrinter, TestCXXRecordDecl4) {
278   ASSERT_TRUE(PrintedDeclCXX98Matches(
279     "class Z { int a; };"
280     "class A : Z { int b; };",
281     "A",
282     "class A : Z {\n}"));
283     // Should be: with semicolon, with { ... }
284 }
285 
TEST(DeclPrinter,TestCXXRecordDecl5)286 TEST(DeclPrinter, TestCXXRecordDecl5) {
287   ASSERT_TRUE(PrintedDeclCXX98Matches(
288     "struct Z { int a; };"
289     "struct A : Z { int b; };",
290     "A",
291     "struct A : Z {\n}"));
292     // Should be: with semicolon, with { ... }
293 }
294 
TEST(DeclPrinter,TestCXXRecordDecl6)295 TEST(DeclPrinter, TestCXXRecordDecl6) {
296   ASSERT_TRUE(PrintedDeclCXX98Matches(
297     "class Z { int a; };"
298     "class A : public Z { int b; };",
299     "A",
300     "class A : public Z {\n}"));
301     // Should be: with semicolon, with { ... }
302 }
303 
TEST(DeclPrinter,TestCXXRecordDecl7)304 TEST(DeclPrinter, TestCXXRecordDecl7) {
305   ASSERT_TRUE(PrintedDeclCXX98Matches(
306     "class Z { int a; };"
307     "class A : protected Z { int b; };",
308     "A",
309     "class A : protected Z {\n}"));
310     // Should be: with semicolon, with { ... }
311 }
312 
TEST(DeclPrinter,TestCXXRecordDecl8)313 TEST(DeclPrinter, TestCXXRecordDecl8) {
314   ASSERT_TRUE(PrintedDeclCXX98Matches(
315     "class Z { int a; };"
316     "class A : private Z { int b; };",
317     "A",
318     "class A : private Z {\n}"));
319     // Should be: with semicolon, with { ... }
320 }
321 
TEST(DeclPrinter,TestCXXRecordDecl9)322 TEST(DeclPrinter, TestCXXRecordDecl9) {
323   ASSERT_TRUE(PrintedDeclCXX98Matches(
324     "class Z { int a; };"
325     "class A : virtual Z { int b; };",
326     "A",
327     "class A : virtual Z {\n}"));
328     // Should be: with semicolon, with { ... }
329 }
330 
TEST(DeclPrinter,TestCXXRecordDecl10)331 TEST(DeclPrinter, TestCXXRecordDecl10) {
332   ASSERT_TRUE(PrintedDeclCXX98Matches(
333     "class Z { int a; };"
334     "class A : virtual public Z { int b; };",
335     "A",
336     "class A : virtual public Z {\n}"));
337     // Should be: with semicolon, with { ... }
338 }
339 
TEST(DeclPrinter,TestCXXRecordDecl11)340 TEST(DeclPrinter, TestCXXRecordDecl11) {
341   ASSERT_TRUE(PrintedDeclCXX98Matches(
342     "class Z { int a; };"
343     "class Y : virtual public Z { int b; };"
344     "class A : virtual public Z, private Y { int c; };",
345     "A",
346     "class A : virtual public Z, private Y {\n}"));
347     // Should be: with semicolon, with { ... }
348 }
349 
TEST(DeclPrinter,TestFunctionDecl1)350 TEST(DeclPrinter, TestFunctionDecl1) {
351   ASSERT_TRUE(PrintedDeclCXX98Matches(
352     "void A();",
353     "A",
354     "void A()"));
355     // Should be: with semicolon
356 }
357 
TEST(DeclPrinter,TestFunctionDecl2)358 TEST(DeclPrinter, TestFunctionDecl2) {
359   ASSERT_TRUE(PrintedDeclCXX98Matches(
360     "void A() {}",
361     "A",
362     "void A()"));
363     // Should be: with semicolon
364 }
365 
TEST(DeclPrinter,TestFunctionDecl3)366 TEST(DeclPrinter, TestFunctionDecl3) {
367   ASSERT_TRUE(PrintedDeclCXX98Matches(
368     "void Z();"
369     "void A() { Z(); }",
370     "A",
371     "void A()"));
372     // Should be: with semicolon
373 }
374 
TEST(DeclPrinter,TestFunctionDecl4)375 TEST(DeclPrinter, TestFunctionDecl4) {
376   ASSERT_TRUE(PrintedDeclCXX98Matches(
377     "extern void A();",
378     "A",
379     "extern void A()"));
380     // Should be: with semicolon
381 }
382 
TEST(DeclPrinter,TestFunctionDecl5)383 TEST(DeclPrinter, TestFunctionDecl5) {
384   ASSERT_TRUE(PrintedDeclCXX98Matches(
385     "static void A();",
386     "A",
387     "static void A()"));
388     // Should be: with semicolon
389 }
390 
TEST(DeclPrinter,TestFunctionDecl6)391 TEST(DeclPrinter, TestFunctionDecl6) {
392   ASSERT_TRUE(PrintedDeclCXX98Matches(
393     "inline void A();",
394     "A",
395     "inline void A()"));
396     // Should be: with semicolon
397 }
398 
TEST(DeclPrinter,TestFunctionDecl7)399 TEST(DeclPrinter, TestFunctionDecl7) {
400   ASSERT_TRUE(PrintedDeclCXX11Matches(
401     "constexpr int A(int a);",
402     "A",
403     "constexpr int A(int a)"));
404     // Should be: with semicolon
405 }
406 
TEST(DeclPrinter,TestFunctionDecl8)407 TEST(DeclPrinter, TestFunctionDecl8) {
408   ASSERT_TRUE(PrintedDeclCXX98Matches(
409     "void A(int a);",
410     "A",
411     "void A(int a)"));
412     // Should be: with semicolon
413 }
414 
TEST(DeclPrinter,TestFunctionDecl9)415 TEST(DeclPrinter, TestFunctionDecl9) {
416   ASSERT_TRUE(PrintedDeclCXX98Matches(
417     "void A(...);",
418     "A",
419     "void A(...)"));
420     // Should be: with semicolon
421 }
422 
TEST(DeclPrinter,TestFunctionDecl10)423 TEST(DeclPrinter, TestFunctionDecl10) {
424   ASSERT_TRUE(PrintedDeclCXX98Matches(
425     "void A(int a, ...);",
426     "A",
427     "void A(int a, ...)"));
428     // Should be: with semicolon
429 }
430 
TEST(DeclPrinter,TestFunctionDecl11)431 TEST(DeclPrinter, TestFunctionDecl11) {
432   ASSERT_TRUE(PrintedDeclCXX98Matches(
433     "typedef long ssize_t;"
434     "typedef int *pInt;"
435     "void A(int a, pInt b, ssize_t c);",
436     "A",
437     "void A(int a, pInt b, ssize_t c)"));
438     // Should be: with semicolon
439 }
440 
TEST(DeclPrinter,TestFunctionDecl12)441 TEST(DeclPrinter, TestFunctionDecl12) {
442   ASSERT_TRUE(PrintedDeclCXX98Matches(
443     "void A(int a, int b = 0);",
444     "A",
445     "void A(int a, int b = 0)"));
446     // Should be: with semicolon
447 }
448 
TEST(DeclPrinter,TestFunctionDecl13)449 TEST(DeclPrinter, TestFunctionDecl13) {
450   ASSERT_TRUE(PrintedDeclCXX98Matches(
451     "void (*A(int a))(int b);",
452     "A",
453     "void (*A(int a))(int)"));
454     // Should be: with semicolon, with parameter name (?)
455 }
456 
TEST(DeclPrinter,TestFunctionDecl14)457 TEST(DeclPrinter, TestFunctionDecl14) {
458   ASSERT_TRUE(PrintedDeclCXX98Matches(
459     "template<typename T>"
460     "void A(T t) { }"
461     "template<>"
462     "void A(int N) { }",
463     functionDecl(hasName("A"), isExplicitTemplateSpecialization()).bind("id"),
464     "void A(int N)"));
465     // WRONG; Should be: "template <> void A(int N);"));
466 }
467 
468 
TEST(DeclPrinter,TestCXXConstructorDecl1)469 TEST(DeclPrinter, TestCXXConstructorDecl1) {
470   ASSERT_TRUE(PrintedDeclCXX98Matches(
471     "struct A {"
472     "  A();"
473     "};",
474     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
475     "A()"));
476 }
477 
TEST(DeclPrinter,TestCXXConstructorDecl2)478 TEST(DeclPrinter, TestCXXConstructorDecl2) {
479   ASSERT_TRUE(PrintedDeclCXX98Matches(
480     "struct A {"
481     "  A(int a);"
482     "};",
483     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
484     "A(int a)"));
485 }
486 
TEST(DeclPrinter,TestCXXConstructorDecl3)487 TEST(DeclPrinter, TestCXXConstructorDecl3) {
488   ASSERT_TRUE(PrintedDeclCXX98Matches(
489     "struct A {"
490     "  A(const A &a);"
491     "};",
492     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
493     "A(const A &a)"));
494 }
495 
TEST(DeclPrinter,TestCXXConstructorDecl4)496 TEST(DeclPrinter, TestCXXConstructorDecl4) {
497   ASSERT_TRUE(PrintedDeclCXX98Matches(
498     "struct A {"
499     "  A(const A &a, int = 0);"
500     "};",
501     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
502     "A(const A &a, int = 0)"));
503 }
504 
TEST(DeclPrinter,TestCXXConstructorDecl5)505 TEST(DeclPrinter, TestCXXConstructorDecl5) {
506   ASSERT_TRUE(PrintedDeclCXX11Matches(
507     "struct A {"
508     "  A(const A &&a);"
509     "};",
510     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
511     "A(const A &&a)"));
512 }
513 
TEST(DeclPrinter,TestCXXConstructorDecl6)514 TEST(DeclPrinter, TestCXXConstructorDecl6) {
515   ASSERT_TRUE(PrintedDeclCXX98Matches(
516     "struct A {"
517     "  explicit A(int a);"
518     "};",
519     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
520     "explicit A(int a)"));
521 }
522 
TEST(DeclPrinter,TestCXXConstructorDecl7)523 TEST(DeclPrinter, TestCXXConstructorDecl7) {
524   ASSERT_TRUE(PrintedDeclCXX11Matches(
525     "struct A {"
526     "  constexpr A();"
527     "};",
528     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
529     "constexpr A()"));
530 }
531 
TEST(DeclPrinter,TestCXXConstructorDecl8)532 TEST(DeclPrinter, TestCXXConstructorDecl8) {
533   ASSERT_TRUE(PrintedDeclCXX11Matches(
534     "struct A {"
535     "  A() = default;"
536     "};",
537     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
538     "A() = default"));
539 }
540 
TEST(DeclPrinter,TestCXXConstructorDecl9)541 TEST(DeclPrinter, TestCXXConstructorDecl9) {
542   ASSERT_TRUE(PrintedDeclCXX11Matches(
543     "struct A {"
544     "  A() = delete;"
545     "};",
546     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
547     "A() = delete"));
548 }
549 
TEST(DeclPrinter,TestCXXConstructorDecl10)550 TEST(DeclPrinter, TestCXXConstructorDecl10) {
551   ASSERT_TRUE(PrintedDeclCXX11Matches(
552     "template<typename... T>"
553     "struct A {"
554     "  A(const A &a);"
555     "};",
556     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
557     "A<T...>(const A<T...> &a)"));
558     // WRONG; Should be: "A(const A<T...> &a);"
559 }
560 
TEST(DeclPrinter,TestCXXConstructorDecl11)561 TEST(DeclPrinter, TestCXXConstructorDecl11) {
562   ASSERT_TRUE(PrintedDeclCXX11nonMSCMatches(
563     "template<typename... T>"
564     "struct A : public T... {"
565     "  A(T&&... ts) : T(ts)... {}"
566     "};",
567     cxxConstructorDecl(ofClass(hasName("A"))).bind("id"),
568     "A<T...>(T &&...ts) : T(ts)..."));
569     // WRONG; Should be: "A(T &&...ts) : T(ts)... {}"
570 }
571 
TEST(DeclPrinter,TestCXXDestructorDecl1)572 TEST(DeclPrinter, TestCXXDestructorDecl1) {
573   ASSERT_TRUE(PrintedDeclCXX98Matches(
574     "struct A {"
575     "  ~A();"
576     "};",
577     cxxDestructorDecl(ofClass(hasName("A"))).bind("id"),
578     "~A()"));
579 }
580 
TEST(DeclPrinter,TestCXXDestructorDecl2)581 TEST(DeclPrinter, TestCXXDestructorDecl2) {
582   ASSERT_TRUE(PrintedDeclCXX98Matches(
583     "struct A {"
584     "  virtual ~A();"
585     "};",
586     cxxDestructorDecl(ofClass(hasName("A"))).bind("id"),
587     "virtual ~A()"));
588 }
589 
TEST(DeclPrinter,TestCXXConversionDecl1)590 TEST(DeclPrinter, TestCXXConversionDecl1) {
591   ASSERT_TRUE(PrintedDeclCXX98Matches(
592     "struct A {"
593     "  operator int();"
594     "};",
595     cxxMethodDecl(ofClass(hasName("A"))).bind("id"),
596     "operator int()"));
597 }
598 
TEST(DeclPrinter,TestCXXConversionDecl2)599 TEST(DeclPrinter, TestCXXConversionDecl2) {
600   ASSERT_TRUE(PrintedDeclCXX98Matches(
601     "struct A {"
602     "  operator bool();"
603     "};",
604     cxxMethodDecl(ofClass(hasName("A"))).bind("id"),
605     "operator bool()"));
606 }
607 
TEST(DeclPrinter,TestCXXConversionDecl3)608 TEST(DeclPrinter, TestCXXConversionDecl3) {
609   ASSERT_TRUE(PrintedDeclCXX98Matches(
610     "struct Z {};"
611     "struct A {"
612     "  operator Z();"
613     "};",
614     cxxMethodDecl(ofClass(hasName("A"))).bind("id"),
615     "operator Z()"));
616 }
617 
TEST(DeclPrinter,TestCXXMethodDecl_AllocationFunction1)618 TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction1) {
619   ASSERT_TRUE(PrintedDeclCXX11Matches(
620     "namespace std { typedef decltype(sizeof(int)) size_t; }"
621     "struct Z {"
622     "  void *operator new(std::size_t);"
623     "};",
624     cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
625     "void *operator new(std::size_t)"));
626     // Should be: with semicolon
627 }
628 
TEST(DeclPrinter,TestCXXMethodDecl_AllocationFunction2)629 TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction2) {
630   ASSERT_TRUE(PrintedDeclCXX11Matches(
631     "namespace std { typedef decltype(sizeof(int)) size_t; }"
632     "struct Z {"
633     "  void *operator new[](std::size_t);"
634     "};",
635     cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
636     "void *operator new[](std::size_t)"));
637     // Should be: with semicolon
638 }
639 
TEST(DeclPrinter,TestCXXMethodDecl_AllocationFunction3)640 TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction3) {
641   ASSERT_TRUE(PrintedDeclCXX11Matches(
642     "struct Z {"
643     "  void operator delete(void *);"
644     "};",
645     cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
646     "void operator delete(void *) noexcept"));
647     // Should be: with semicolon, without noexcept?
648 }
649 
TEST(DeclPrinter,TestCXXMethodDecl_AllocationFunction4)650 TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction4) {
651   ASSERT_TRUE(PrintedDeclCXX98Matches(
652     "struct Z {"
653     "  void operator delete(void *);"
654     "};",
655     cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
656     "void operator delete(void *)"));
657     // Should be: with semicolon
658 }
659 
TEST(DeclPrinter,TestCXXMethodDecl_AllocationFunction5)660 TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction5) {
661   ASSERT_TRUE(PrintedDeclCXX11Matches(
662     "struct Z {"
663     "  void operator delete[](void *);"
664     "};",
665     cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
666     "void operator delete[](void *) noexcept"));
667     // Should be: with semicolon, without noexcept?
668 }
669 
TEST(DeclPrinter,TestCXXMethodDecl_Operator1)670 TEST(DeclPrinter, TestCXXMethodDecl_Operator1) {
671   const char *OperatorNames[] = {
672     "+",  "-",  "*",  "/",  "%",  "^",   "&",   "|",
673     "=",  "<",  ">",  "+=", "-=", "*=",  "/=",  "%=",
674     "^=", "&=", "|=", "<<", ">>", ">>=", "<<=", "==",  "!=",
675     "<=", ">=", "&&", "||",  ",", "->*",
676     "()", "[]"
677   };
678 
679   for (unsigned i = 0, e = llvm::array_lengthof(OperatorNames); i != e; ++i) {
680     SmallString<128> Code;
681     Code.append("struct Z { void operator");
682     Code.append(OperatorNames[i]);
683     Code.append("(Z z); };");
684 
685     SmallString<128> Expected;
686     Expected.append("void operator");
687     Expected.append(OperatorNames[i]);
688     Expected.append("(Z z)");
689     // Should be: with semicolon
690 
691     ASSERT_TRUE(PrintedDeclCXX98Matches(
692       Code,
693       cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
694       Expected));
695   }
696 }
697 
TEST(DeclPrinter,TestCXXMethodDecl_Operator2)698 TEST(DeclPrinter, TestCXXMethodDecl_Operator2) {
699   const char *OperatorNames[] = {
700     "~", "!", "++", "--", "->"
701   };
702 
703   for (unsigned i = 0, e = llvm::array_lengthof(OperatorNames); i != e; ++i) {
704     SmallString<128> Code;
705     Code.append("struct Z { void operator");
706     Code.append(OperatorNames[i]);
707     Code.append("(); };");
708 
709     SmallString<128> Expected;
710     Expected.append("void operator");
711     Expected.append(OperatorNames[i]);
712     Expected.append("()");
713     // Should be: with semicolon
714 
715     ASSERT_TRUE(PrintedDeclCXX98Matches(
716       Code,
717       cxxMethodDecl(ofClass(hasName("Z"))).bind("id"),
718       Expected));
719   }
720 }
721 
TEST(DeclPrinter,TestCXXMethodDecl1)722 TEST(DeclPrinter, TestCXXMethodDecl1) {
723   ASSERT_TRUE(PrintedDeclCXX98Matches(
724     "struct Z {"
725     "  void A(int a);"
726     "};",
727     "A",
728     "void A(int a)"));
729     // Should be: with semicolon
730 }
731 
TEST(DeclPrinter,TestCXXMethodDecl2)732 TEST(DeclPrinter, TestCXXMethodDecl2) {
733   ASSERT_TRUE(PrintedDeclCXX98Matches(
734     "struct Z {"
735     "  virtual void A(int a);"
736     "};",
737     "A",
738     "virtual void A(int a)"));
739     // Should be: with semicolon
740 }
741 
TEST(DeclPrinter,TestCXXMethodDecl3)742 TEST(DeclPrinter, TestCXXMethodDecl3) {
743   ASSERT_TRUE(PrintedDeclCXX98Matches(
744     "struct Z {"
745     "  virtual void A(int a);"
746     "};"
747     "struct ZZ : Z {"
748     "  void A(int a);"
749     "};",
750     "ZZ::A",
751     "void A(int a)"));
752     // Should be: with semicolon
753     // TODO: should we print "virtual"?
754 }
755 
TEST(DeclPrinter,TestCXXMethodDecl4)756 TEST(DeclPrinter, TestCXXMethodDecl4) {
757   ASSERT_TRUE(PrintedDeclCXX98Matches(
758     "struct Z {"
759     "  inline void A(int a);"
760     "};",
761     "A",
762     "inline void A(int a)"));
763     // Should be: with semicolon
764 }
765 
TEST(DeclPrinter,TestCXXMethodDecl5)766 TEST(DeclPrinter, TestCXXMethodDecl5) {
767   ASSERT_TRUE(PrintedDeclCXX98Matches(
768     "struct Z {"
769     "  virtual void A(int a) = 0;"
770     "};",
771     "A",
772     "virtual void A(int a) = 0"));
773     // Should be: with semicolon
774 }
775 
TEST(DeclPrinter,TestCXXMethodDecl_CVQualifier1)776 TEST(DeclPrinter, TestCXXMethodDecl_CVQualifier1) {
777   ASSERT_TRUE(PrintedDeclCXX98Matches(
778     "struct Z {"
779     "  void A(int a) const;"
780     "};",
781     "A",
782     "void A(int a) const"));
783     // Should be: with semicolon
784 }
785 
TEST(DeclPrinter,TestCXXMethodDecl_CVQualifier2)786 TEST(DeclPrinter, TestCXXMethodDecl_CVQualifier2) {
787   ASSERT_TRUE(PrintedDeclCXX98Matches(
788     "struct Z {"
789     "  void A(int a) volatile;"
790     "};",
791     "A",
792     "void A(int a) volatile"));
793     // Should be: with semicolon
794 }
795 
TEST(DeclPrinter,TestCXXMethodDecl_CVQualifier3)796 TEST(DeclPrinter, TestCXXMethodDecl_CVQualifier3) {
797   ASSERT_TRUE(PrintedDeclCXX98Matches(
798     "struct Z {"
799     "  void A(int a) const volatile;"
800     "};",
801     "A",
802     "void A(int a) const volatile"));
803     // Should be: with semicolon
804 }
805 
TEST(DeclPrinter,TestCXXMethodDecl_RefQualifier1)806 TEST(DeclPrinter, TestCXXMethodDecl_RefQualifier1) {
807   ASSERT_TRUE(PrintedDeclCXX11Matches(
808     "struct Z {"
809     "  void A(int a) &;"
810     "};",
811     "A",
812     "void A(int a) &"));
813     // Should be: with semicolon
814 }
815 
TEST(DeclPrinter,TestCXXMethodDecl_RefQualifier2)816 TEST(DeclPrinter, TestCXXMethodDecl_RefQualifier2) {
817   ASSERT_TRUE(PrintedDeclCXX11Matches(
818     "struct Z {"
819     "  void A(int a) &&;"
820     "};",
821     "A",
822     "void A(int a) &&"));
823     // Should be: with semicolon
824 }
825 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification1)826 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification1) {
827   ASSERT_TRUE(PrintedDeclCXX98Matches(
828     "struct Z {"
829     "  void A(int a) throw();"
830     "};",
831     "A",
832     "void A(int a) throw()"));
833     // Should be: with semicolon
834 }
835 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification2)836 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification2) {
837   ASSERT_TRUE(PrintedDeclCXX98Matches(
838     "struct Z {"
839     "  void A(int a) throw(int);"
840     "};",
841     "A",
842     "void A(int a) throw(int)"));
843     // Should be: with semicolon
844 }
845 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification3)846 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification3) {
847   ASSERT_TRUE(PrintedDeclCXX98Matches(
848     "class ZZ {};"
849     "struct Z {"
850     "  void A(int a) throw(ZZ, int);"
851     "};",
852     "A",
853     "void A(int a) throw(ZZ, int)"));
854     // Should be: with semicolon
855 }
856 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification4)857 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification4) {
858   ASSERT_TRUE(PrintedDeclCXX11Matches(
859     "struct Z {"
860     "  void A(int a) noexcept;"
861     "};",
862     "A",
863     "void A(int a) noexcept"));
864     // Should be: with semicolon
865 }
866 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification5)867 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification5) {
868   ASSERT_TRUE(PrintedDeclCXX11Matches(
869     "struct Z {"
870     "  void A(int a) noexcept(true);"
871     "};",
872     "A",
873     "void A(int a) noexcept(trueA(int a) noexcept(true)"));
874     // WRONG; Should be: "void A(int a) noexcept(true);"
875 }
876 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification6)877 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification6) {
878   ASSERT_TRUE(PrintedDeclCXX11Matches(
879     "struct Z {"
880     "  void A(int a) noexcept(1 < 2);"
881     "};",
882     "A",
883     "void A(int a) noexcept(1 < 2A(int a) noexcept(1 < 2)"));
884     // WRONG; Should be: "void A(int a) noexcept(1 < 2);"
885 }
886 
TEST(DeclPrinter,TestFunctionDecl_ExceptionSpecification7)887 TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification7) {
888   ASSERT_TRUE(PrintedDeclCXX11Matches(
889     "template<int N>"
890     "struct Z {"
891     "  void A(int a) noexcept(N < 2);"
892     "};",
893     "A",
894     "void A(int a) noexcept(N < 2A(int a) noexcept(N < 2)"));
895     // WRONG; Should be: "void A(int a) noexcept(N < 2);"
896 }
897 
TEST(DeclPrinter,TestVarDecl1)898 TEST(DeclPrinter, TestVarDecl1) {
899   ASSERT_TRUE(PrintedDeclCXX98Matches(
900     "char *const (*(*A)[5])(int);",
901     "A",
902     "char *const (*(*A)[5])(int)"));
903     // Should be: with semicolon
904 }
905 
TEST(DeclPrinter,TestVarDecl2)906 TEST(DeclPrinter, TestVarDecl2) {
907   ASSERT_TRUE(PrintedDeclCXX98Matches(
908     "void (*A)() throw(int);",
909     "A",
910     "void (*A)() throw(int)"));
911     // Should be: with semicolon
912 }
913 
TEST(DeclPrinter,TestVarDecl3)914 TEST(DeclPrinter, TestVarDecl3) {
915   ASSERT_TRUE(PrintedDeclCXX11Matches(
916     "void (*A)() noexcept;",
917     "A",
918     "void (*A)() noexcept"));
919     // Should be: with semicolon
920 }
921 
TEST(DeclPrinter,TestFieldDecl1)922 TEST(DeclPrinter, TestFieldDecl1) {
923   ASSERT_TRUE(PrintedDeclCXX98Matches(
924     "template<typename T>"
925     "struct Z { T A; };",
926     "A",
927     "T A"));
928     // Should be: with semicolon
929 }
930 
TEST(DeclPrinter,TestFieldDecl2)931 TEST(DeclPrinter, TestFieldDecl2) {
932   ASSERT_TRUE(PrintedDeclCXX98Matches(
933     "template<int N>"
934     "struct Z { int A[N]; };",
935     "A",
936     "int A[N]"));
937     // Should be: with semicolon
938 }
939 
TEST(DeclPrinter,TestClassTemplateDecl1)940 TEST(DeclPrinter, TestClassTemplateDecl1) {
941   ASSERT_TRUE(PrintedDeclCXX98Matches(
942     "template<typename T>"
943     "struct A { T a; };",
944     classTemplateDecl(hasName("A")).bind("id"),
945     "template <typename T> struct A {\n}"));
946     // Should be: with semicolon, with { ... }
947 }
948 
TEST(DeclPrinter,TestClassTemplateDecl2)949 TEST(DeclPrinter, TestClassTemplateDecl2) {
950   ASSERT_TRUE(PrintedDeclCXX98Matches(
951     "template<typename T = int>"
952     "struct A { T a; };",
953     classTemplateDecl(hasName("A")).bind("id"),
954     "template <typename T = int> struct A {\n}"));
955     // Should be: with semicolon, with { ... }
956 }
957 
TEST(DeclPrinter,TestClassTemplateDecl3)958 TEST(DeclPrinter, TestClassTemplateDecl3) {
959   ASSERT_TRUE(PrintedDeclCXX98Matches(
960     "template<class T>"
961     "struct A { T a; };",
962     classTemplateDecl(hasName("A")).bind("id"),
963     "template <class T> struct A {\n}"));
964     // Should be: with semicolon, with { ... }
965 }
966 
TEST(DeclPrinter,TestClassTemplateDecl4)967 TEST(DeclPrinter, TestClassTemplateDecl4) {
968   ASSERT_TRUE(PrintedDeclCXX98Matches(
969     "template<typename T, typename U>"
970     "struct A { T a; U b; };",
971     classTemplateDecl(hasName("A")).bind("id"),
972     "template <typename T, typename U> struct A {\n}"));
973     // Should be: with semicolon, with { ... }
974 }
975 
TEST(DeclPrinter,TestClassTemplateDecl5)976 TEST(DeclPrinter, TestClassTemplateDecl5) {
977   ASSERT_TRUE(PrintedDeclCXX98Matches(
978     "template<int N>"
979     "struct A { int a[N]; };",
980     classTemplateDecl(hasName("A")).bind("id"),
981     "template <int N> struct A {\n}"));
982     // Should be: with semicolon, with { ... }
983 }
984 
TEST(DeclPrinter,TestClassTemplateDecl6)985 TEST(DeclPrinter, TestClassTemplateDecl6) {
986   ASSERT_TRUE(PrintedDeclCXX98Matches(
987     "template<int N = 42>"
988     "struct A { int a[N]; };",
989     classTemplateDecl(hasName("A")).bind("id"),
990     "template <int N = 42> struct A {\n}"));
991     // Should be: with semicolon, with { ... }
992 }
993 
TEST(DeclPrinter,TestClassTemplateDecl7)994 TEST(DeclPrinter, TestClassTemplateDecl7) {
995   ASSERT_TRUE(PrintedDeclCXX98Matches(
996     "typedef int MyInt;"
997     "template<MyInt N>"
998     "struct A { int a[N]; };",
999     classTemplateDecl(hasName("A")).bind("id"),
1000     "template <MyInt N> struct A {\n}"));
1001     // Should be: with semicolon, with { ... }
1002 }
1003 
TEST(DeclPrinter,TestClassTemplateDecl8)1004 TEST(DeclPrinter, TestClassTemplateDecl8) {
1005   ASSERT_TRUE(PrintedDeclCXX98Matches(
1006     "template<template<typename U> class T> struct A { };",
1007     classTemplateDecl(hasName("A")).bind("id"),
1008     "template <template <typename U> class T> struct A {\n}"));
1009     // Should be: with semicolon, with { ... }
1010 }
1011 
TEST(DeclPrinter,TestClassTemplateDecl9)1012 TEST(DeclPrinter, TestClassTemplateDecl9) {
1013   ASSERT_TRUE(PrintedDeclCXX98Matches(
1014     "template<typename T> struct Z { };"
1015     "template<template<typename U> class T = Z> struct A { };",
1016     classTemplateDecl(hasName("A")).bind("id"),
1017     "template <template <typename U> class T> struct A {\n}"));
1018     // Should be: with semicolon, with { ... }
1019 }
1020 
TEST(DeclPrinter,TestClassTemplateDecl10)1021 TEST(DeclPrinter, TestClassTemplateDecl10) {
1022   ASSERT_TRUE(PrintedDeclCXX11Matches(
1023     "template<typename... T>"
1024     "struct A { int a; };",
1025     classTemplateDecl(hasName("A")).bind("id"),
1026     "template <typename ...T> struct A {\n}"));
1027     // Should be: with semicolon, with { ... }
1028 }
1029 
TEST(DeclPrinter,TestClassTemplateDecl11)1030 TEST(DeclPrinter, TestClassTemplateDecl11) {
1031   ASSERT_TRUE(PrintedDeclCXX11Matches(
1032     "template<typename... T>"
1033     "struct A : public T... { int a; };",
1034     classTemplateDecl(hasName("A")).bind("id"),
1035     "template <typename ...T> struct A : public T... {\n}"));
1036     // Should be: with semicolon, with { ... }
1037 }
1038 
TEST(DeclPrinter,TestClassTemplatePartialSpecializationDecl1)1039 TEST(DeclPrinter, TestClassTemplatePartialSpecializationDecl1) {
1040   ASSERT_TRUE(PrintedDeclCXX98Matches(
1041     "template<typename T, typename U>"
1042     "struct A { T a; U b; };"
1043     "template<typename T>"
1044     "struct A<T, int> { T a; };",
1045     classTemplateSpecializationDecl().bind("id"),
1046     "struct A {\n}"));
1047     // WRONG; Should be: "template<typename T> struct A<T, int> { ... }"
1048 }
1049 
TEST(DeclPrinter,TestClassTemplatePartialSpecializationDecl2)1050 TEST(DeclPrinter, TestClassTemplatePartialSpecializationDecl2) {
1051   ASSERT_TRUE(PrintedDeclCXX98Matches(
1052     "template<typename T>"
1053     "struct A { T a; };"
1054     "template<typename T>"
1055     "struct A<T *> { T a; };",
1056     classTemplateSpecializationDecl().bind("id"),
1057     "struct A {\n}"));
1058     // WRONG; Should be: "template<typename T> struct A<T *> { ... }"
1059 }
1060 
TEST(DeclPrinter,TestClassTemplateSpecializationDecl1)1061 TEST(DeclPrinter, TestClassTemplateSpecializationDecl1) {
1062   ASSERT_TRUE(PrintedDeclCXX98Matches(
1063     "template<typename T>"
1064     "struct A { T a; };"
1065     "template<>"
1066     "struct A<int> { int a; };",
1067     classTemplateSpecializationDecl().bind("id"),
1068     "struct A {\n}"));
1069     // WRONG; Should be: "template<> struct A<int> { ... }"
1070 }
1071 
TEST(DeclPrinter,TestFunctionTemplateDecl1)1072 TEST(DeclPrinter, TestFunctionTemplateDecl1) {
1073   ASSERT_TRUE(PrintedDeclCXX98Matches(
1074     "template<typename T>"
1075     "void A(T &t);",
1076     functionTemplateDecl(hasName("A")).bind("id"),
1077     "template <typename T> void A(T &t)"));
1078     // Should be: with semicolon
1079 }
1080 
TEST(DeclPrinter,TestFunctionTemplateDecl2)1081 TEST(DeclPrinter, TestFunctionTemplateDecl2) {
1082   ASSERT_TRUE(PrintedDeclCXX98Matches(
1083     "template<typename T>"
1084     "void A(T &t) { }",
1085     functionTemplateDecl(hasName("A")).bind("id"),
1086     "template <typename T> void A(T &t)"));
1087     // Should be: with semicolon
1088 }
1089 
TEST(DeclPrinter,TestFunctionTemplateDecl3)1090 TEST(DeclPrinter, TestFunctionTemplateDecl3) {
1091   ASSERT_TRUE(PrintedDeclCXX11Matches(
1092     "template<typename... T>"
1093     "void A(T... a);",
1094     functionTemplateDecl(hasName("A")).bind("id"),
1095     "template <typename ...T> void A(T ...a)"));
1096     // Should be: with semicolon.
1097 }
1098 
TEST(DeclPrinter,TestFunctionTemplateDecl4)1099 TEST(DeclPrinter, TestFunctionTemplateDecl4) {
1100   ASSERT_TRUE(PrintedDeclCXX98Matches(
1101     "struct Z { template<typename T> void A(T t); };",
1102     functionTemplateDecl(hasName("A")).bind("id"),
1103     "template <typename T> void A(T t)"));
1104     // Should be: with semicolon
1105 }
1106 
TEST(DeclPrinter,TestFunctionTemplateDecl5)1107 TEST(DeclPrinter, TestFunctionTemplateDecl5) {
1108   ASSERT_TRUE(PrintedDeclCXX98Matches(
1109     "struct Z { template<typename T> void A(T t) {} };",
1110     functionTemplateDecl(hasName("A")).bind("id"),
1111     "template <typename T> void A(T t)"));
1112     // Should be: with semicolon
1113 }
1114 
TEST(DeclPrinter,TestFunctionTemplateDecl6)1115 TEST(DeclPrinter, TestFunctionTemplateDecl6) {
1116   ASSERT_TRUE(PrintedDeclCXX98Matches(
1117     "template<typename T >struct Z {"
1118     "  template<typename U> void A(U t) {}"
1119     "};",
1120     functionTemplateDecl(hasName("A")).bind("id"),
1121     "template <typename U> void A(U t)"));
1122     // Should be: with semicolon
1123 }
1124 
TEST(DeclPrinter,TestTemplateArgumentList1)1125 TEST(DeclPrinter, TestTemplateArgumentList1) {
1126   ASSERT_TRUE(PrintedDeclCXX98Matches(
1127     "template<typename T> struct Z {};"
1128     "struct X {};"
1129     "Z<X> A;",
1130     "A",
1131     "Z<X> A"));
1132     // Should be: with semicolon
1133 }
1134 
TEST(DeclPrinter,TestTemplateArgumentList2)1135 TEST(DeclPrinter, TestTemplateArgumentList2) {
1136   ASSERT_TRUE(PrintedDeclCXX98Matches(
1137     "template<typename T, typename U> struct Z {};"
1138     "struct X {};"
1139     "typedef int Y;"
1140     "Z<X, Y> A;",
1141     "A",
1142     "Z<X, Y> A"));
1143     // Should be: with semicolon
1144 }
1145 
TEST(DeclPrinter,TestTemplateArgumentList3)1146 TEST(DeclPrinter, TestTemplateArgumentList3) {
1147   ASSERT_TRUE(PrintedDeclCXX98Matches(
1148     "template<typename T> struct Z {};"
1149     "template<typename T> struct X {};"
1150     "Z<X<int> > A;",
1151     "A",
1152     "Z<X<int> > A"));
1153     // Should be: with semicolon
1154 }
1155 
TEST(DeclPrinter,TestTemplateArgumentList4)1156 TEST(DeclPrinter, TestTemplateArgumentList4) {
1157   ASSERT_TRUE(PrintedDeclCXX11Matches(
1158     "template<typename T> struct Z {};"
1159     "template<typename T> struct X {};"
1160     "Z<X<int>> A;",
1161     "A",
1162     "Z<X<int> > A"));
1163     // Should be: with semicolon, without extra space in "> >"
1164 }
1165 
TEST(DeclPrinter,TestTemplateArgumentList5)1166 TEST(DeclPrinter, TestTemplateArgumentList5) {
1167   ASSERT_TRUE(PrintedDeclCXX98Matches(
1168     "template<typename T> struct Z {};"
1169     "template<typename T> struct X { Z<T> A; };",
1170     "A",
1171     "Z<T> A"));
1172     // Should be: with semicolon
1173 }
1174 
TEST(DeclPrinter,TestTemplateArgumentList6)1175 TEST(DeclPrinter, TestTemplateArgumentList6) {
1176   ASSERT_TRUE(PrintedDeclCXX98Matches(
1177     "template<template<typename T> class U> struct Z {};"
1178     "template<typename T> struct X {};"
1179     "Z<X> A;",
1180     "A",
1181     "Z<X> A"));
1182     // Should be: with semicolon
1183 }
1184 
TEST(DeclPrinter,TestTemplateArgumentList7)1185 TEST(DeclPrinter, TestTemplateArgumentList7) {
1186   ASSERT_TRUE(PrintedDeclCXX98Matches(
1187     "template<template<typename T> class U> struct Z {};"
1188     "template<template<typename T> class U> struct Y {"
1189     "  Z<U> A;"
1190     "};",
1191     "A",
1192     "Z<U> A"));
1193     // Should be: with semicolon
1194 }
1195 
TEST(DeclPrinter,TestTemplateArgumentList8)1196 TEST(DeclPrinter, TestTemplateArgumentList8) {
1197   ASSERT_TRUE(PrintedDeclCXX98Matches(
1198     "template<typename T> struct Z {};"
1199     "template<template<typename T> class U> struct Y {"
1200     "  Z<U<int> > A;"
1201     "};",
1202     "A",
1203     "Z<U<int> > A"));
1204     // Should be: with semicolon
1205 }
1206 
TEST(DeclPrinter,TestTemplateArgumentList9)1207 TEST(DeclPrinter, TestTemplateArgumentList9) {
1208   ASSERT_TRUE(PrintedDeclCXX98Matches(
1209     "template<unsigned I> struct Z {};"
1210     "Z<0> A;",
1211     "A",
1212     "Z<0> A"));
1213     // Should be: with semicolon
1214 }
1215 
TEST(DeclPrinter,TestTemplateArgumentList10)1216 TEST(DeclPrinter, TestTemplateArgumentList10) {
1217   ASSERT_TRUE(PrintedDeclCXX98Matches(
1218     "template<unsigned I> struct Z {};"
1219     "template<unsigned I> struct X { Z<I> A; };",
1220     "A",
1221     "Z<I> A"));
1222     // Should be: with semicolon
1223 }
1224 
TEST(DeclPrinter,TestTemplateArgumentList11)1225 TEST(DeclPrinter, TestTemplateArgumentList11) {
1226   ASSERT_TRUE(PrintedDeclCXX98Matches(
1227     "template<int I> struct Z {};"
1228     "Z<42 * 10 - 420 / 1> A;",
1229     "A",
1230     "Z<42 * 10 - 420 / 1> A"));
1231     // Should be: with semicolon
1232 }
1233 
TEST(DeclPrinter,TestTemplateArgumentList12)1234 TEST(DeclPrinter, TestTemplateArgumentList12) {
1235   ASSERT_TRUE(PrintedDeclCXX98Matches(
1236     "template<const char *p> struct Z {};"
1237     "extern const char X[] = \"aaa\";"
1238     "Z<X> A;",
1239     "A",
1240     "Z<X> A"));
1241     // Should be: with semicolon
1242 }
1243 
TEST(DeclPrinter,TestTemplateArgumentList13)1244 TEST(DeclPrinter, TestTemplateArgumentList13) {
1245   ASSERT_TRUE(PrintedDeclCXX11Matches(
1246     "template<typename... T> struct Z {};"
1247     "template<typename... T> struct X {"
1248     "  Z<T...> A;"
1249     "};",
1250     "A",
1251     "Z<T...> A"));
1252     // Should be: with semicolon
1253 }
1254 
TEST(DeclPrinter,TestTemplateArgumentList14)1255 TEST(DeclPrinter, TestTemplateArgumentList14) {
1256   ASSERT_TRUE(PrintedDeclCXX11Matches(
1257     "template<typename... T> struct Z {};"
1258     "template<typename T> struct Y {};"
1259     "template<typename... T> struct X {"
1260     "  Z<Y<T>...> A;"
1261     "};",
1262     "A",
1263     "Z<Y<T>...> A"));
1264     // Should be: with semicolon
1265 }
1266 
TEST(DeclPrinter,TestTemplateArgumentList15)1267 TEST(DeclPrinter, TestTemplateArgumentList15) {
1268   ASSERT_TRUE(PrintedDeclCXX11Matches(
1269     "template<unsigned I> struct Z {};"
1270     "template<typename... T> struct X {"
1271     "  Z<sizeof...(T)> A;"
1272     "};",
1273     "A",
1274     "Z<sizeof...(T)> A"));
1275     // Should be: with semicolon
1276 }
1277 
TEST(DeclPrinter,TestStaticAssert1)1278 TEST(DeclPrinter, TestStaticAssert1) {
1279   ASSERT_TRUE(PrintedDeclCXX1ZMatches(
1280     "static_assert(true);",
1281     staticAssertDecl().bind("id"),
1282     "static_assert(true)"));
1283 }
1284 
TEST(DeclPrinter,TestObjCMethod1)1285 TEST(DeclPrinter, TestObjCMethod1) {
1286   ASSERT_TRUE(PrintedDeclObjCMatches(
1287     "__attribute__((objc_root_class)) @interface X\n"
1288     "- (int)A:(id)anObject inRange:(long)range;\n"
1289     "@end\n"
1290     "@implementation X\n"
1291     "- (int)A:(id)anObject inRange:(long)range { int printThis; return 0; }\n"
1292     "@end\n",
1293     namedDecl(hasName("A:inRange:"),
1294               hasDescendant(namedDecl(hasName("printThis")))).bind("id"),
1295     "- (int) A:(id)anObject inRange:(long)range"));
1296 }
1297 
TEST(DeclPrinter,TestObjCProtocol1)1298 TEST(DeclPrinter, TestObjCProtocol1) {
1299   ASSERT_TRUE(PrintedDeclObjCMatches(
1300     "@protocol P1, P2;",
1301     namedDecl(hasName("P1")).bind("id"),
1302     "@protocol P1;\n"));
1303   ASSERT_TRUE(PrintedDeclObjCMatches(
1304     "@protocol P1, P2;",
1305     namedDecl(hasName("P2")).bind("id"),
1306     "@protocol P2;\n"));
1307 }
1308 
TEST(DeclPrinter,TestObjCProtocol2)1309 TEST(DeclPrinter, TestObjCProtocol2) {
1310   ASSERT_TRUE(PrintedDeclObjCMatches(
1311     "@protocol P2 @end"
1312     "@protocol P1<P2> @end",
1313     namedDecl(hasName("P1")).bind("id"),
1314     "@protocol P1<P2>\n@end"));
1315 }
1316