blob: f775a31e59b21b999218758f0ff88af9dbb255df [file] [log] [blame]
David Zarzyckid488daa2018-04-19 18:19:02 +00001//===- unittest/Tooling/RecursiveASTVisitorTests/ConstructExpr.cpp --------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#include "TestVisitor.h"
11
12using namespace clang;
13
14namespace {
15
16/// \brief A visitor that optionally includes implicit code and matches
17/// CXXConstructExpr.
18///
19/// The name recorded for the match is the name of the class whose constructor
20/// is invoked by the CXXConstructExpr, not the name of the class whose
21/// constructor the CXXConstructExpr is contained in.
22class ConstructExprVisitor
23 : public ExpectedLocationVisitor<ConstructExprVisitor> {
24public:
25 ConstructExprVisitor() : ShouldVisitImplicitCode(false) {}
26
27 bool shouldVisitImplicitCode() const { return ShouldVisitImplicitCode; }
28
29 void setShouldVisitImplicitCode(bool NewValue) {
30 ShouldVisitImplicitCode = NewValue;
31 }
32
33 bool VisitCXXConstructExpr(CXXConstructExpr* Expr) {
34 if (const CXXConstructorDecl* Ctor = Expr->getConstructor()) {
35 if (const CXXRecordDecl* Class = Ctor->getParent()) {
36 Match(Class->getName(), Expr->getLocation());
37 }
38 }
39 return true;
40 }
41
42 private:
43 bool ShouldVisitImplicitCode;
44};
45
46TEST(RecursiveASTVisitor, CanVisitImplicitMemberInitializations) {
47 ConstructExprVisitor Visitor;
48 Visitor.setShouldVisitImplicitCode(true);
49 Visitor.ExpectMatch("WithCtor", 2, 8);
50 // Simple has a constructor that implicitly initializes 'w'. Test
51 // that a visitor that visits implicit code visits that initialization.
52 // Note: Clang lazily instantiates implicit declarations, so we need
53 // to use them in order to force them to appear in the AST.
54 EXPECT_TRUE(Visitor.runOver(
55 "struct WithCtor { WithCtor(); }; \n"
56 "struct Simple { WithCtor w; }; \n"
57 "int main() { Simple s; }\n"));
58}
59
60// The same as CanVisitImplicitMemberInitializations, but checking that the
61// visits are omitted when the visitor does not include implicit code.
62TEST(RecursiveASTVisitor, CanSkipImplicitMemberInitializations) {
63 ConstructExprVisitor Visitor;
64 Visitor.setShouldVisitImplicitCode(false);
65 Visitor.DisallowMatch("WithCtor", 2, 8);
66 // Simple has a constructor that implicitly initializes 'w'. Test
67 // that a visitor that skips implicit code skips that initialization.
68 // Note: Clang lazily instantiates implicit declarations, so we need
69 // to use them in order to force them to appear in the AST.
70 EXPECT_TRUE(Visitor.runOver(
71 "struct WithCtor { WithCtor(); }; \n"
72 "struct Simple { WithCtor w; }; \n"
73 "int main() { Simple s; }\n"));
74}
75
76} // end anonymous namespace