[clang] baba78d - [clang] Fix loss of `dllexport` for exported template specialization (#94664)

via cfe-commits cfe-commits at lists.llvm.org
Mon Jun 10 11:39:31 PDT 2024


Author: Andrew Ng
Date: 2024-06-10T19:39:28+01:00
New Revision: baba78daf2b3a3ee9bfa21f1f8ff3584aa982ac8

URL: https://github.com/llvm/llvm-project/commit/baba78daf2b3a3ee9bfa21f1f8ff3584aa982ac8
DIFF: https://github.com/llvm/llvm-project/commit/baba78daf2b3a3ee9bfa21f1f8ff3584aa982ac8.diff

LOG: [clang] Fix loss of `dllexport` for exported template specialization (#94664)

When dropping DLL attributes, ensure that the most recent declaration is
being checked.

Added: 
    clang/test/CodeGenCXX/windows-instantiate-dllexport-template-specialization.cpp

Modified: 
    clang/lib/CodeGen/CodeGenModule.cpp
    clang/lib/CodeGen/CodeGenModule.h

Removed: 
    


################################################################################
diff  --git a/clang/lib/CodeGen/CodeGenModule.cpp b/clang/lib/CodeGen/CodeGenModule.cpp
index 75b1449090389..dd4a665ebc78b 100644
--- a/clang/lib/CodeGen/CodeGenModule.cpp
+++ b/clang/lib/CodeGen/CodeGenModule.cpp
@@ -4512,6 +4512,19 @@ llvm::Constant *CodeGenModule::GetOrCreateMultiVersionResolver(GlobalDecl GD) {
   return Resolver;
 }
 
+bool CodeGenModule::shouldDropDLLAttribute(const Decl *D,
+                                           const llvm::GlobalValue *GV) const {
+  auto SC = GV->getDLLStorageClass();
+  if (SC == llvm::GlobalValue::DefaultStorageClass)
+    return false;
+  const Decl *MRD = D->getMostRecentDecl();
+  return (((SC == llvm::GlobalValue::DLLImportStorageClass &&
+            !MRD->hasAttr<DLLImportAttr>()) ||
+           (SC == llvm::GlobalValue::DLLExportStorageClass &&
+            !MRD->hasAttr<DLLExportAttr>())) &&
+          !shouldMapVisibilityToDLLExport(cast<NamedDecl>(MRD)));
+}
+
 /// GetOrCreateLLVMFunction - If the specified mangled name is not in the
 /// module, create and return an llvm Function with the specified type. If there
 /// is something in the module with the specified name, return it potentially
@@ -4564,8 +4577,7 @@ llvm::Constant *CodeGenModule::GetOrCreateLLVMFunction(
     }
 
     // Handle dropped DLL attributes.
-    if (D && !D->hasAttr<DLLImportAttr>() && !D->hasAttr<DLLExportAttr>() &&
-        !shouldMapVisibilityToDLLExport(cast_or_null<NamedDecl>(D))) {
+    if (D && shouldDropDLLAttribute(D, Entry)) {
       Entry->setDLLStorageClass(llvm::GlobalValue::DefaultStorageClass);
       setDSOLocal(Entry);
     }
@@ -4859,8 +4871,7 @@ CodeGenModule::GetOrCreateLLVMGlobal(StringRef MangledName, llvm::Type *Ty,
     }
 
     // Handle dropped DLL attributes.
-    if (D && !D->hasAttr<DLLImportAttr>() && !D->hasAttr<DLLExportAttr>() &&
-        !shouldMapVisibilityToDLLExport(D))
+    if (D && shouldDropDLLAttribute(D, Entry))
       Entry->setDLLStorageClass(llvm::GlobalValue::DefaultStorageClass);
 
     if (LangOpts.OpenMP && !LangOpts.OpenMPSimd && D)

diff  --git a/clang/lib/CodeGen/CodeGenModule.h b/clang/lib/CodeGen/CodeGenModule.h
index dc24971a3c186..9b63f47ef42cb 100644
--- a/clang/lib/CodeGen/CodeGenModule.h
+++ b/clang/lib/CodeGen/CodeGenModule.h
@@ -1594,6 +1594,8 @@ class CodeGenModule : public CodeGenTypeCache {
   }
 
 private:
+  bool shouldDropDLLAttribute(const Decl *D, const llvm::GlobalValue *GV) const;
+
   llvm::Constant *GetOrCreateLLVMFunction(
       StringRef MangledName, llvm::Type *Ty, GlobalDecl D, bool ForVTable,
       bool DontDefer = false, bool IsThunk = false,

diff  --git a/clang/test/CodeGenCXX/windows-instantiate-dllexport-template-specialization.cpp b/clang/test/CodeGenCXX/windows-instantiate-dllexport-template-specialization.cpp
new file mode 100644
index 0000000000000..97f341ba1f909
--- /dev/null
+++ b/clang/test/CodeGenCXX/windows-instantiate-dllexport-template-specialization.cpp
@@ -0,0 +1,18 @@
+// RUN: %clang_cc1 -triple i686-windows         -fdeclspec -emit-llvm %s -o - | FileCheck %s -check-prefix CHECK-MS
+// RUN: %clang_cc1 -triple i686-windows-itanium -fdeclspec -emit-llvm %s -o - | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-scei-ps4      -fdeclspec -emit-llvm %s -o - | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-sie-ps5       -fdeclspec -emit-llvm %s -o - | FileCheck %s
+
+struct s {
+  template <bool b = true> static bool f();
+};
+
+template <typename T> bool template_using_f(T) { return s::f(); }
+
+bool use_template_using_f() { return template_using_f(0); }
+
+template<>
+bool __declspec(dllexport) s::f<true>() { return true; }
+
+// CHECK-MS: dllexport {{.*}} @"??$f@$00 at s@@SA_NXZ"
+// CHECK: dllexport {{.*}} @_ZN1s1fILb1EEEbv


        


More information about the cfe-commits mailing list