[cfe-commits] r105606 - in /cfe/trunk: lib/CodeGen/Mangle.cpp test/CodeGenCXX/mangle-unnamed.cpp
Anders Carlsson
andersca at mac.com
Tue Jun 8 07:49:03 PDT 2010
Author: andersca
Date: Tue Jun 8 09:49:03 2010
New Revision: 105606
URL: http://llvm.org/viewvc/llvm-project?rev=105606&view=rev
Log:
Correctly mangle static variables of anonymous struct/union type.
Modified:
cfe/trunk/lib/CodeGen/Mangle.cpp
cfe/trunk/test/CodeGenCXX/mangle-unnamed.cpp
Modified: cfe/trunk/lib/CodeGen/Mangle.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/Mangle.cpp?rev=105606&r1=105605&r2=105606&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/Mangle.cpp (original)
+++ cfe/trunk/lib/CodeGen/Mangle.cpp Tue Jun 8 09:49:03 2010
@@ -598,6 +598,28 @@
mangleUnqualifiedName(0, Name, KnownArity);
}
+static const FieldDecl *FindFirstNamedDataMember(const RecordDecl *RD) {
+ assert(RD->isAnonymousStructOrUnion() &&
+ "Expected anonymous struct or union!");
+
+ for (RecordDecl::field_iterator I = RD->field_begin(), E = RD->field_end();
+ I != E; ++I) {
+ const FieldDecl *FD = *I;
+
+ if (FD->getIdentifier())
+ return FD;
+
+ if (const RecordType *RT = FD->getType()->getAs<RecordType>()) {
+ if (const FieldDecl *NamedDataMember =
+ FindFirstNamedDataMember(RT->getDecl()))
+ return NamedDataMember;
+ }
+ }
+
+ // We didn't find a named data member.
+ return 0;
+}
+
void CXXNameMangler::mangleUnqualifiedName(const NamedDecl *ND,
DeclarationName Name,
unsigned KnownArity) {
@@ -630,6 +652,28 @@
}
}
+ if (const VarDecl *VD = dyn_cast<VarDecl>(ND)) {
+ // We must have an anonymous union or struct declaration.
+ const RecordDecl *RD =
+ cast<RecordDecl>(VD->getType()->getAs<RecordType>()->getDecl());
+
+ // Itanium C++ ABI 5.1.2:
+ //
+ // For the purposes of mangling, the name of an anonymous union is
+ // considered to be the name of the first named data member found by a
+ // pre-order, depth-first, declaration-order walk of the data members of
+ // the anonymous union. If there is no such data member (i.e., if all of
+ // the data members in the union are unnamed), then there is no way for
+ // a program to refer to the anonymous union, and there is therefore no
+ // need to mangle its name.
+ const FieldDecl *FD = FindFirstNamedDataMember(RD);
+ assert(FD && "Didn't find a named data member!");
+ assert(FD->getIdentifier() && "Data member name isn't an identifier!");
+
+ mangleSourceName(FD->getIdentifier());
+ break;
+ }
+
// We must have an anonymous struct.
const TagDecl *TD = cast<TagDecl>(ND);
if (const TypedefDecl *D = TD->getTypedefForAnonDecl()) {
Modified: cfe/trunk/test/CodeGenCXX/mangle-unnamed.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/mangle-unnamed.cpp?rev=105606&r1=105605&r2=105606&view=diff
==============================================================================
--- cfe/trunk/test/CodeGenCXX/mangle-unnamed.cpp (original)
+++ cfe/trunk/test/CodeGenCXX/mangle-unnamed.cpp Tue Jun 8 09:49:03 2010
@@ -1,4 +1,4 @@
-// RUN: %clang_cc1 -emit-llvm-only -verify %s
+// RUN: %clang_cc1 -emit-llvm %s -o - -triple=x86_64-apple-darwin10 | FileCheck %s
struct S {
virtual ~S() { }
@@ -37,3 +37,35 @@
};
int f4() { return A().a(); }
+
+int f5() {
+ static union {
+ int a;
+ };
+
+ // CHECK: _ZZ2f5vE1a
+ return a;
+}
+
+int f6() {
+ static union {
+ union {
+ int : 1;
+ };
+ int b;
+ };
+
+ // CHECK: _ZZ2f6vE1b
+ return b;
+}
+
+int f7() {
+ static union {
+ union {
+ int b;
+ } a;
+ };
+
+ // CHECK: _ZZ2f7vE1a
+ return a.b;
+}
More information about the cfe-commits
mailing list