]> granicus.if.org Git - clang/commitdiff
[modules] Teach clang how to merge typedef over anonymous structs in C mode.
authorVassil Vassilev <v.g.vassilev@gmail.com>
Sat, 1 Jul 2017 20:44:49 +0000 (20:44 +0000)
committerVassil Vassilev <v.g.vassilev@gmail.com>
Sat, 1 Jul 2017 20:44:49 +0000 (20:44 +0000)
In C mode clang fails to merge the textually included definition with the one imported from a module. The C lookup rules fail to find the imported definition because its linkage is internal in non C++ mode.

This patch reinstates some of the ODR merging rules for typedefs of anonymous tags for languages other than C++.

Patch by Raphael Isemann and me (D34510).

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@306964 91177308-0d34-0410-b5e6-96231b3b80d8

lib/AST/Decl.cpp
lib/Sema/SemaDecl.cpp
test/Index/usrs.m

index 267c6992af89784ed0c3ba2f6eedbded401f8de2..24d998391257eac0bc71c14a7eb36b17020cbbbd 100644 (file)
@@ -1259,8 +1259,7 @@ static LinkageInfo computeLVForDecl(const NamedDecl *D,
     case Decl::TypeAlias:
       // A typedef declaration has linkage if it gives a type a name for
       // linkage purposes.
-      if (!D->getASTContext().getLangOpts().CPlusPlus ||
-          !cast<TypedefNameDecl>(D)
+      if (!cast<TypedefNameDecl>(D)
                ->getAnonDeclWithTypedefName(/*AnyRedecl*/true))
         return LinkageInfo::none();
       break;
index ef8a408f90de9ce99b05c90adb4766856f5f33f7..ab2661cd7131b9a1f1b591bb5866c21335d1fde7 100644 (file)
@@ -1998,8 +1998,7 @@ static void filterNonConflictingPreviousTypedefDecls(Sema &S,
 
       // If both declarations give a tag declaration a typedef name for linkage
       // purposes, then they declare the same entity.
-      if (S.getLangOpts().CPlusPlus &&
-          OldTD->getAnonDeclWithTypedefName(/*AnyRedecl*/true) &&
+      if (OldTD->getAnonDeclWithTypedefName(/*AnyRedecl*/true) &&
           Decl->getAnonDeclWithTypedefName())
         continue;
     }
@@ -2117,7 +2116,7 @@ void Sema::MergeTypedefNameDecl(Scope *S, TypedefNameDecl *New,
     auto *OldTag = OldTD->getAnonDeclWithTypedefName(/*AnyRedecl*/true);
     auto *NewTag = New->getAnonDeclWithTypedefName();
     NamedDecl *Hidden = nullptr;
-    if (getLangOpts().CPlusPlus && OldTag && NewTag &&
+    if (OldTag && NewTag &&
         OldTag->getCanonicalDecl() != NewTag->getCanonicalDecl() &&
         !hasVisibleDefinition(OldTag, &Hidden)) {
       // There is a definition of this tag, but it is not visible. Use it
index 92c3a3fafee2caf8ba03c9a8102fb40ce4897503..d0a860e1afadff7ff123e36ef0ec240efcc6ad4d 100644 (file)
@@ -119,7 +119,7 @@ int test_multi_declaration(void) {
 // CHECK: usrs.m c:@SA@MyStruct Extent=[15:9 - 18:2]
 // CHECK: usrs.m c:@SA@MyStruct@FI@wa Extent=[16:3 - 16:9]
 // CHECK: usrs.m c:@SA@MyStruct@FI@moo Extent=[17:3 - 17:10]
-// CHECK: usrs.m c:usrs.m@T@MyStruct Extent=[15:1 - 18:11]
+// CHECK: usrs.m c:@T@MyStruct Extent=[15:1 - 18:11]
 // CHECK: usrs.m c:@E@Pizza Extent=[20:1 - 23:2]
 // CHECK: usrs.m c:@E@Pizza@CHEESE Extent=[21:3 - 21:9]
 // CHECK: usrs.m c:@E@Pizza@MUSHROOMS Extent=[22:3 - 22:12]