From: Anders Carlsson Date: Thu, 10 Dec 2009 03:14:39 +0000 (+0000) Subject: Mangle static variables inside Objective-C methods in Objective-C++. We currently... X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=7b06f6c20e124afa4d1fde85b1dd721462f2d912;p=clang Mangle static variables inside Objective-C methods in Objective-C++. We currently mangle them the same way as gcc does. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@91042 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/Mangle.cpp b/lib/CodeGen/Mangle.cpp index 2d86709f8f..d156ba549e 100644 --- a/lib/CodeGen/Mangle.cpp +++ b/lib/CodeGen/Mangle.cpp @@ -106,6 +106,8 @@ private: void mangleOperatorName(OverloadedOperatorKind OO, unsigned Arity); void mangleQualifiers(Qualifiers Quals); + void mangleObjCMethodName(const ObjCMethodDecl *MD); + // Declare manglers for every type class. #define ABSTRACT_TYPE(CLASS, PARENT) #define NON_CANONICAL_TYPE(CLASS, PARENT) @@ -325,7 +327,7 @@ void CXXNameMangler::mangleName(const NamedDecl *ND) { return; } - if (isa(DC)) { + if (isa(DC) || isa(DC)) { mangleLocalName(ND); return; } @@ -539,7 +541,12 @@ void CXXNameMangler::mangleLocalName(const NamedDecl *ND) { // := Z E s [] // := _ Out << 'Z'; - mangleFunctionEncoding(cast(ND->getDeclContext())); + + if (const ObjCMethodDecl *MD = dyn_cast(ND->getDeclContext())) + mangleObjCMethodName(MD); + else + mangleFunctionEncoding(cast(ND->getDeclContext())); + Out << 'E'; mangleSourceName(ND->getIdentifier()); } @@ -550,7 +557,6 @@ void CXXNameMangler::manglePrefix(const DeclContext *DC) { // ::= // ::= # empty // ::= - // FIXME: We only handle mangling of namespaces and classes at the moment. while (isa(DC)) DC = DC->getParent(); @@ -703,6 +709,21 @@ void CXXNameMangler::mangleQualifiers(Qualifiers Quals) { // FIXME: For now, just drop all extension qualifiers on the floor. } +void CXXNameMangler::mangleObjCMethodName(const ObjCMethodDecl *MD) { + llvm::SmallString<64> Name; + llvm::raw_svector_ostream OS(Name); + + const ObjCContainerDecl *CD = + dyn_cast(MD->getDeclContext()); + assert (CD && "Missing container decl in GetNameForMethod"); + OS << (MD->isInstanceMethod() ? '-' : '+') << '[' << CD->getName(); + if (const ObjCCategoryImplDecl *CID = dyn_cast(CD)) + OS << '(' << CID->getNameAsString() << ')'; + OS << ' ' << MD->getSelector().getAsString() << ']'; + + Out << OS.str().size() << OS.str(); +} + void CXXNameMangler::mangleType(QualType T) { // Only operate on the canonical type! T = Context.getASTContext().getCanonicalType(T); diff --git a/test/CodeGenObjCXX/mangle.mm b/test/CodeGenObjCXX/mangle.mm new file mode 100644 index 0000000000..00df14b689 --- /dev/null +++ b/test/CodeGenObjCXX/mangle.mm @@ -0,0 +1,32 @@ +// RUN: clang-cc %s -triple=x86_64-apple-darwin10 -emit-llvm -o - | FileCheck %s + +// CHECK: @"_ZZ11+[A shared]E1a" = internal global +// CHECK: @"_ZZ11-[A(Foo) f]E1a" = internal global + +@interface A +@end + +@implementation A + ++ (A *)shared { + static A* a; + + return a; +} + +@end + +@interface A(Foo) +@end + +@implementation A(Foo) +- (int)f { + // FIXME: Add a member function to s and make sure that it's mangled correctly. + struct s { + }; + + static s a; + + return 0; +} +@end