diff options
-rw-r--r-- | lib/Rewrite/RewriteModernObjC.cpp | 30 | ||||
-rw-r--r-- | test/Rewriter/objc-modern-metadata-visibility.mm | 34 |
2 files changed, 54 insertions, 10 deletions
diff --git a/lib/Rewrite/RewriteModernObjC.cpp b/lib/Rewrite/RewriteModernObjC.cpp index acb0ac73f2..5b9a12fb9b 100644 --- a/lib/Rewrite/RewriteModernObjC.cpp +++ b/lib/Rewrite/RewriteModernObjC.cpp @@ -3217,16 +3217,14 @@ void RewriteModernObjC::RewriteIvarOffsetSymbols(ObjCInterfaceDecl *CDecl, e = Ivars.end(); i != e; i++) { ObjCIvarDecl *IvarDecl = (*i); Result += "\n"; - Result += "extern \"C\" "; if (LangOpts.MicrosoftExt) Result += "__declspec(allocate(\".objc_ivar$B\")) "; + Result += "extern \"C\" "; if (LangOpts.MicrosoftExt && IvarDecl->getAccessControl() != ObjCIvarDecl::Private && - IvarDecl->getAccessControl() != ObjCIvarDecl::Package) { - const ObjCInterfaceDecl *CDecl = IvarDecl->getContainingInterface(); - if (CDecl->getImplementation()) - Result += "__declspec(dllexport) "; - } + IvarDecl->getAccessControl() != ObjCIvarDecl::Package) + Result += "__declspec(dllimport) "; + Result += "unsigned long "; WriteInternalIvarName(CDecl, IvarDecl, Result); Result += ";"; @@ -5440,7 +5438,7 @@ static void WriteModernMetadataDeclarations(ASTContext *Context, std::string &Re Result += "};\n"; Result += "extern \"C\" __declspec(dllimport) struct objc_cache _objc_empty_cache;\n"; - + Result += "#pragma warning(disable:4273)\n"; meta_data_declared = true; } @@ -5682,6 +5680,9 @@ static void Write_class_t(ASTContext *Context, std::string &Result, Result += "extern \"C\" "; if (CDecl->getImplementation()) Result += "__declspec(dllexport) "; + else + Result += "__declspec(dllimport) "; + Result += "struct _class_t OBJC_CLASS_$_"; Result += CDecl->getNameAsString(); Result += ";\n"; @@ -5692,6 +5693,9 @@ static void Write_class_t(ASTContext *Context, std::string &Result, Result += "extern \"C\" "; if (CDecl->getSuperClass()->getImplementation()) Result += "__declspec(dllexport) "; + else + Result += "__declspec(dllimport) "; + Result += "struct _class_t "; Result += VarName; Result += CDecl->getSuperClass()->getNameAsString(); @@ -5701,6 +5705,9 @@ static void Write_class_t(ASTContext *Context, std::string &Result, Result += "extern \"C\" "; if (RootClass->getImplementation()) Result += "__declspec(dllexport) "; + else + Result += "__declspec(dllimport) "; + Result += "struct _class_t "; Result += VarName; Result += RootClass->getNameAsString(); @@ -5708,7 +5715,8 @@ static void Write_class_t(ASTContext *Context, std::string &Result, } } - Result += "\n__declspec(dllexport) struct _class_t "; Result += VarName; Result += CDecl->getNameAsString(); + Result += "\nextern \"C\" __declspec(dllexport) struct _class_t "; + Result += VarName; Result += CDecl->getNameAsString(); Result += " __attribute__ ((used, section (\"__DATA,__objc_data\"))) = {\n"; Result += "\t"; if (metaclass) { @@ -5807,6 +5815,8 @@ static void Write_category_t(RewriteModernObjC &RewriteObj, ASTContext *Context, Result += "extern \"C\" "; if (ClassDecl->getImplementation()) Result += "__declspec(dllexport) "; + else + Result += "__declspec(dllimport) "; Result += "struct _class_t "; Result += "OBJC_CLASS_$_"; Result += ClassName; @@ -5921,9 +5931,9 @@ static void Write_IvarOffsetVar(ASTContext *Context, if (!Context->getLangOpts().MicrosoftExt || IvarDecl->getAccessControl() == ObjCIvarDecl::Private || IvarDecl->getAccessControl() == ObjCIvarDecl::Package) - Result += "unsigned long int "; + Result += "extern \"C\" unsigned long int "; else - Result += "__declspec(dllexport) unsigned long int "; + Result += "extern \"C\" __declspec(dllexport) unsigned long int "; WriteInternalIvarName(CDecl, IvarDecl, Result); Result += " __attribute__ ((used, section (\"__DATA,__objc_ivar\")))"; Result += " = "; diff --git a/test/Rewriter/objc-modern-metadata-visibility.mm b/test/Rewriter/objc-modern-metadata-visibility.mm new file mode 100644 index 0000000000..dc145b79a0 --- /dev/null +++ b/test/Rewriter/objc-modern-metadata-visibility.mm @@ -0,0 +1,34 @@ +// RUN: %clang_cc1 -E %s -o %t.mm +// RUN: %clang_cc1 -x objective-c++ -fblocks -fms-extensions -rewrite-objc %t.mm -o - | FileCheck %s +// rdar://11144048 + +@class NSString; + +@interface NSObject { + Class isa; +} +@end + +@interface Sub : NSObject { + int subIvar; + NSString *nsstring; +@private + id PrivateIvar; +} +@end + +@implementation Sub +- (id) MyNSString { return subIvar ? PrivateIvar : nsstring; } +@end + +// CHECK: __declspec(allocate(".objc_ivar$B")) extern "C" __declspec(dllimport) unsigned long OBJC_IVAR_$_Sub$subIvar; +// CHECK: __declspec(allocate(".objc_ivar$B")) extern "C" unsigned long OBJC_IVAR_$_Sub$PrivateIvar; +// CHECK: __declspec(allocate(".objc_ivar$B")) extern "C" __declspec(dllimport) unsigned long OBJC_IVAR_$_Sub$nsstring; +// CHECK: #pragma warning(disable:4273) +// CHECK: __declspec(allocate(".objc_ivar$B")) extern "C" __declspec(dllexport) unsigned long int OBJC_IVAR_$_Sub$subIvar +// CHECK: __declspec(allocate(".objc_ivar$B")) extern "C" __declspec(dllexport) unsigned long int OBJC_IVAR_$_Sub$nsstring +// CHECK: __declspec(allocate(".objc_ivar$B")) extern "C" unsigned long int OBJC_IVAR_$_Sub$PrivateIvar +// CHECK: extern "C" __declspec(dllimport) struct _class_t OBJC_METACLASS_$_NSObject; +// CHECK: extern "C" __declspec(dllexport) struct _class_t OBJC_METACLASS_$_Sub +// CHECK: extern "C" __declspec(dllimport) struct _class_t OBJC_CLASS_$_NSObject; +// CHECK: extern "C" __declspec(dllexport) struct _class_t OBJC_CLASS_$_Sub |