diff --git a/include/clang/Basic/Attr.td b/include/clang/Basic/Attr.td
index c7a797c..dc22b27 100644
--- a/include/clang/Basic/Attr.td
+++ b/include/clang/Basic/Attr.td
@@ -2023,7 +2023,8 @@ def DLLExport : InheritableAttr, TargetSpecificAttr<TargetWindows> {
 
 def DLLImport : InheritableAttr, TargetSpecificAttr<TargetWindows> {
   let Spellings = [Declspec<"dllimport">, GCC<"dllimport">];
-  let Subjects = SubjectList<[Function, Var, CXXRecord]>;
+  let Subjects = SubjectList<[Function, Var, CXXRecord, ObjCInterface], WarnDiag,
+                             "ExpectedFunctionVariableOrClass">;
   let Documentation = [Undocumented];
 }
 
diff --git a/lib/CodeGen/CGBlocks.cpp b/lib/CodeGen/CGBlocks.cpp
index ea164aa..9d2b2f9 100644
--- a/lib/CodeGen/CGBlocks.cpp
+++ b/lib/CodeGen/CGBlocks.cpp
@@ -2334,5 +2334,9 @@ llvm::Constant *CodeGenModule::getNSConcreteStackBlock() {
                                                Int8PtrTy->getPointerTo(),
                                                nullptr);
   configureBlocksRuntimeObject(*this, NSConcreteStackBlock);
+  if (getContext().getLangOpts().MSVCCompat) {
+    auto *GV = cast<llvm::GlobalValue>(NSConcreteStackBlock->stripPointerCasts());
+    GV->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
+  }
   return NSConcreteStackBlock;  
 }
diff --git a/lib/CodeGen/CGObjCGNU.cpp b/lib/CodeGen/CGObjCGNU.cpp
index bbe1b8b..dcb3a7d 100644
--- a/lib/CodeGen/CGObjCGNU.cpp
+++ b/lib/CodeGen/CGObjCGNU.cpp
@@ -472,7 +472,7 @@ protected:
 
   /// Emits a pointer to the named class
   virtual llvm::Value *GetClassNamed(CodeGenFunction &CGF,
-                                     const std::string &Name, bool isWeak);
+                                     StringRef Name, bool isWeak, bool isDLLImport);
 
   /// Looks up the method for sending a message to the specified object.  This
   /// mechanism differs between the GCC and GNU runtimes, so this method must be
@@ -866,21 +866,24 @@ protected:
     }
 
   llvm::Value *GetClassNamed(CodeGenFunction &CGF,
-                             const std::string &Name, bool isWeak) override {
+                             StringRef Name, bool isWeak, bool isDLLImport) override {
     if (isWeak)
-      return CGObjCGNU::GetClassNamed(CGF, Name, isWeak);
+      return CGObjCGNU::GetClassNamed(CGF, Name, isWeak, isDLLImport);
 
     EmitClassRef(Name);
 
-    std::string SymbolName = "_OBJC_CLASS_" + Name;
+    std::string SymbolName = "_OBJC_CLASS_" + Name.str();
 
     llvm::GlobalVariable *ClassSymbol = TheModule.getGlobalVariable(SymbolName);
 
-    if (!ClassSymbol)
+    if (!ClassSymbol) {
       ClassSymbol = new llvm::GlobalVariable(TheModule, LongTy, false,
                                              llvm::GlobalValue::ExternalLinkage,
                                              nullptr, SymbolName);
-
+      if (isDLLImport)
+        ClassSymbol->setDLLStorageClass(llvm::GlobalValue::DLLImportStorageClass);
+    }
+    
     return ClassSymbol;
   }
 
@@ -1054,8 +1057,8 @@ CGObjCGNU::CGObjCGNU(CodeGenModule &cgm, unsigned runtimeABIVersion,
 }
 
 llvm::Value *CGObjCGNU::GetClassNamed(CodeGenFunction &CGF,
-                                      const std::string &Name,
-                                      bool isWeak) {
+                                      StringRef Name,
+                                      bool isWeak, bool isDLLImport) {
   llvm::Constant *ClassName = MakeConstantString(Name);
   // With the incompatible ABI, this will need to be replaced with a direct
   // reference to the class symbol.  For the compatible nonfragile ABI we are
@@ -1077,11 +1080,12 @@ llvm::Value *CGObjCGNU::GetClassNamed(CodeGenFunction &CGF,
 // techniques can modify the name -> class mapping.
 llvm::Value *CGObjCGNU::GetClass(CodeGenFunction &CGF,
                                  const ObjCInterfaceDecl *OID) {
-  return GetClassNamed(CGF, OID->getNameAsString(), OID->isWeakImported());
+  return GetClassNamed(CGF, OID->getNameAsString(), OID->isWeakImported(), 
+                       OID->hasAttr<DLLImportAttr>());
 }
 
 llvm::Value *CGObjCGNU::EmitNSAutoreleasePoolClassRef(CodeGenFunction &CGF) {
-  return GetClassNamed(CGF, "NSAutoreleasePool", false);
+  return GetClassNamed(CGF, "NSAutoreleasePool", false, CGF.CGM.getTarget().getTriple().isKnownWindowsMSVCEnvironment());
 }
 
 llvm::Value *CGObjCGNU::GetSelector(CodeGenFunction &CGF, Selector Sel,
@@ -2878,7 +2882,10 @@ llvm::Value *CGObjCGNU::EmitIvarOffset(CodeGenFunction &CGF,
                          const ObjCIvarDecl *Ivar) {
   if (CGM.getLangOpts().ObjCRuntime.isNonFragile()) {
     Interface = FindIvarInterface(CGM.getContext(), Interface, Ivar);
-    if (RuntimeVersion < 10)
+    // The MSVC linker cannot have a single global defined as LinkOnceAnyLinkage and
+    // ExternalLinkage, so create a reference to the ivar global and rely on the
+    // definition being created as part of GenerateClass.
+    if (RuntimeVersion < 10 || CGF.CGM.getTarget().getTriple().isKnownWindowsMSVCEnvironment())
       return CGF.Builder.CreateZExtOrBitCast(
           CGF.Builder.CreateDefaultAlignedLoad(CGF.Builder.CreateAlignedLoad(
                   ObjCIvarOffsetVariable(Interface, Ivar),
diff --git a/test/Sema/dllimport.c b/test/Sema/dllimport.c
index f863499..b2e2d3c 100644
--- a/test/Sema/dllimport.c
+++ b/test/Sema/dllimport.c
@@ -4,12 +4,12 @@
 // RUN: %clang_cc1 -triple x86_64-mingw32 -fsyntax-only -fms-extensions -verify -std=c99 -DGNU %s
 
 // Invalid usage.
-__declspec(dllimport) typedef int typedef1; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
-typedef __declspec(dllimport) int typedef2; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
-typedef int __declspec(dllimport) typedef3; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
-typedef __declspec(dllimport) void (*FunTy)(); // expected-warning{{'dllimport' attribute only applies to variables and functions}}
-enum __declspec(dllimport) Enum { EnumVal }; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
-struct __declspec(dllimport) Record {}; // expected-warning{{'dllimport' attribute only applies to variables and functions}}
+__declspec(dllimport) typedef int typedef1; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
+typedef __declspec(dllimport) int typedef2; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
+typedef int __declspec(dllimport) typedef3; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
+typedef __declspec(dllimport) void (*FunTy)(); // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
+enum __declspec(dllimport) Enum { EnumVal }; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
+struct __declspec(dllimport) Record {}; // expected-warning{{'dllimport' attribute only applies to variables, functions and classes}}
 
 
 
diff --git a/test/SemaObjC/dllimport.m b/test/SemaObjC/dllimport.m
new file mode 100644
index 0000000..b8fde7c
--- /dev/null
+++ b/test/SemaObjC/dllimport.m
@@ -0,0 +1,19 @@
+// RUN: %clang -fsyntax-only -fms-extensions %s -Xclang -verify
+#if !__LP64__
+// expected-no-diagnostics
+#endif
+
+@interface NSObject @end
+
+#if __LP64__
+__declspec(dllimport) // expected-warning {{__declspec attribute 'dllimport' is not supported}}
+#else
+__declspec(dllimport)
+#endif
+@interface testinterface : NSObject
+- (void)testmethod;
+@end
+
+@implementation testinterface
+- (void)testmethod { }
+@end
\ No newline at end of file
