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 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(); 36 Policy.TerseOutput = true; 37 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 68::testing::AssertionResult PrintedDeclMatches( 69 StringRef Code, 70 const std::vector<std::string> &Args, 71 const DeclarationMatcher &NodeMatch, 72 StringRef ExpectedPrinted) { 73 PrintMatch Printer; 74 MatchFinder Finder; 75 Finder.addMatcher(NodeMatch, &Printer); 76 OwningPtr<FrontendActionFactory> Factory(newFrontendActionFactory(&Finder)); 77 78 if (!runToolOnCodeWithArgs(Factory->create(), Code, Args)) 79 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 98::testing::AssertionResult PrintedDeclCXX98Matches(StringRef Code, 99 StringRef DeclName, 100 StringRef ExpectedPrinted) { 101 std::vector<std::string> Args(1, "-std=c++98"); 102 return PrintedDeclMatches(Code, 103 Args, 104 namedDecl(hasName(DeclName)).bind("id"), 105 ExpectedPrinted); 106} 107 108::testing::AssertionResult PrintedDeclCXX98Matches( 109 StringRef Code, 110 const DeclarationMatcher &NodeMatch, 111 StringRef ExpectedPrinted) { 112 std::vector<std::string> Args(1, "-std=c++98"); 113 return PrintedDeclMatches(Code, 114 Args, 115 NodeMatch, 116 ExpectedPrinted); 117} 118 119::testing::AssertionResult PrintedDeclCXX11Matches(StringRef Code, 120 StringRef DeclName, 121 StringRef ExpectedPrinted) { 122 std::vector<std::string> Args(1, "-std=c++11"); 123 return PrintedDeclMatches(Code, 124 Args, 125 namedDecl(hasName(DeclName)).bind("id"), 126 ExpectedPrinted); 127} 128 129::testing::AssertionResult PrintedDeclCXX11Matches( 130 StringRef Code, 131 const DeclarationMatcher &NodeMatch, 132 StringRef ExpectedPrinted) { 133 std::vector<std::string> Args(1, "-std=c++11"); 134 return PrintedDeclMatches(Code, 135 Args, 136 NodeMatch, 137 ExpectedPrinted); 138} 139 140} // unnamed namespace 141 142TEST(DeclPrinter, TestNamespace1) { 143 ASSERT_TRUE(PrintedDeclCXX98Matches( 144 "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) { 159 ASSERT_TRUE(PrintedDeclCXX98Matches( 160 "namespace Z { }" 161 "namespace A = Z;", 162 "A", 163 "namespace A = Z")); 164 // Should be: with semicolon 165} 166 167TEST(DeclPrinter, TestNamespaceAlias2) { 168 ASSERT_TRUE(PrintedDeclCXX98Matches( 169 "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) { 177 ASSERT_TRUE(PrintedDeclCXX98Matches( 178 "class A { int a; };", 179 "A", 180 "class A {\n}")); 181 // Should be: with semicolon, with { ... } 182} 183 184TEST(DeclPrinter, TestCXXRecordDecl2) { 185 ASSERT_TRUE(PrintedDeclCXX98Matches( 186 "struct A { int a; };", 187 "A", 188 "struct A {\n}")); 189 // Should be: with semicolon, with { ... } 190} 191 192TEST(DeclPrinter, TestCXXRecordDecl3) { 193 ASSERT_TRUE(PrintedDeclCXX98Matches( 194 "union A { int a; };", 195 "A", 196 "union A {\n}")); 197 // Should be: with semicolon, with { ... } 198} 199 200TEST(DeclPrinter, TestCXXRecordDecl4) { 201 ASSERT_TRUE(PrintedDeclCXX98Matches( 202 "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) { 210 ASSERT_TRUE(PrintedDeclCXX98Matches( 211 "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) { 219 ASSERT_TRUE(PrintedDeclCXX98Matches( 220 "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) { 228 ASSERT_TRUE(PrintedDeclCXX98Matches( 229 "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) { 237 ASSERT_TRUE(PrintedDeclCXX98Matches( 238 "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) { 246 ASSERT_TRUE(PrintedDeclCXX98Matches( 247 "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) { 255 ASSERT_TRUE(PrintedDeclCXX98Matches( 256 "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) { 264 ASSERT_TRUE(PrintedDeclCXX98Matches( 265 "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) { 274 ASSERT_TRUE(PrintedDeclCXX98Matches( 275 "void A();", 276 "A", 277 "void A()")); 278 // Should be: with semicolon 279} 280 281TEST(DeclPrinter, TestFunctionDecl2) { 282 ASSERT_TRUE(PrintedDeclCXX98Matches( 283 "void A() {}", 284 "A", 285 "void A()")); 286 // Should be: with semicolon 287} 288 289TEST(DeclPrinter, TestFunctionDecl3) { 290 ASSERT_TRUE(PrintedDeclCXX98Matches( 291 "void Z();" 292 "void A() { Z(); }", 293 "A", 294 "void A()")); 295 // Should be: with semicolon 296} 297 298TEST(DeclPrinter, TestFunctionDecl4) { 299 ASSERT_TRUE(PrintedDeclCXX98Matches( 300 "extern void A();", 301 "A", 302 "extern void A()")); 303 // Should be: with semicolon 304} 305 306TEST(DeclPrinter, TestFunctionDecl5) { 307 ASSERT_TRUE(PrintedDeclCXX98Matches( 308 "static void A();", 309 "A", 310 "static void A()")); 311 // Should be: with semicolon 312} 313 314TEST(DeclPrinter, TestFunctionDecl6) { 315 ASSERT_TRUE(PrintedDeclCXX98Matches( 316 "inline void A();", 317 "A", 318 "inline void A()")); 319 // Should be: with semicolon 320} 321 322TEST(DeclPrinter, TestFunctionDecl7) { 323 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 330TEST(DeclPrinter, TestFunctionDecl8) { 331 ASSERT_TRUE(PrintedDeclCXX98Matches( 332 "void A(int a);", 333 "A", 334 "void A(int a)")); 335 // Should be: with semicolon 336} 337 338TEST(DeclPrinter, TestFunctionDecl9) { 339 ASSERT_TRUE(PrintedDeclCXX98Matches( 340 "void A(...);", 341 "A", 342 "void A(...)")); 343 // Should be: with semicolon 344} 345 346TEST(DeclPrinter, TestFunctionDecl10) { 347 ASSERT_TRUE(PrintedDeclCXX98Matches( 348 "void A(int a, ...);", 349 "A", 350 "void A(int a, ...)")); 351 // Should be: with semicolon 352} 353 354TEST(DeclPrinter, TestFunctionDecl11) { 355 ASSERT_TRUE(PrintedDeclCXX98Matches( 356 "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 364TEST(DeclPrinter, TestFunctionDecl12) { 365 ASSERT_TRUE(PrintedDeclCXX98Matches( 366 "void A(int a, int b = 0);", 367 "A", 368 "void A(int a, int b = 0)")); 369 // Should be: with semicolon 370} 371 372TEST(DeclPrinter, TestFunctionDecl13) { 373 ASSERT_TRUE(PrintedDeclCXX98Matches( 374 "void (*A(int a))(int b);", 375 "A", 376 "void (*A(int a))(int)")); 377 // Should be: with semicolon, with parameter name (?) 378} 379 380TEST(DeclPrinter, TestFunctionDecl14) { 381 ASSERT_TRUE(PrintedDeclCXX98Matches( 382 "template<typename T>" 383 "void A(T t) { }" 384 "template<>" 385 "void A(int N) { }", 386 functionDecl(hasName("A"), isExplicitTemplateSpecialization()).bind("id"), 387 "void A(int N)")); 388 // WRONG; Should be: "template <> void A(int N);")); 389} 390 391 392TEST(DeclPrinter, TestCXXConstructorDecl1) { 393 ASSERT_TRUE(PrintedDeclCXX98Matches( 394 "struct A {" 395 " A();" 396 "};", 397 constructorDecl(ofClass(hasName("A"))).bind("id"), 398 "")); 399 // WRONG; Should be: "A();" 400} 401 402TEST(DeclPrinter, TestCXXConstructorDecl2) { 403 ASSERT_TRUE(PrintedDeclCXX98Matches( 404 "struct A {" 405 " A(int a);" 406 "};", 407 constructorDecl(ofClass(hasName("A"))).bind("id"), 408 "")); 409 // WRONG; Should be: "A(int a);" 410} 411 412TEST(DeclPrinter, TestCXXConstructorDecl3) { 413 ASSERT_TRUE(PrintedDeclCXX98Matches( 414 "struct A {" 415 " A(const A &a);" 416 "};", 417 constructorDecl(ofClass(hasName("A"))).bind("id"), 418 "")); 419 // WRONG; Should be: "A(const A &a);" 420} 421 422TEST(DeclPrinter, TestCXXConstructorDecl4) { 423 ASSERT_TRUE(PrintedDeclCXX98Matches( 424 "struct A {" 425 " A(const A &a, int = 0);" 426 "};", 427 constructorDecl(ofClass(hasName("A"))).bind("id"), 428 "")); 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 "};", 437 constructorDecl(ofClass(hasName("A"))).bind("id"), 438 "")); 439 // WRONG; Should be: "A(const A &&a);" 440} 441 442TEST(DeclPrinter, TestCXXConstructorDecl6) { 443 ASSERT_TRUE(PrintedDeclCXX98Matches( 444 "struct A {" 445 " explicit A(int a);" 446 "};", 447 constructorDecl(ofClass(hasName("A"))).bind("id"), 448 "")); 449 // WRONG; Should be: "explicit A(int a);" 450} 451 452TEST(DeclPrinter, TestCXXConstructorDecl7) { 453 ASSERT_TRUE(PrintedDeclCXX11Matches( 454 "struct A {" 455 " constexpr A();" 456 "};", 457 constructorDecl(ofClass(hasName("A"))).bind("id"), 458 "")); 459 // WRONG; Should be: "constexpr A();" 460} 461 462TEST(DeclPrinter, TestCXXConstructorDecl8) { 463 ASSERT_TRUE(PrintedDeclCXX11Matches( 464 "struct A {" 465 " A() = default;" 466 "};", 467 constructorDecl(ofClass(hasName("A"))).bind("id"), 468 "")); 469 // WRONG; Should be: "A() = default;" 470} 471 472TEST(DeclPrinter, TestCXXConstructorDecl9) { 473 ASSERT_TRUE(PrintedDeclCXX11Matches( 474 "struct A {" 475 " A() = delete;" 476 "};", 477 constructorDecl(ofClass(hasName("A"))).bind("id"), 478 " = delete")); 479 // WRONG; Should be: "A() = delete;" 480} 481 482TEST(DeclPrinter, TestCXXConstructorDecl10) { 483 ASSERT_TRUE(PrintedDeclCXX11Matches( 484 "template<typename... T>" 485 "struct A {" 486 " A(const A &a);" 487 "};", 488 constructorDecl(ofClass(hasName("A"))).bind("id"), 489 "")); 490 // WRONG; Should be: "A(const A &a);" 491} 492 493#if !defined(_MSC_VER) 494TEST(DeclPrinter, TestCXXConstructorDecl11) { 495 ASSERT_TRUE(PrintedDeclCXX11Matches( 496 "template<typename... T>" 497 "struct A : public T... {" 498 " A(T&&... ts) : T(ts)... {}" 499 "};", 500 constructorDecl(ofClass(hasName("A"))).bind("id"), 501 "A<T...>(T &&ts...) : T(ts)")); 502 // WRONG; Should be: "A(T&&... ts) : T(ts)..." 503} 504#endif 505 506TEST(DeclPrinter, TestCXXDestructorDecl1) { 507 ASSERT_TRUE(PrintedDeclCXX98Matches( 508 "struct A {" 509 " ~A();" 510 "};", 511 destructorDecl(ofClass(hasName("A"))).bind("id"), 512 "void ~A()")); 513 // WRONG; Should be: "~A();" 514} 515 516TEST(DeclPrinter, TestCXXDestructorDecl2) { 517 ASSERT_TRUE(PrintedDeclCXX98Matches( 518 "struct A {" 519 " virtual ~A();" 520 "};", 521 destructorDecl(ofClass(hasName("A"))).bind("id"), 522 "virtual void ~A()")); 523 // WRONG; Should be: "virtual ~A();" 524} 525 526TEST(DeclPrinter, TestCXXConversionDecl1) { 527 ASSERT_TRUE(PrintedDeclCXX98Matches( 528 "struct A {" 529 " operator int();" 530 "};", 531 methodDecl(ofClass(hasName("A"))).bind("id"), 532 "int operator int()")); 533 // WRONG; Should be: "operator int();" 534} 535 536TEST(DeclPrinter, TestCXXConversionDecl2) { 537 ASSERT_TRUE(PrintedDeclCXX98Matches( 538 "struct A {" 539 " operator bool();" 540 "};", 541 methodDecl(ofClass(hasName("A"))).bind("id"), 542 "bool operator _Bool()")); 543 // WRONG; Should be: "operator bool();" 544} 545 546TEST(DeclPrinter, TestCXXConversionDecl3) { 547 ASSERT_TRUE(PrintedDeclCXX98Matches( 548 "struct Z {};" 549 "struct A {" 550 " operator Z();" 551 "};", 552 methodDecl(ofClass(hasName("A"))).bind("id"), 553 "Z operator struct Z()")); 554 // WRONG; Should be: "operator Z();" 555} 556 557TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction1) { 558 ASSERT_TRUE(PrintedDeclCXX11Matches( 559 "namespace std { typedef decltype(sizeof(int)) size_t; }" 560 "struct Z {" 561 " void *operator new(std::size_t);" 562 "};", 563 methodDecl(ofClass(hasName("Z"))).bind("id"), 564 "void *operator new(std::size_t)")); 565 // Should be: with semicolon 566} 567 568TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction2) { 569 ASSERT_TRUE(PrintedDeclCXX11Matches( 570 "namespace std { typedef decltype(sizeof(int)) size_t; }" 571 "struct Z {" 572 " void *operator new[](std::size_t);" 573 "};", 574 methodDecl(ofClass(hasName("Z"))).bind("id"), 575 "void *operator new[](std::size_t)")); 576 // Should be: with semicolon 577} 578 579TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction3) { 580 ASSERT_TRUE(PrintedDeclCXX11Matches( 581 "struct Z {" 582 " void operator delete(void *);" 583 "};", 584 methodDecl(ofClass(hasName("Z"))).bind("id"), 585 "void operator delete(void *) noexcept")); 586 // Should be: with semicolon, without noexcept? 587} 588 589TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction4) { 590 ASSERT_TRUE(PrintedDeclCXX98Matches( 591 "struct Z {" 592 " void operator delete(void *);" 593 "};", 594 methodDecl(ofClass(hasName("Z"))).bind("id"), 595 "void operator delete(void *)")); 596 // Should be: with semicolon 597} 598 599TEST(DeclPrinter, TestCXXMethodDecl_AllocationFunction5) { 600 ASSERT_TRUE(PrintedDeclCXX11Matches( 601 "struct Z {" 602 " void operator delete[](void *);" 603 "};", 604 methodDecl(ofClass(hasName("Z"))).bind("id"), 605 "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 630 ASSERT_TRUE(PrintedDeclCXX98Matches( 631 Code, 632 methodDecl(ofClass(hasName("Z"))).bind("id"), 633 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 654 ASSERT_TRUE(PrintedDeclCXX98Matches( 655 Code, 656 methodDecl(ofClass(hasName("Z"))).bind("id"), 657 Expected)); 658 } 659} 660 661TEST(DeclPrinter, TestCXXMethodDecl1) { 662 ASSERT_TRUE(PrintedDeclCXX98Matches( 663 "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) { 672 ASSERT_TRUE(PrintedDeclCXX98Matches( 673 "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) { 682 ASSERT_TRUE(PrintedDeclCXX98Matches( 683 "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) { 696 ASSERT_TRUE(PrintedDeclCXX98Matches( 697 "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) { 706 ASSERT_TRUE(PrintedDeclCXX98Matches( 707 "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) { 716 ASSERT_TRUE(PrintedDeclCXX98Matches( 717 "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) { 726 ASSERT_TRUE(PrintedDeclCXX98Matches( 727 "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) { 736 ASSERT_TRUE(PrintedDeclCXX98Matches( 737 "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) { 766 ASSERT_TRUE(PrintedDeclCXX98Matches( 767 "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) { 776 ASSERT_TRUE(PrintedDeclCXX98Matches( 777 "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) { 786 ASSERT_TRUE(PrintedDeclCXX98Matches( 787 "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) { 838 ASSERT_TRUE(PrintedDeclCXX98Matches( 839 "char *const (*(*A)[5])(int);", 840 "A", 841 "char *const (*(*A)[5])(int)")); 842 // Should be: with semicolon 843} 844 845TEST(DeclPrinter, TestVarDecl2) { 846 ASSERT_TRUE(PrintedDeclCXX98Matches( 847 "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) { 862 ASSERT_TRUE(PrintedDeclCXX98Matches( 863 "template<typename T>" 864 "struct Z { T A; };", 865 "A", 866 "T A")); 867 // Should be: with semicolon 868} 869 870TEST(DeclPrinter, TestFieldDecl2) { 871 ASSERT_TRUE(PrintedDeclCXX98Matches( 872 "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) { 880 ASSERT_TRUE(PrintedDeclCXX98Matches( 881 "template<typename T>" 882 "struct A { T a; };", 883 classTemplateDecl(hasName("A")).bind("id"), 884 "template <typename T> struct A {\n}")); 885 // Should be: with semicolon, with { ... } 886} 887 888TEST(DeclPrinter, TestClassTemplateDecl2) { 889 ASSERT_TRUE(PrintedDeclCXX98Matches( 890 "template<typename T = int>" 891 "struct A { T a; };", 892 classTemplateDecl(hasName("A")).bind("id"), 893 "template <typename T = int> struct A {\n}")); 894 // Should be: with semicolon, with { ... } 895} 896 897TEST(DeclPrinter, TestClassTemplateDecl3) { 898 ASSERT_TRUE(PrintedDeclCXX98Matches( 899 "template<class T>" 900 "struct A { T a; };", 901 classTemplateDecl(hasName("A")).bind("id"), 902 "template <class T> struct A {\n}")); 903 // Should be: with semicolon, with { ... } 904} 905 906TEST(DeclPrinter, TestClassTemplateDecl4) { 907 ASSERT_TRUE(PrintedDeclCXX98Matches( 908 "template<typename T, typename U>" 909 "struct A { T a; U b; };", 910 classTemplateDecl(hasName("A")).bind("id"), 911 "template <typename T, typename U> struct A {\n}")); 912 // Should be: with semicolon, with { ... } 913} 914 915TEST(DeclPrinter, TestClassTemplateDecl5) { 916 ASSERT_TRUE(PrintedDeclCXX98Matches( 917 "template<int N>" 918 "struct A { int a[N]; };", 919 classTemplateDecl(hasName("A")).bind("id"), 920 "template <int N> struct A {\n}")); 921 // Should be: with semicolon, with { ... } 922} 923 924TEST(DeclPrinter, TestClassTemplateDecl6) { 925 ASSERT_TRUE(PrintedDeclCXX98Matches( 926 "template<int N = 42>" 927 "struct A { int a[N]; };", 928 classTemplateDecl(hasName("A")).bind("id"), 929 "template <int N = 42> struct A {\n}")); 930 // Should be: with semicolon, with { ... } 931} 932 933TEST(DeclPrinter, TestClassTemplateDecl7) { 934 ASSERT_TRUE(PrintedDeclCXX98Matches( 935 "typedef int MyInt;" 936 "template<MyInt N>" 937 "struct A { int a[N]; };", 938 classTemplateDecl(hasName("A")).bind("id"), 939 "template <MyInt N> struct A {\n}")); 940 // Should be: with semicolon, with { ... } 941} 942 943TEST(DeclPrinter, TestClassTemplateDecl8) { 944 ASSERT_TRUE(PrintedDeclCXX98Matches( 945 "template<template<typename U> class T> struct A { };", 946 classTemplateDecl(hasName("A")).bind("id"), 947 "template <template <typename U> class T> struct A {\n}")); 948 // Should be: with semicolon, with { ... } 949} 950 951TEST(DeclPrinter, TestClassTemplateDecl9) { 952 ASSERT_TRUE(PrintedDeclCXX98Matches( 953 "template<typename T> struct Z { };" 954 "template<template<typename U> class T = Z> struct A { };", 955 classTemplateDecl(hasName("A")).bind("id"), 956 "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; };", 964 classTemplateDecl(hasName("A")).bind("id"), 965 "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; };", 973 classTemplateDecl(hasName("A")).bind("id"), 974 "template <typename ... T> struct A : public T... {\n}")); 975 // Should be: with semicolon, with { ... }, without spaces before '...' 976} 977 978TEST(DeclPrinter, TestClassTemplatePartialSpecializationDecl1) { 979 ASSERT_TRUE(PrintedDeclCXX98Matches( 980 "template<typename T, typename U>" 981 "struct A { T a; U b; };" 982 "template<typename T>" 983 "struct A<T, int> { T a; };", 984 classTemplateSpecializationDecl().bind("id"), 985 "struct A {\n}")); 986 // WRONG; Should be: "template<typename T> struct A<T, int> { ... }" 987} 988 989TEST(DeclPrinter, TestClassTemplatePartialSpecializationDecl2) { 990 ASSERT_TRUE(PrintedDeclCXX98Matches( 991 "template<typename T>" 992 "struct A { T a; };" 993 "template<typename T>" 994 "struct A<T *> { T a; };", 995 classTemplateSpecializationDecl().bind("id"), 996 "struct A {\n}")); 997 // WRONG; Should be: "template<typename T> struct A<T *> { ... }" 998} 999 1000TEST(DeclPrinter, TestClassTemplateSpecializationDecl1) { 1001 ASSERT_TRUE(PrintedDeclCXX98Matches( 1002 "template<typename T>" 1003 "struct A { T a; };" 1004 "template<>" 1005 "struct A<int> { int a; };", 1006 classTemplateSpecializationDecl().bind("id"), 1007 "struct A {\n}")); 1008 // WRONG; Should be: "template<> struct A<int> { ... }" 1009} 1010 1011TEST(DeclPrinter, TestFunctionTemplateDecl1) { 1012 ASSERT_TRUE(PrintedDeclCXX98Matches( 1013 "template<typename T>" 1014 "void A(T &t);", 1015 functionTemplateDecl(hasName("A")).bind("id"), 1016 "template <typename T> void A(T &t)")); 1017 // Should be: with semicolon 1018} 1019 1020TEST(DeclPrinter, TestFunctionTemplateDecl2) { 1021 ASSERT_TRUE(PrintedDeclCXX98Matches( 1022 "template<typename T>" 1023 "void A(T &t) { }", 1024 functionTemplateDecl(hasName("A")).bind("id"), 1025 "template <typename T> void A(T &t)")); 1026 // Should be: with semicolon 1027} 1028 1029TEST(DeclPrinter, TestFunctionTemplateDecl3) { 1030 ASSERT_TRUE(PrintedDeclCXX11Matches( 1031 "template<typename... T>" 1032 "void A(T... a);", 1033 functionTemplateDecl(hasName("A")).bind("id"), 1034 "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) { 1041 ASSERT_TRUE(PrintedDeclCXX98Matches( 1042 "struct Z { template<typename T> void A(T t); };", 1043 functionTemplateDecl(hasName("A")).bind("id"), 1044 "template <typename T> void A(T t)")); 1045 // Should be: with semicolon 1046} 1047 1048TEST(DeclPrinter, TestFunctionTemplateDecl5) { 1049 ASSERT_TRUE(PrintedDeclCXX98Matches( 1050 "struct Z { template<typename T> void A(T t) {} };", 1051 functionTemplateDecl(hasName("A")).bind("id"), 1052 "template <typename T> void A(T t)")); 1053 // Should be: with semicolon 1054} 1055 1056TEST(DeclPrinter, TestFunctionTemplateDecl6) { 1057 ASSERT_TRUE(PrintedDeclCXX98Matches( 1058 "template<typename T >struct Z {" 1059 " template<typename U> void A(U t) {}" 1060 "};", 1061 functionTemplateDecl(hasName("A")).bind("id"), 1062 "template <typename U> void A(U t)")); 1063 // Should be: with semicolon 1064} 1065 1066TEST(DeclPrinter, TestTemplateArgumentList1) { 1067 ASSERT_TRUE(PrintedDeclCXX98Matches( 1068 "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) { 1077 ASSERT_TRUE(PrintedDeclCXX98Matches( 1078 "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) { 1088 ASSERT_TRUE(PrintedDeclCXX98Matches( 1089 "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) { 1108 ASSERT_TRUE(PrintedDeclCXX98Matches( 1109 "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) { 1117 ASSERT_TRUE(PrintedDeclCXX98Matches( 1118 "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) { 1127 ASSERT_TRUE(PrintedDeclCXX98Matches( 1128 "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) { 1138 ASSERT_TRUE(PrintedDeclCXX98Matches( 1139 "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) { 1149 ASSERT_TRUE(PrintedDeclCXX98Matches( 1150 "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) { 1158 ASSERT_TRUE(PrintedDeclCXX98Matches( 1159 "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) { 1167 ASSERT_TRUE(PrintedDeclCXX98Matches( 1168 "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) { 1176 ASSERT_TRUE(PrintedDeclCXX98Matches( 1177 "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} 1218 1219