blob: 0bb0272eb56f59758e4a13deafb689a616194901 [file] [log] [blame]
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001//===- 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"
Daniel Jasper7fd90b02012-08-24 05:50:27 +000025#include "llvm/ADT/SmallString.h"
Dmitri Gribenko49795ae2012-08-20 23:39:06 +000026#include "gtest/gtest.h"
27
28using namespace clang;
29using namespace ast_matchers;
30using namespace tooling;
31
32namespace {
33
34void PrintDecl(raw_ostream &Out, const ASTContext *Context, const Decl *D) {
35 PrintingPolicy Policy = Context->getPrintingPolicy();
Dmitri Gribenkod1fc82e2012-08-21 17:36:32 +000036 Policy.TerseOutput = true;
Dmitri Gribenko49795ae2012-08-20 23:39:06 +000037 D->print(Out, Policy, /*Indentation*/ 0, /*PrintInstantiation*/ false);
38}
39
40class PrintMatch : public MatchFinder::MatchCallback {
41 SmallString<1024> Printed;
42 unsigned NumFoundDecls;
43
44public:
45 PrintMatch() : NumFoundDecls(0) {}
46
47 virtual void run(const MatchFinder::MatchResult &Result) {
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
59 StringRef getPrinted() const {
60 return Printed;
61 }
62
63 unsigned getNumFoundDecls() const {
64 return NumFoundDecls;
65 }
66};
67
Dmitri Gribenko49795ae2012-08-20 23:39:06 +000068::testing::AssertionResult PrintedDeclMatches(
69 StringRef Code,
Dmitri Gribenko976f1182012-08-31 03:23:26 +000070 const std::vector<std::string> &Args,
Dmitri Gribenko49795ae2012-08-20 23:39:06 +000071 const DeclarationMatcher &NodeMatch,
72 StringRef ExpectedPrinted) {
73 PrintMatch Printer;
74 MatchFinder Finder;
75 Finder.addMatcher(NodeMatch, &Printer);
76 OwningPtr<FrontendActionFactory> Factory(newFrontendActionFactory(&Finder));
77
Dmitri Gribenko976f1182012-08-31 03:23:26 +000078 if (!runToolOnCodeWithArgs(Factory->create(), Code, Args))
Dmitri Gribenko49795ae2012-08-20 23:39:06 +000079 return testing::AssertionFailure() << "Parsing error in \"" << Code << "\"";
80
81 if (Printer.getNumFoundDecls() == 0)
82 return testing::AssertionFailure()
83 << "Matcher didn't find any declarations";
84
85 if (Printer.getNumFoundDecls() > 1)
86 return testing::AssertionFailure()
87 << "Matcher should match only one declaration "
88 "(found " << Printer.getNumFoundDecls() << ")";
89
90 if (Printer.getPrinted() != ExpectedPrinted)
91 return ::testing::AssertionFailure()
92 << "Expected \"" << ExpectedPrinted << "\", "
93 "got \"" << Printer.getPrinted() << "\"";
94
95 return ::testing::AssertionSuccess();
96}
97
Dmitri Gribenko44470ef2012-08-31 03:05:44 +000098::testing::AssertionResult PrintedDeclCXX98Matches(StringRef Code,
99 StringRef DeclName,
100 StringRef ExpectedPrinted) {
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000101 std::vector<std::string> Args(1, "-std=c++98");
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000102 return PrintedDeclMatches(Code,
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000103 Args,
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000104 namedDecl(hasName(DeclName)).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000105 ExpectedPrinted);
106}
107
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000108::testing::AssertionResult PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000109 StringRef Code,
110 const DeclarationMatcher &NodeMatch,
111 StringRef ExpectedPrinted) {
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000112 std::vector<std::string> Args(1, "-std=c++98");
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000113 return PrintedDeclMatches(Code,
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000114 Args,
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000115 NodeMatch,
116 ExpectedPrinted);
117}
118
119::testing::AssertionResult PrintedDeclCXX11Matches(StringRef Code,
120 StringRef DeclName,
121 StringRef ExpectedPrinted) {
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000122 std::vector<std::string> Args(1, "-std=c++11");
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000123 return PrintedDeclMatches(Code,
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000124 Args,
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000125 namedDecl(hasName(DeclName)).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000126 ExpectedPrinted);
127}
128
129::testing::AssertionResult PrintedDeclCXX11Matches(
130 StringRef Code,
131 const DeclarationMatcher &NodeMatch,
132 StringRef ExpectedPrinted) {
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000133 std::vector<std::string> Args(1, "-std=c++11");
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000134 return PrintedDeclMatches(Code,
Dmitri Gribenko976f1182012-08-31 03:23:26 +0000135 Args,
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000136 NodeMatch,
137 ExpectedPrinted);
138}
139
140} // unnamed namespace
141
142TEST(DeclPrinter, TestNamespace1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000143 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000144 "namespace A { int B; }",
145 "A",
146 "namespace A {\n}"));
147 // Should be: with { ... }
148}
149
150TEST(DeclPrinter, TestNamespace2) {
151 ASSERT_TRUE(PrintedDeclCXX11Matches(
152 "inline namespace A { int B; }",
153 "A",
154 "inline namespace A {\n}"));
155 // Should be: with { ... }
156}
157
158TEST(DeclPrinter, TestNamespaceAlias1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000159 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000160 "namespace Z { }"
161 "namespace A = Z;",
162 "A",
163 "namespace A = Z"));
164 // Should be: with semicolon
165}
166
167TEST(DeclPrinter, TestNamespaceAlias2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000168 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000169 "namespace X { namespace Y {} }"
170 "namespace A = X::Y;",
171 "A",
172 "namespace A = X::Y"));
173 // Should be: with semicolon
174}
175
176TEST(DeclPrinter, TestCXXRecordDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000177 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000178 "class A { int a; };",
179 "A",
180 "class A {\n}"));
181 // Should be: with semicolon, with { ... }
182}
183
184TEST(DeclPrinter, TestCXXRecordDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000185 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000186 "struct A { int a; };",
187 "A",
188 "struct A {\n}"));
189 // Should be: with semicolon, with { ... }
190}
191
192TEST(DeclPrinter, TestCXXRecordDecl3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000193 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000194 "union A { int a; };",
195 "A",
196 "union A {\n}"));
197 // Should be: with semicolon, with { ... }
198}
199
200TEST(DeclPrinter, TestCXXRecordDecl4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000201 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000202 "class Z { int a; };"
203 "class A : Z { int b; };",
204 "A",
205 "class A : Z {\n}"));
206 // Should be: with semicolon, with { ... }, without two spaces
207}
208
209TEST(DeclPrinter, TestCXXRecordDecl5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000210 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000211 "struct Z { int a; };"
212 "struct A : Z { int b; };",
213 "A",
214 "struct A : Z {\n}"));
215 // Should be: with semicolon, with { ... }, without two spaces
216}
217
218TEST(DeclPrinter, TestCXXRecordDecl6) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000219 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000220 "class Z { int a; };"
221 "class A : public Z { int b; };",
222 "A",
223 "class A : public Z {\n}"));
224 // Should be: with semicolon, with { ... }
225}
226
227TEST(DeclPrinter, TestCXXRecordDecl7) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000228 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000229 "class Z { int a; };"
230 "class A : protected Z { int b; };",
231 "A",
232 "class A : protected Z {\n}"));
233 // Should be: with semicolon, with { ... }
234}
235
236TEST(DeclPrinter, TestCXXRecordDecl8) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000237 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000238 "class Z { int a; };"
239 "class A : private Z { int b; };",
240 "A",
241 "class A : private Z {\n}"));
242 // Should be: with semicolon, with { ... }
243}
244
245TEST(DeclPrinter, TestCXXRecordDecl9) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000246 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000247 "class Z { int a; };"
248 "class A : virtual Z { int b; };",
249 "A",
250 "class A : virtual Z {\n}"));
251 // Should be: with semicolon, with { ... }, without two spaces
252}
253
254TEST(DeclPrinter, TestCXXRecordDecl10) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000255 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000256 "class Z { int a; };"
257 "class A : virtual public Z { int b; };",
258 "A",
259 "class A : virtual public Z {\n}"));
260 // Should be: with semicolon, with { ... }
261}
262
263TEST(DeclPrinter, TestCXXRecordDecl11) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000264 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000265 "class Z { int a; };"
266 "class Y : virtual public Z { int b; };"
267 "class A : virtual public Z, private Y { int c; };",
268 "A",
269 "class A : virtual public Z, private Y {\n}"));
270 // Should be: with semicolon, with { ... }
271}
272
273TEST(DeclPrinter, TestFunctionDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000274 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000275 "void A();",
276 "A",
277 "void A()"));
278 // Should be: with semicolon
279}
280
281TEST(DeclPrinter, TestFunctionDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000282 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000283 "void A() {}",
284 "A",
285 "void A()"));
286 // Should be: with semicolon
287}
288
289TEST(DeclPrinter, TestFunctionDecl3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000290 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000291 "void Z();"
292 "void A() { Z(); }",
293 "A",
294 "void A()"));
295 // Should be: with semicolon
296}
297
298TEST(DeclPrinter, TestFunctionDecl4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000299 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000300 "extern void A();",
301 "A",
302 "extern void A()"));
303 // Should be: with semicolon
304}
305
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000306TEST(DeclPrinter, TestFunctionDecl5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000307 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000308 "static void A();",
309 "A",
310 "static void A()"));
311 // Should be: with semicolon
312}
313
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000314TEST(DeclPrinter, TestFunctionDecl6) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000315 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000316 "inline void A();",
317 "A",
318 "inline void A()"));
319 // Should be: with semicolon
320}
321
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000322TEST(DeclPrinter, TestFunctionDecl7) {
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000323 ASSERT_TRUE(PrintedDeclCXX11Matches(
324 "constexpr int A(int a);",
325 "A",
326 "int A(int a)"));
327 // WRONG; Should be: "constexpr int A(int a);"
328}
329
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000330TEST(DeclPrinter, TestFunctionDecl8) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000331 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000332 "void A(int a);",
333 "A",
334 "void A(int a)"));
335 // Should be: with semicolon
336}
337
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000338TEST(DeclPrinter, TestFunctionDecl9) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000339 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000340 "void A(...);",
341 "A",
342 "void A(...)"));
343 // Should be: with semicolon
344}
345
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000346TEST(DeclPrinter, TestFunctionDecl10) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000347 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000348 "void A(int a, ...);",
349 "A",
350 "void A(int a, ...)"));
351 // Should be: with semicolon
352}
353
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000354TEST(DeclPrinter, TestFunctionDecl11) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000355 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000356 "typedef long size_t;"
357 "typedef int *pInt;"
358 "void A(int a, pInt b, size_t c);",
359 "A",
360 "void A(int a, pInt b, size_t c)"));
361 // Should be: with semicolon
362}
363
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000364TEST(DeclPrinter, TestFunctionDecl12) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000365 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000366 "void A(int a, int b = 0);",
367 "A",
368 "void A(int a, int b = 0)"));
369 // Should be: with semicolon
370}
371
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000372TEST(DeclPrinter, TestFunctionDecl13) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000373 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000374 "void (*A(int a))(int b);",
375 "A",
376 "void (*A(int a))(int)"));
377 // Should be: with semicolon, with parameter name (?)
378}
379
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000380TEST(DeclPrinter, TestFunctionDecl14) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000381 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000382 "template<typename T>"
383 "void A(T t) { }"
384 "template<>"
385 "void A(int N) { }",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000386 functionDecl(hasName("A"), isExplicitTemplateSpecialization()).bind("id"),
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +0000387 "void A(int N)"));
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000388 // WRONG; Should be: "template <> void A(int N);"));
389}
390
391
392TEST(DeclPrinter, TestCXXConstructorDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000393 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000394 "struct A {"
395 " A();"
396 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000397 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000398 ""));
399 // WRONG; Should be: "A();"
400}
401
402TEST(DeclPrinter, TestCXXConstructorDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000403 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000404 "struct A {"
405 " A(int a);"
406 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000407 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000408 ""));
409 // WRONG; Should be: "A(int a);"
410}
411
412TEST(DeclPrinter, TestCXXConstructorDecl3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000413 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000414 "struct A {"
415 " A(const A &a);"
416 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000417 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000418 ""));
419 // WRONG; Should be: "A(const A &a);"
420}
421
422TEST(DeclPrinter, TestCXXConstructorDecl4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000423 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000424 "struct A {"
425 " A(const A &a, int = 0);"
426 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000427 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000428 ""));
429 // WRONG; Should be: "A(const A &a, int = 0);"
430}
431
432TEST(DeclPrinter, TestCXXConstructorDecl5) {
433 ASSERT_TRUE(PrintedDeclCXX11Matches(
434 "struct A {"
435 " A(const A &&a);"
436 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000437 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000438 ""));
439 // WRONG; Should be: "A(const A &&a);"
440}
441
442TEST(DeclPrinter, TestCXXConstructorDecl6) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000443 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000444 "struct A {"
445 " explicit A(int a);"
446 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000447 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000448 ""));
449 // WRONG; Should be: "explicit A(int a);"
450}
451
452TEST(DeclPrinter, TestCXXConstructorDecl7) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000453 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000454 "struct A {"
455 " constexpr A();"
456 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000457 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000458 ""));
459 // WRONG; Should be: "constexpr A();"
460}
461
462TEST(DeclPrinter, TestCXXConstructorDecl8) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000463 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000464 "struct A {"
465 " A() = default;"
466 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000467 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000468 ""));
469 // WRONG; Should be: "A() = default;"
470}
471
472TEST(DeclPrinter, TestCXXConstructorDecl9) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000473 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000474 "struct A {"
475 " A() = delete;"
476 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000477 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000478 " = delete"));
479 // WRONG; Should be: "A() = delete;"
480}
481
Dmitri Gribenkoc4684242012-08-24 00:26:25 +0000482TEST(DeclPrinter, TestCXXConstructorDecl10) {
483 ASSERT_TRUE(PrintedDeclCXX11Matches(
484 "template<typename... T>"
485 "struct A {"
486 " A(const A &a);"
487 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000488 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenkoc4684242012-08-24 00:26:25 +0000489 ""));
490 // WRONG; Should be: "A(const A &a);"
491}
492
NAKAMURA Takumi29b1f682012-08-25 00:05:56 +0000493#if !defined(_MSC_VER)
Dmitri Gribenkoc4684242012-08-24 00:26:25 +0000494TEST(DeclPrinter, TestCXXConstructorDecl11) {
495 ASSERT_TRUE(PrintedDeclCXX11Matches(
496 "template<typename... T>"
497 "struct A : public T... {"
498 " A(T&&... ts) : T(ts)... {}"
499 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000500 constructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenkoc4684242012-08-24 00:26:25 +0000501 "A<T...>(T &&ts...) : T(ts)"));
Dmitri Gribenkof6ec15a2012-08-24 00:27:50 +0000502 // WRONG; Should be: "A(T&&... ts) : T(ts)..."
Dmitri Gribenkoc4684242012-08-24 00:26:25 +0000503}
NAKAMURA Takumi29b1f682012-08-25 00:05:56 +0000504#endif
Dmitri Gribenkoc4684242012-08-24 00:26:25 +0000505
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000506TEST(DeclPrinter, TestCXXDestructorDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000507 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000508 "struct A {"
509 " ~A();"
510 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000511 destructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000512 "void ~A()"));
513 // WRONG; Should be: "~A();"
514}
515
516TEST(DeclPrinter, TestCXXDestructorDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000517 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000518 "struct A {"
519 " virtual ~A();"
520 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000521 destructorDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000522 "virtual void ~A()"));
523 // WRONG; Should be: "virtual ~A();"
524}
525
526TEST(DeclPrinter, TestCXXConversionDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000527 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000528 "struct A {"
529 " operator int();"
530 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000531 methodDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000532 "int operator int()"));
533 // WRONG; Should be: "operator int();"
534}
535
536TEST(DeclPrinter, TestCXXConversionDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000537 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000538 "struct A {"
539 " operator bool();"
540 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000541 methodDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000542 "bool operator _Bool()"));
543 // WRONG; Should be: "operator bool();"
544}
545
546TEST(DeclPrinter, TestCXXConversionDecl3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000547 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000548 "struct Z {};"
549 "struct A {"
550 " operator Z();"
551 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000552 methodDecl(ofClass(hasName("A"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000553 "Z operator struct Z()"));
554 // WRONG; Should be: "operator Z();"
555}
556
557TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000558 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000559 "namespace std { typedef decltype(sizeof(int)) size_t; }"
560 "struct Z {"
561 " void *operator new(std::size_t);"
562 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000563 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000564 "void *operator new(std::size_t)"));
565 // Should be: with semicolon
566}
567
568TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000569 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000570 "namespace std { typedef decltype(sizeof(int)) size_t; }"
571 "struct Z {"
572 " void *operator new[](std::size_t);"
573 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000574 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000575 "void *operator new[](std::size_t)"));
576 // Should be: with semicolon
577}
578
579TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000580 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000581 "struct Z {"
582 " void operator delete(void *);"
583 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000584 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000585 "void operator delete(void *) noexcept"));
586 // Should be: with semicolon, without noexcept?
587}
588
589TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000590 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000591 "struct Z {"
592 " void operator delete(void *);"
593 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000594 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000595 "void operator delete(void *)"));
596 // Should be: with semicolon
597}
598
599TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000600 ASSERT_TRUE(PrintedDeclCXX11Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000601 "struct Z {"
602 " void operator delete[](void *);"
603 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000604 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000605 "void operator delete[](void *) noexcept"));
606 // Should be: with semicolon, without noexcept?
607}
608
609TEST(DeclPrinter, TestCXXMethodDecl_Operator1) {
610 const char *OperatorNames[] = {
611 "+", "-", "*", "/", "%", "^", "&", "|",
612 "=", "<", ">", "+=", "-=", "*=", "/=", "%=",
613 "^=", "&=", "|=", "<<", ">>", ">>=", "<<=", "==", "!=",
614 "<=", ">=", "&&", "||", ",", "->*",
615 "()", "[]"
616 };
617
618 for (unsigned i = 0, e = llvm::array_lengthof(OperatorNames); i != e; ++i) {
619 SmallString<128> Code;
620 Code.append("struct Z { void operator");
621 Code.append(OperatorNames[i]);
622 Code.append("(Z z); };");
623
624 SmallString<128> Expected;
625 Expected.append("void operator");
626 Expected.append(OperatorNames[i]);
627 Expected.append("(Z z)");
628 // Should be: with semicolon
629
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000630 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000631 Code,
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000632 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000633 Expected));
634 }
635}
636
637TEST(DeclPrinter, TestCXXMethodDecl_Operator2) {
638 const char *OperatorNames[] = {
639 "~", "!", "++", "--", "->"
640 };
641
642 for (unsigned i = 0, e = llvm::array_lengthof(OperatorNames); i != e; ++i) {
643 SmallString<128> Code;
644 Code.append("struct Z { void operator");
645 Code.append(OperatorNames[i]);
646 Code.append("(); };");
647
648 SmallString<128> Expected;
649 Expected.append("void operator");
650 Expected.append(OperatorNames[i]);
651 Expected.append("()");
652 // Should be: with semicolon
653
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000654 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000655 Code,
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000656 methodDecl(ofClass(hasName("Z"))).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000657 Expected));
658 }
659}
660
661TEST(DeclPrinter, TestCXXMethodDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000662 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000663 "struct Z {"
664 " void A(int a);"
665 "};",
666 "A",
667 "void A(int a)"));
668 // Should be: with semicolon
669}
670
671TEST(DeclPrinter, TestCXXMethodDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000672 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000673 "struct Z {"
674 " virtual void A(int a);"
675 "};",
676 "A",
677 "virtual void A(int a)"));
678 // Should be: with semicolon
679}
680
681TEST(DeclPrinter, TestCXXMethodDecl3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000682 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000683 "struct Z {"
684 " virtual void A(int a);"
685 "};"
686 "struct ZZ : Z {"
687 " void A(int a);"
688 "};",
689 "ZZ::A",
690 "void A(int a)"));
691 // Should be: with semicolon
692 // TODO: should we print "virtual"?
693}
694
695TEST(DeclPrinter, TestCXXMethodDecl4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000696 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000697 "struct Z {"
698 " inline void A(int a);"
699 "};",
700 "A",
701 "inline void A(int a)"));
702 // Should be: with semicolon
703}
704
705TEST(DeclPrinter, TestCXXMethodDecl5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000706 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000707 "struct Z {"
708 " virtual void A(int a) = 0;"
709 "};",
710 "A",
711 "virtual void A(int a) = 0"));
712 // Should be: with semicolon
713}
714
715TEST(DeclPrinter, TestCXXMethodDecl_CVQualifier1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000716 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000717 "struct Z {"
718 " void A(int a) const;"
719 "};",
720 "A",
721 "void A(int a) const"));
722 // Should be: with semicolon
723}
724
725TEST(DeclPrinter, TestCXXMethodDecl_CVQualifier2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000726 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000727 "struct Z {"
728 " void A(int a) volatile;"
729 "};",
730 "A",
731 "void A(int a) volatile"));
732 // Should be: with semicolon
733}
734
735TEST(DeclPrinter, TestCXXMethodDecl_CVQualifier3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000736 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000737 "struct Z {"
738 " void A(int a) const volatile;"
739 "};",
740 "A",
741 "void A(int a) const volatile"));
742 // Should be: with semicolon
743}
744
745TEST(DeclPrinter, TestCXXMethodDecl_RefQualifier1) {
746 ASSERT_TRUE(PrintedDeclCXX11Matches(
747 "struct Z {"
748 " void A(int a) &;"
749 "};",
750 "A",
751 "void A(int a)"));
752 // WRONG; Should be: "void A(int a) &;"
753}
754
755TEST(DeclPrinter, TestCXXMethodDecl_RefQualifier2) {
756 ASSERT_TRUE(PrintedDeclCXX11Matches(
757 "struct Z {"
758 " void A(int a) &&;"
759 "};",
760 "A",
761 "void A(int a)"));
762 // WRONG; Should be: "void A(int a) &&;"
763}
764
765TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000766 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000767 "struct Z {"
768 " void A(int a) throw();"
769 "};",
770 "A",
771 "void A(int a) throw()"));
772 // Should be: with semicolon
773}
774
775TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000776 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000777 "struct Z {"
778 " void A(int a) throw(int);"
779 "};",
780 "A",
781 "void A(int a) throw(int)"));
782 // Should be: with semicolon
783}
784
785TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000786 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000787 "class ZZ {};"
788 "struct Z {"
789 " void A(int a) throw(ZZ, int);"
790 "};",
791 "A",
792 "void A(int a) throw(ZZ, int)"));
793 // Should be: with semicolon
794}
795
796TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification4) {
797 ASSERT_TRUE(PrintedDeclCXX11Matches(
798 "struct Z {"
799 " void A(int a) noexcept;"
800 "};",
801 "A",
802 "void A(int a) noexcept"));
803 // Should be: with semicolon
804}
805
806TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification5) {
807 ASSERT_TRUE(PrintedDeclCXX11Matches(
808 "struct Z {"
809 " void A(int a) noexcept(true);"
810 "};",
811 "A",
812 "void A(int a) noexcept(trueA(int a) noexcept(true)"));
813 // WRONG; Should be: "void A(int a) noexcept(true);"
814}
815
816TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification6) {
817 ASSERT_TRUE(PrintedDeclCXX11Matches(
818 "struct Z {"
819 " void A(int a) noexcept(1 < 2);"
820 "};",
821 "A",
822 "void A(int a) noexcept(1 < 2A(int a) noexcept(1 < 2)"));
823 // WRONG; Should be: "void A(int a) noexcept(1 < 2);"
824}
825
826TEST(DeclPrinter, TestFunctionDecl_ExceptionSpecification7) {
827 ASSERT_TRUE(PrintedDeclCXX11Matches(
828 "template<int N>"
829 "struct Z {"
830 " void A(int a) noexcept(N < 2);"
831 "};",
832 "A",
833 "void A(int a) noexcept(N < 2A(int a) noexcept(N < 2)"));
834 // WRONG; Should be: "void A(int a) noexcept(N < 2);"
835}
836
837TEST(DeclPrinter, TestVarDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000838 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000839 "char *const (*(*A)[5])(int);",
840 "A",
841 "char *const (*(*A)[5])(int)"));
842 // Should be: with semicolon
843}
844
845TEST(DeclPrinter, TestVarDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000846 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000847 "void (*A)() throw(int);",
848 "A",
849 "void (*A)() throw(int)"));
850 // Should be: with semicolon
851}
852
853TEST(DeclPrinter, TestVarDecl3) {
854 ASSERT_TRUE(PrintedDeclCXX11Matches(
855 "void (*A)() noexcept;",
856 "A",
857 "void (*A)() noexcept"));
858 // Should be: with semicolon
859}
860
861TEST(DeclPrinter, TestFieldDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000862 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000863 "template<typename T>"
864 "struct Z { T A; };",
865 "A",
866 "T A"));
867 // Should be: with semicolon
868}
869
870TEST(DeclPrinter, TestFieldDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000871 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000872 "template<int N>"
873 "struct Z { int A[N]; };",
874 "A",
875 "int A[N]"));
876 // Should be: with semicolon
877}
878
879TEST(DeclPrinter, TestClassTemplateDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000880 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000881 "template<typename T>"
882 "struct A { T a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000883 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000884 "template <typename T> struct A {\n}"));
885 // Should be: with semicolon, with { ... }
886}
887
888TEST(DeclPrinter, TestClassTemplateDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000889 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000890 "template<typename T = int>"
891 "struct A { T a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000892 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000893 "template <typename T = int> struct A {\n}"));
894 // Should be: with semicolon, with { ... }
895}
896
897TEST(DeclPrinter, TestClassTemplateDecl3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000898 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000899 "template<class T>"
900 "struct A { T a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000901 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000902 "template <class T> struct A {\n}"));
903 // Should be: with semicolon, with { ... }
904}
905
906TEST(DeclPrinter, TestClassTemplateDecl4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000907 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000908 "template<typename T, typename U>"
909 "struct A { T a; U b; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000910 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000911 "template <typename T, typename U> struct A {\n}"));
912 // Should be: with semicolon, with { ... }
913}
914
915TEST(DeclPrinter, TestClassTemplateDecl5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000916 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000917 "template<int N>"
918 "struct A { int a[N]; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000919 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000920 "template <int N> struct A {\n}"));
921 // Should be: with semicolon, with { ... }
922}
923
924TEST(DeclPrinter, TestClassTemplateDecl6) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000925 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000926 "template<int N = 42>"
927 "struct A { int a[N]; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000928 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000929 "template <int N = 42> struct A {\n}"));
930 // Should be: with semicolon, with { ... }
931}
932
933TEST(DeclPrinter, TestClassTemplateDecl7) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000934 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000935 "typedef int MyInt;"
936 "template<MyInt N>"
937 "struct A { int a[N]; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000938 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000939 "template <MyInt N> struct A {\n}"));
940 // Should be: with semicolon, with { ... }
941}
942
943TEST(DeclPrinter, TestClassTemplateDecl8) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000944 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000945 "template<template<typename U> class T> struct A { };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000946 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000947 "template <template <typename U> class T> struct A {\n}"));
948 // Should be: with semicolon, with { ... }
949}
950
951TEST(DeclPrinter, TestClassTemplateDecl9) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000952 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000953 "template<typename T> struct Z { };"
954 "template<template<typename U> class T = Z> struct A { };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000955 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000956 "template <template <typename U> class T> struct A {\n}"));
957 // Should be: with semicolon, with { ... }
958}
959
960TEST(DeclPrinter, TestClassTemplateDecl10) {
961 ASSERT_TRUE(PrintedDeclCXX11Matches(
962 "template<typename... T>"
963 "struct A { int a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000964 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000965 "template <typename ... T> struct A {\n}"));
966 // Should be: with semicolon, with { ... }, without spaces before '...'
967}
968
969TEST(DeclPrinter, TestClassTemplateDecl11) {
970 ASSERT_TRUE(PrintedDeclCXX11Matches(
971 "template<typename... T>"
972 "struct A : public T... { int a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000973 classTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000974 "template <typename ... T> struct A : public T... {\n}"));
975 // Should be: with semicolon, with { ... }, without spaces before '...'
976}
977
978TEST(DeclPrinter, TestClassTemplatePartialSpecializationDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000979 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000980 "template<typename T, typename U>"
981 "struct A { T a; U b; };"
982 "template<typename T>"
983 "struct A<T, int> { T a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000984 classTemplateSpecializationDecl().bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000985 "struct A {\n}"));
986 // WRONG; Should be: "template<typename T> struct A<T, int> { ... }"
987}
988
989TEST(DeclPrinter, TestClassTemplatePartialSpecializationDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +0000990 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000991 "template<typename T>"
992 "struct A { T a; };"
993 "template<typename T>"
994 "struct A<T *> { T a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +0000995 classTemplateSpecializationDecl().bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +0000996 "struct A {\n}"));
997 // WRONG; Should be: "template<typename T> struct A<T *> { ... }"
998}
999
1000TEST(DeclPrinter, TestClassTemplateSpecializationDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001001 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001002 "template<typename T>"
1003 "struct A { T a; };"
1004 "template<>"
1005 "struct A<int> { int a; };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001006 classTemplateSpecializationDecl().bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001007 "struct A {\n}"));
1008 // WRONG; Should be: "template<> struct A<int> { ... }"
1009}
1010
1011TEST(DeclPrinter, TestFunctionTemplateDecl1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001012 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001013 "template<typename T>"
1014 "void A(T &t);",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001015 functionTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001016 "template <typename T> void A(T &t)"));
1017 // Should be: with semicolon
1018}
1019
1020TEST(DeclPrinter, TestFunctionTemplateDecl2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001021 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001022 "template<typename T>"
1023 "void A(T &t) { }",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001024 functionTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +00001025 "template <typename T> void A(T &t)"));
1026 // Should be: with semicolon
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001027}
1028
1029TEST(DeclPrinter, TestFunctionTemplateDecl3) {
1030 ASSERT_TRUE(PrintedDeclCXX11Matches(
1031 "template<typename... T>"
1032 "void A(T... a);",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001033 functionTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001034 "template <typename ... T> void A(T a...)"));
1035 // WRONG; Should be: "template <typename ... T> void A(T... a)"
1036 // (not "T a...")
1037 // Should be: with semicolon.
1038}
1039
1040TEST(DeclPrinter, TestFunctionTemplateDecl4) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001041 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001042 "struct Z { template<typename T> void A(T t); };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001043 functionTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001044 "template <typename T> void A(T t)"));
1045 // Should be: with semicolon
1046}
1047
1048TEST(DeclPrinter, TestFunctionTemplateDecl5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001049 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001050 "struct Z { template<typename T> void A(T t) {} };",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001051 functionTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +00001052 "template <typename T> void A(T t)"));
1053 // Should be: with semicolon
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001054}
1055
1056TEST(DeclPrinter, TestFunctionTemplateDecl6) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001057 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001058 "template<typename T >struct Z {"
1059 " template<typename U> void A(U t) {}"
1060 "};",
Daniel Jasper2dc75ed2012-08-24 05:12:34 +00001061 functionTemplateDecl(hasName("A")).bind("id"),
Dmitri Gribenko2e0b8d92012-08-21 17:47:24 +00001062 "template <typename U> void A(U t)"));
1063 // Should be: with semicolon
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001064}
1065
1066TEST(DeclPrinter, TestTemplateArgumentList1) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001067 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001068 "template<typename T> struct Z {};"
1069 "struct X {};"
1070 "Z<X> A;",
1071 "A",
1072 "Z<X> A"));
1073 // Should be: with semicolon
1074}
1075
1076TEST(DeclPrinter, TestTemplateArgumentList2) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001077 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001078 "template<typename T, typename U> struct Z {};"
1079 "struct X {};"
1080 "typedef int Y;"
1081 "Z<X, Y> A;",
1082 "A",
1083 "Z<X, Y> A"));
1084 // Should be: with semicolon
1085}
1086
1087TEST(DeclPrinter, TestTemplateArgumentList3) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001088 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001089 "template<typename T> struct Z {};"
1090 "template<typename T> struct X {};"
1091 "Z<X<int> > A;",
1092 "A",
1093 "Z<X<int> > A"));
1094 // Should be: with semicolon
1095}
1096
1097TEST(DeclPrinter, TestTemplateArgumentList4) {
1098 ASSERT_TRUE(PrintedDeclCXX11Matches(
1099 "template<typename T> struct Z {};"
1100 "template<typename T> struct X {};"
1101 "Z<X<int>> A;",
1102 "A",
1103 "Z<X<int> > A"));
1104 // Should be: with semicolon, without extra space in "> >"
1105}
1106
1107TEST(DeclPrinter, TestTemplateArgumentList5) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001108 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001109 "template<typename T> struct Z {};"
1110 "template<typename T> struct X { Z<T> A; };",
1111 "A",
1112 "Z<T> A"));
1113 // Should be: with semicolon
1114}
1115
1116TEST(DeclPrinter, TestTemplateArgumentList6) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001117 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001118 "template<template<typename T> class U> struct Z {};"
1119 "template<typename T> struct X {};"
1120 "Z<X> A;",
1121 "A",
1122 "Z<X> A"));
1123 // Should be: with semicolon
1124}
1125
1126TEST(DeclPrinter, TestTemplateArgumentList7) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001127 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001128 "template<template<typename T> class U> struct Z {};"
1129 "template<template<typename T> class U> struct Y {"
1130 " Z<U> A;"
1131 "};",
1132 "A",
1133 "Z<U> A"));
1134 // Should be: with semicolon
1135}
1136
1137TEST(DeclPrinter, TestTemplateArgumentList8) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001138 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001139 "template<typename T> struct Z {};"
1140 "template<template<typename T> class U> struct Y {"
1141 " Z<U<int> > A;"
1142 "};",
1143 "A",
1144 "Z<U<int> > A"));
1145 // Should be: with semicolon
1146}
1147
1148TEST(DeclPrinter, TestTemplateArgumentList9) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001149 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001150 "template<unsigned I> struct Z {};"
1151 "Z<0> A;",
1152 "A",
1153 "Z<0> A"));
1154 // Should be: with semicolon
1155}
1156
1157TEST(DeclPrinter, TestTemplateArgumentList10) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001158 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001159 "template<unsigned I> struct Z {};"
1160 "template<unsigned I> struct X { Z<I> A; };",
1161 "A",
1162 "Z<I> A"));
1163 // Should be: with semicolon
1164}
1165
1166TEST(DeclPrinter, TestTemplateArgumentList11) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001167 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001168 "template<int I> struct Z {};"
1169 "Z<42 * 10 - 420 / 1> A;",
1170 "A",
1171 "Z<42 * 10 - 420 / 1> A"));
1172 // Should be: with semicolon
1173}
1174
1175TEST(DeclPrinter, TestTemplateArgumentList12) {
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001176 ASSERT_TRUE(PrintedDeclCXX98Matches(
Dmitri Gribenko49795ae2012-08-20 23:39:06 +00001177 "template<const char *p> struct Z {};"
1178 "extern const char X[] = \"aaa\";"
1179 "Z<X> A;",
1180 "A",
1181 "Z<X> A"));
1182 // Should be: with semicolon
1183}
1184
1185TEST(DeclPrinter, TestTemplateArgumentList13) {
1186 ASSERT_TRUE(PrintedDeclCXX11Matches(
1187 "template<typename... T> struct Z {};"
1188 "template<typename... T> struct X {"
1189 " Z<T...> A;"
1190 "};",
1191 "A",
1192 "Z<T...> A"));
1193 // Should be: with semicolon, without extra space in "> >"
1194}
1195
1196TEST(DeclPrinter, TestTemplateArgumentList14) {
1197 ASSERT_TRUE(PrintedDeclCXX11Matches(
1198 "template<typename... T> struct Z {};"
1199 "template<typename T> struct Y {};"
1200 "template<typename... T> struct X {"
1201 " Z<Y<T>...> A;"
1202 "};",
1203 "A",
1204 "Z<Y<T>...> A"));
1205 // Should be: with semicolon, without extra space in "> >"
1206}
1207
1208TEST(DeclPrinter, TestTemplateArgumentList15) {
1209 ASSERT_TRUE(PrintedDeclCXX11Matches(
1210 "template<unsigned I> struct Z {};"
1211 "template<typename... T> struct X {"
1212 " Z<sizeof...(T)> A;"
1213 "};",
1214 "A",
1215 "Z<sizeof...(T)> A"));
1216 // Should be: with semicolon, without extra space in "> >"
1217}
Dmitri Gribenko44470ef2012-08-31 03:05:44 +00001218