danix800 created this revision.
danix800 added a project: clang.
Herald added a subscriber: martong.
Herald added a reviewer: a.sidorin.
Herald added a reviewer: shafik.
Herald added a project: All.
danix800 requested review of this revision.
Herald added a subscriber: cfe-commits.

Revision https://reviews.llvm.org/D154764 is still not complete. An extra 
sorting is needed
for keeping lexical order of all imported decls within a record. The final 
algorithm could be
summarized as the following:

1. Import all fields that'll be part of the layout;
2. Sort these fields to ensure correct layout;
3. Import everything else;
4. Final sort for correct lexical order.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D156093

Files:
  clang/lib/AST/ASTImporter.cpp
  clang/unittests/AST/ASTImporterTest.cpp

Index: clang/unittests/AST/ASTImporterTest.cpp
===================================================================
--- clang/unittests/AST/ASTImporterTest.cpp
+++ clang/unittests/AST/ASTImporterTest.cpp
@@ -1462,10 +1462,10 @@
       MatchVerifier<Decl>{}.match(To->getTranslationUnitDecl(), Pattern));
 }
 
-AST_MATCHER_P(RecordDecl, hasFieldOrder, std::vector<StringRef>, Order) {
+AST_MATCHER_P(RecordDecl, hasLexicalOrder, std::vector<StringRef>, Order) {
   size_t Index = 0;
   for (Decl *D : Node.decls()) {
-    if (isa<FieldDecl>(D) || isa<IndirectFieldDecl>(D)) {
+    if (isa<FieldDecl>(D) || isa<IndirectFieldDecl>(D) || !D->isImplicit()) {
       auto *ND = cast<NamedDecl>(D);
       if (Index == Order.size())
         return false;
@@ -1513,8 +1513,8 @@
                       Lang_CXX11, "", Lang_CXX11);
 
   MatchVerifier<Decl> Verifier;
-  ASSERT_TRUE(Verifier.match(From, cxxRecordDecl(hasFieldOrder({"a", "b"}))));
-  EXPECT_TRUE(Verifier.match(To, cxxRecordDecl(hasFieldOrder({"a", "b"}))));
+  ASSERT_TRUE(Verifier.match(From, cxxRecordDecl(hasLexicalOrder({"a", "b"}))));
+  EXPECT_TRUE(Verifier.match(To, cxxRecordDecl(hasLexicalOrder({"a", "b"}))));
 }
 
 TEST_P(ASTImporterOptionSpecificTestBase,
@@ -1532,11 +1532,30 @@
       )s",
       Lang_CXX11, "", Lang_CXX11);
 
+  auto Pattern = cxxRecordDecl(hasLexicalOrder({"a", "b", "c"}));
   MatchVerifier<Decl> Verifier;
-  ASSERT_TRUE(
-      Verifier.match(From, cxxRecordDecl(hasFieldOrder({"a", "b", "c"}))));
-  EXPECT_TRUE(
-      Verifier.match(To, cxxRecordDecl(hasFieldOrder({"a", "b", "c"}))));
+  ASSERT_TRUE(Verifier.match(From, Pattern));
+  EXPECT_TRUE(Verifier.match(To, Pattern));
+}
+
+TEST_P(ASTImporterOptionSpecificTestBase, CXXRecordDeclCorrectLexicalOrder) {
+  Decl *From, *To;
+  std::tie(From, To) = getImportedDecl(
+      R"s(
+      struct declToImport {
+          int a = c;
+          void g() { h(); }
+          int b = 1;
+          void h();
+          int c = 2;
+      };
+      )s",
+      Lang_CXX11, "", Lang_CXX11);
+
+  auto Pattern = cxxRecordDecl(hasLexicalOrder({"a", "g", "b", "h", "c"}));
+  MatchVerifier<Decl> Verifier;
+  ASSERT_TRUE(Verifier.match(From, Pattern));
+  EXPECT_TRUE(Verifier.match(To, Pattern));
 }
 
 TEST_P(ASTImporterOptionSpecificTestBase,
@@ -1557,11 +1576,17 @@
       )s",
       Lang_CXX11, "", Lang_CXX11);
 
+  auto Pattern = cxxRecordDecl(hasLexicalOrder({
+    "a",
+    "" /*anony union*/,
+    "" /* implicit field */,
+    "b" /* indirect */,
+    "c" /* indirect */,
+    "d"
+  }));
   MatchVerifier<Decl> Verifier;
-  ASSERT_TRUE(Verifier.match(
-      From, cxxRecordDecl(hasFieldOrder({"a", "", "b", "c", "d"}))));
-  EXPECT_TRUE(Verifier.match(
-      To, cxxRecordDecl(hasFieldOrder({"a", "", "b", "c", "d"}))));
+  ASSERT_TRUE(Verifier.match(From, Pattern));
+  EXPECT_TRUE(Verifier.match(To, Pattern));
 }
 
 TEST_P(ASTImporterOptionSpecificTestBase, ShouldImportImplicitCXXRecordDecl) {
@@ -3007,7 +3032,7 @@
              "  int a = 5;"
              "};",
              Lang_CXX11, "", Lang_CXX11, Verifier,
-             recordDecl(hasFieldOrder({"b", "a"})));
+             recordDecl(hasLexicalOrder({"b", "a"})));
 }
 
 const internal::VariadicDynCastAllOfMatcher<Expr, DependentScopeDeclRefExpr>
Index: clang/lib/AST/ASTImporter.cpp
===================================================================
--- clang/lib/AST/ASTImporter.cpp
+++ clang/lib/AST/ASTImporter.cpp
@@ -1942,6 +1942,16 @@
                                                 ImportedOrErr.takeError());
   }
 
+  // Final round to re-order everything
+  for (auto *D : FromDC->decls()) {
+    assert(D && "DC contains a null decl");
+    if (Decl *ToD = Importer.GetAlreadyImportedOrNull(D); ToD &&
+        ToDC == ToD->getLexicalDeclContext() && ToDC->containsDecl(ToD)) {
+      ToDC->removeDecl(ToD);
+      ToDC->addDeclInternal(ToD);
+    }
+  }
+
   return ChildErrors;
 }
 
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to