summaryrefslogtreecommitdiffstats
path: root/clang/unittests/AST/ASTImporterTest.cpp
diff options
context:
space:
mode:
authorBalazs Keri <1.int32@gmail.com>2018-07-16 12:16:39 +0000
committerBalazs Keri <1.int32@gmail.com>2018-07-16 12:16:39 +0000
commit1d20cc20f672ed7eb5f94584905ba6e902f669eb (patch)
tree14466e68ad4d6a6dfe5335af45864b9e38dfbd98 /clang/unittests/AST/ASTImporterTest.cpp
parentc3d8002c2e1b41a05095f6a0f2e720fa9bb63c00 (diff)
downloadbcm5719-llvm-1d20cc20f672ed7eb5f94584905ba6e902f669eb.tar.gz
bcm5719-llvm-1d20cc20f672ed7eb5f94584905ba6e902f669eb.zip
[ASTImporter] Import implicit methods of existing class.
Summary: When an already existing class is encountered during import, check if it has implicit methods that are missing in the existing one, and import these. The to-be-imported code may use the same class in different way than the existing (before the import) code. This may result in that there are implicit methods that are not generated for the existing code. Reviewers: a.sidorin, a_sidorin Reviewed By: a_sidorin Subscribers: a_sidorin, martong, cfe-commits Differential Revision: https://reviews.llvm.org/D49245 llvm-svn: 337162
Diffstat (limited to 'clang/unittests/AST/ASTImporterTest.cpp')
-rw-r--r--clang/unittests/AST/ASTImporterTest.cpp111
1 files changed, 111 insertions, 0 deletions
diff --git a/clang/unittests/AST/ASTImporterTest.cpp b/clang/unittests/AST/ASTImporterTest.cpp
index cd8254c0a04..8aff6b5df9a 100644
--- a/clang/unittests/AST/ASTImporterTest.cpp
+++ b/clang/unittests/AST/ASTImporterTest.cpp
@@ -2343,6 +2343,117 @@ TEST_P(ImportExpr, UnresolvedMemberExpr) {
compoundStmt(has(callExpr(has(unresolvedMemberExpr())))))))));
}
+class ImportImplicitMethods : public ASTImporterTestBase {
+public:
+ static constexpr auto DefaultCode = R"(
+ struct A { int x; };
+ void f() {
+ A a;
+ A a1(a);
+ A a2(A{});
+ a = a1;
+ a = A{};
+ a.~A();
+ })";
+
+ template <typename MatcherType>
+ void testImportOf(
+ const MatcherType &MethodMatcher, const char *Code = DefaultCode) {
+ test(MethodMatcher, Code, /*ExpectedCount=*/1u);
+ }
+
+ template <typename MatcherType>
+ void testNoImportOf(
+ const MatcherType &MethodMatcher, const char *Code = DefaultCode) {
+ test(MethodMatcher, Code, /*ExpectedCount=*/0u);
+ }
+
+private:
+ template <typename MatcherType>
+ void test(const MatcherType &MethodMatcher,
+ const char *Code, unsigned int ExpectedCount) {
+ auto ClassMatcher = cxxRecordDecl(unless(isImplicit()));
+
+ Decl *ToTU = getToTuDecl(Code, Lang_CXX11);
+ auto *ToClass = FirstDeclMatcher<CXXRecordDecl>().match(
+ ToTU, ClassMatcher);
+
+ ASSERT_EQ(DeclCounter<CXXMethodDecl>().match(ToClass, MethodMatcher), 1);
+
+ {
+ CXXMethodDecl *Method =
+ FirstDeclMatcher<CXXMethodDecl>().match(ToClass, MethodMatcher);
+ ToClass->removeDecl(Method);
+ }
+
+ ASSERT_EQ(DeclCounter<CXXMethodDecl>().match(ToClass, MethodMatcher), 0);
+
+ Decl *ImportedClass = nullptr;
+ {
+ Decl *FromTU = getTuDecl(Code, Lang_CXX11, "input1.cc");
+ auto *FromClass = FirstDeclMatcher<CXXRecordDecl>().match(
+ FromTU, ClassMatcher);
+ ImportedClass = Import(FromClass, Lang_CXX11);
+ }
+
+ EXPECT_EQ(ToClass, ImportedClass);
+ EXPECT_EQ(DeclCounter<CXXMethodDecl>().match(ToClass, MethodMatcher),
+ ExpectedCount);
+ }
+};
+
+TEST_P(ImportImplicitMethods, DefaultConstructor) {
+ testImportOf(cxxConstructorDecl(isDefaultConstructor()));
+}
+
+TEST_P(ImportImplicitMethods, CopyConstructor) {
+ testImportOf(cxxConstructorDecl(isCopyConstructor()));
+}
+
+TEST_P(ImportImplicitMethods, MoveConstructor) {
+ testImportOf(cxxConstructorDecl(isMoveConstructor()));
+}
+
+TEST_P(ImportImplicitMethods, Destructor) {
+ testImportOf(cxxDestructorDecl());
+}
+
+TEST_P(ImportImplicitMethods, CopyAssignment) {
+ testImportOf(cxxMethodDecl(isCopyAssignmentOperator()));
+}
+
+TEST_P(ImportImplicitMethods, MoveAssignment) {
+ testImportOf(cxxMethodDecl(isMoveAssignmentOperator()));
+}
+
+TEST_P(ImportImplicitMethods, DoNotImportUserProvided) {
+ auto Code = R"(
+ struct A { A() { int x; } };
+ )";
+ testNoImportOf(cxxConstructorDecl(isDefaultConstructor()), Code);
+}
+
+TEST_P(ImportImplicitMethods, DoNotImportDefault) {
+ auto Code = R"(
+ struct A { A() = default; };
+ )";
+ testNoImportOf(cxxConstructorDecl(isDefaultConstructor()), Code);
+}
+
+TEST_P(ImportImplicitMethods, DoNotImportDeleted) {
+ auto Code = R"(
+ struct A { A() = delete; };
+ )";
+ testNoImportOf(cxxConstructorDecl(isDefaultConstructor()), Code);
+}
+
+TEST_P(ImportImplicitMethods, DoNotImportOtherMethod) {
+ auto Code = R"(
+ struct A { void f() { } };
+ )";
+ testNoImportOf(cxxMethodDecl(hasName("f")), Code);
+}
+
TEST_P(ASTImporterTestBase, ImportOfEquivalentRecord) {
Decl *ToR1;
{
OpenPOWER on IntegriCloud