r324701 - AST: support ObjC lifetime qualifiers in MS ABI

Saleem Abdulrasool via cfe-commits cfe-commits at lists.llvm.org
Thu Feb 8 19:23:54 PST 2018


Author: compnerd
Date: Thu Feb  8 19:23:54 2018
New Revision: 324701

URL: http://llvm.org/viewvc/llvm-project?rev=324701&view=rev
Log:
AST: support ObjC lifetime qualifiers in MS ABI

Adjust the ObjC protocol conformance workaround to be more extensible.
Use a synthetic type for the protocol (`struct Protocol`).  Embed this
within a reserved namespace to permit extending the extended pointer
type qualifiers similarly for ObjC lifetime qualifiers.

Introduce additional special handling for `__autoreleasing`, `__strong`,
and `__weak` Objective C lifetime qualifiers.  We decorate these by
creating an artificial template type `Autoreleasing`, `Strong`, or
`Weak` in the `__ObjC` namespace.  These are only considered in the
template type specialization and not the function parameter.

Added:
    cfe/trunk/test/CodeGenObjCXX/msabi-objc-extensions.mm
Removed:
    cfe/trunk/test/CodeGenObjCXX/msabi-protocol-conformance.mm
Modified:
    cfe/trunk/lib/AST/MicrosoftMangle.cpp

Modified: cfe/trunk/lib/AST/MicrosoftMangle.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/MicrosoftMangle.cpp?rev=324701&r1=324700&r2=324701&view=diff
==============================================================================
--- cfe/trunk/lib/AST/MicrosoftMangle.cpp (original)
+++ cfe/trunk/lib/AST/MicrosoftMangle.cpp Thu Feb  8 19:23:54 2018
@@ -362,6 +362,10 @@ private:
                           const TemplateArgumentList &TemplateArgs);
   void mangleTemplateArg(const TemplateDecl *TD, const TemplateArgument &TA,
                          const NamedDecl *Parm);
+
+  void mangleObjCProtocol(const ObjCProtocolDecl *PD);
+  void mangleObjCLifetime(const QualType T, Qualifiers Quals,
+                          SourceRange Range);
 };
 }
 
@@ -1456,6 +1460,47 @@ void MicrosoftCXXNameMangler::mangleTemp
   }
 }
 
+void MicrosoftCXXNameMangler::mangleObjCProtocol(const ObjCProtocolDecl *PD) {
+  llvm::SmallString<64> TemplateMangling;
+  llvm::raw_svector_ostream Stream(TemplateMangling);
+  MicrosoftCXXNameMangler Extra(Context, Stream);
+
+  Stream << "?$";
+  Extra.mangleSourceName("Protocol");
+  Extra.mangleArtificalTagType(TTK_Struct, PD->getName());
+
+  mangleArtificalTagType(TTK_Struct, TemplateMangling, {"__ObjC"});
+}
+
+void MicrosoftCXXNameMangler::mangleObjCLifetime(const QualType Type,
+                                                 Qualifiers Quals,
+                                                 SourceRange Range) {
+  llvm::SmallString<64> TemplateMangling;
+  llvm::raw_svector_ostream Stream(TemplateMangling);
+  MicrosoftCXXNameMangler Extra(Context, Stream);
+
+  Stream << "?$";
+  switch (Quals.getObjCLifetime()) {
+  case Qualifiers::OCL_None:
+  case Qualifiers::OCL_ExplicitNone:
+    break;
+  case Qualifiers::OCL_Autoreleasing:
+    Extra.mangleSourceName("Autoreleasing");
+    break;
+  case Qualifiers::OCL_Strong:
+    Extra.mangleSourceName("Strong");
+    break;
+  case Qualifiers::OCL_Weak:
+    Extra.mangleSourceName("Weak");
+    break;
+  }
+  Extra.manglePointerCVQualifiers(Quals);
+  Extra.manglePointerExtQualifiers(Quals, Type);
+  Extra.mangleType(Type, Range);
+
+  mangleArtificalTagType(TTK_Struct, TemplateMangling, {"__ObjC"});
+}
+
 void MicrosoftCXXNameMangler::mangleQualifiers(Qualifiers Quals,
                                                bool IsMember) {
   // <cvr-qualifiers> ::= [E] [F] [I] <base-cvr-qualifiers>
@@ -1683,6 +1728,8 @@ void MicrosoftCXXNameMangler::mangleType
 
   switch (QMM) {
   case QMM_Drop:
+    if (Quals.hasObjCLifetime())
+      Quals = Quals.withoutObjCLifetime();
     break;
   case QMM_Mangle:
     if (const FunctionType *FT = dyn_cast<FunctionType>(T)) {
@@ -1701,6 +1748,8 @@ void MicrosoftCXXNameMangler::mangleType
   case QMM_Result:
     // Presence of __unaligned qualifier shouldn't affect mangling here.
     Quals.removeUnaligned();
+    if (Quals.hasObjCLifetime())
+      Quals = Quals.withoutObjCLifetime();
     if ((!IsPointer && Quals) || isa<TagType>(T)) {
       Out << '?';
       mangleQualifiers(Quals, false);
@@ -2334,6 +2383,15 @@ void MicrosoftCXXNameMangler::mangleType
 void MicrosoftCXXNameMangler::mangleType(const ObjCObjectPointerType *T,
                                          Qualifiers Quals, SourceRange Range) {
   QualType PointeeType = T->getPointeeType();
+  switch (Quals.getObjCLifetime()) {
+  case Qualifiers::OCL_None:
+  case Qualifiers::OCL_ExplicitNone:
+    break;
+  case Qualifiers::OCL_Autoreleasing:
+  case Qualifiers::OCL_Strong:
+  case Qualifiers::OCL_Weak:
+    return mangleObjCLifetime(PointeeType, Quals, Range);
+  }
   manglePointerCVQualifiers(Quals);
   manglePointerExtQualifiers(Quals, PointeeType);
   mangleType(PointeeType, Range);
@@ -2469,11 +2527,8 @@ void MicrosoftCXXNameMangler::mangleType
   else
     mangleSourceName(T->getInterface()->getName());
 
-  for (const auto &Q : T->quals()) {
-    Out << 'Y'; // cointerface
-    mangleSourceName(Q->getName());
-    Out << '@';
-  }
+  for (const auto &Q : T->quals())
+    mangleObjCProtocol(Q);
   Out << '@';
 
   Out << '@';

Added: cfe/trunk/test/CodeGenObjCXX/msabi-objc-extensions.mm
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenObjCXX/msabi-objc-extensions.mm?rev=324701&view=auto
==============================================================================
--- cfe/trunk/test/CodeGenObjCXX/msabi-objc-extensions.mm (added)
+++ cfe/trunk/test/CodeGenObjCXX/msabi-objc-extensions.mm Thu Feb  8 19:23:54 2018
@@ -0,0 +1,66 @@
+// RUN: %clang_cc1 -triple thumbv7-windows-msvc -fobjc-runtime=ios-6.0 -fobjc-arc -o - -emit-llvm %s | FileCheck %s
+
+ at protocol P;
+ at protocol Q;
+
+ at class I;
+
+void f(id<P>, id, id<P>, id) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at U?$Protocol at UP@@@__ObjC@@@@PAUobjc_object@@01 at Z"
+
+void f(id, id<P>, id<P>, id) {}
+// CHECK-LABEL: "\01?f@@YAXPAUobjc_object@@PAU?$objc_object at U?$Protocol at UP@@@__ObjC@@@@10 at Z"
+
+void f(id<P>, id<P>) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at U?$Protocol at UP@@@__ObjC@@@@0 at Z"
+
+void f(id<P>) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at U?$Protocol at UP@@@__ObjC@@@@@Z"
+
+void f(id<P, Q>) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at U?$Protocol at UP@@@__ObjC@@U?$Protocol at UQ@@@2@@@@Z"
+
+void f(Class<P>) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$objc_class at U?$Protocol at UP@@@__ObjC@@@@@Z"
+
+void f(Class<P, Q>) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$objc_class at U?$Protocol at UP@@@__ObjC@@U?$Protocol at UQ@@@2@@@@Z"
+
+void f(I<P> *) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$I at U?$Protocol at UP@@@__ObjC@@@@@Z"
+
+void f(I<P, Q> *) {}
+// CHECK-LABEL: "\01?f@@YAXPAU?$I at U?$Protocol at UP@@@__ObjC@@U?$Protocol at UQ@@@2@@@@Z"
+
+template <typename>
+struct S {};
+
+void f(S<__unsafe_unretained id>) {}
+// CHECK-LABEL: "\01?f@@YAXU?$S at PAUobjc_object@@@@@Z"
+
+void f(S<__autoreleasing id>) {}
+// CHECK-LABEL: "\01?f@@YAXU?$S at U?$Autoreleasing at PAUobjc_object@@@__ObjC@@@@@Z"
+
+void f(S<__strong id>) {}
+// CHECK-LABEL: "\01?f@@YAXU?$S at U?$Strong at PAUobjc_object@@@__ObjC@@@@@Z"
+
+void f(S<__weak id>) {}
+// CHECK-LABEL: "\01?f@@YAXU?$S at U?$Weak at PAUobjc_object@@@__ObjC@@@@@Z"
+
+void w(__weak id) {}
+// CHECK-LABEL: "\01?w@@YAXPAUobjc_object@@@Z"
+
+void s(__strong id) {}
+// CHECK-LABEL: "\01?s@@YAXPAUobjc_object@@@Z"
+
+void a(__autoreleasing id) {}
+// CHECK-LABEL: "\01?a@@YAXPAUobjc_object@@@Z"
+
+void u(__unsafe_unretained id) {}
+// CHECK-LABEL: "\01?u@@YAXPAUobjc_object@@@Z"
+
+S<__autoreleasing id> g() { return S<__autoreleasing id>(); }
+// CHECK-LABEL: "\01?g@@YA?AU?$S at U?$Autoreleasing at PAUobjc_object@@@__ObjC@@@@XZ"
+
+__autoreleasing id h() { return nullptr; }
+// CHECK-LABEL: "\01?h@@YAPAUobjc_object@@XZ"

Removed: cfe/trunk/test/CodeGenObjCXX/msabi-protocol-conformance.mm
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenObjCXX/msabi-protocol-conformance.mm?rev=324700&view=auto
==============================================================================
--- cfe/trunk/test/CodeGenObjCXX/msabi-protocol-conformance.mm (original)
+++ cfe/trunk/test/CodeGenObjCXX/msabi-protocol-conformance.mm (removed)
@@ -1,34 +0,0 @@
-// RUN: %clang_cc1 -triple thumbv7-windows-msvc -fobjc-runtime=ios-6.0 -o - -emit-llvm %s | FileCheck %s
-
- at protocol P;
- at protocol Q;
-
- at class I;
-
-void f(id<P>, id, id<P>, id) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at YP@@@@PAUobjc_object@@01 at Z"
-
-void f(id, id<P>, id<P>, id) {}
-// CHECK-LABEL: "\01?f@@YAXPAUobjc_object@@PAU?$objc_object at YP@@@@10 at Z"
-
-void f(id<P>, id<P>) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at YP@@@@0 at Z"
-
-void f(id<P>) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at YP@@@@@Z"
-
-void f(id<P, Q>) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$objc_object at YP@@YQ@@@@@Z"
-
-void f(Class<P>) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$objc_class at YP@@@@@Z"
-
-void f(Class<P, Q>) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$objc_class at YP@@YQ@@@@@Z"
-
-void f(I<P> *) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$I at YP@@@@@Z"
-
-void f(I<P, Q> *) {}
-// CHECK-LABEL: "\01?f@@YAXPAU?$I at YP@@YQ@@@@@Z"
-




More information about the cfe-commits mailing list