[clang] 10cc3a8 - [MS-ABI] skip generate comdat for vftable defined with internal alias. (#71748)

via cfe-commits cfe-commits at lists.llvm.org
Wed Nov 15 17:39:57 PST 2023


Author: jyu2-git
Date: 2023-11-15T17:39:54-08:00
New Revision: 10cc3a8556a8ff9557890c96de162cb2c09669e2

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

LOG: [MS-ABI] skip generate comdat for vftable defined with internal alias. (#71748)

We got a error:
`LLVM ERROR: Associative COMDAT symbol '??_7?$T at V<lambda_0>@@@@6B@' is
not a key for its COMDAT`

Current we create internal alias for vftable when lambd is used.
For the test, IR generate:
```
 $"??_7?$T at V<lambda_0>@@$0A@@@6b@" = comdat any

@0 = private unnamed_addr constant { [2 x ptr] } { [2 x ptr] [ptr @"??_R4?$T at V<lambda_0>@@$0A@@@6b@", ptr @"?c at b@@UEAAXXZ"] }, comdat($"??_7?$T at V<lambda_0>@@$0A@@@6b@")

@"??_7?$T at V<lambda_0>@@$0A@@@6b@" = internal unnamed_addr alias ptr, getelementptr inbounds ({ [2 x ptr] }, ptr @0, i32 0, i32 0, i32 1)
```

According LLVM language reference manual section on COMDATs:
There are some restrictions on the properties of the global object. It,
or an alias to it, must have the same name as the COMDAT group when
targeting COFF. The contents and size of this object may be used during
link-time to determine which COMDAT groups get selected depending on the
selection kind. Because the name of the object must match the name of
the
COMDAT group, the linkage of the global object must not be local; local
symbols can get renamed if a collision occurs in the symbol table.

So one way to fix this is to not create comdat for the alias.

@0 = private unnamed_addr constant { [2 x ptr] } { [2 x ptr] [ptr
@"??_R4?$T at V<lambda_0>@@@@6B@", ptr @"?c@?$T at V<lambda_0>@@@@UEAAXXZ"] }

Added: 
    clang/test/CodeGenCXX/ms-local-vft-alias-comdat.cpp

Modified: 
    clang/lib/CodeGen/MicrosoftCXXABI.cpp
    clang/test/CodeGenCXX/type-metadata.cpp

Removed: 
    


################################################################################
diff  --git a/clang/lib/CodeGen/MicrosoftCXXABI.cpp b/clang/lib/CodeGen/MicrosoftCXXABI.cpp
index cc7bc3b73589877..44b9acdee62648a 100644
--- a/clang/lib/CodeGen/MicrosoftCXXABI.cpp
+++ b/clang/lib/CodeGen/MicrosoftCXXABI.cpp
@@ -1892,9 +1892,7 @@ llvm::GlobalVariable *MicrosoftCXXABI::getAddrOfVTable(const CXXRecordDecl *RD,
 
   llvm::Comdat *C = nullptr;
   if (!VFTableComesFromAnotherTU &&
-      (llvm::GlobalValue::isWeakForLinker(VFTableLinkage) ||
-       (llvm::GlobalValue::isLocalLinkage(VFTableLinkage) &&
-        VTableAliasIsRequred)))
+      llvm::GlobalValue::isWeakForLinker(VFTableLinkage))
     C = CGM.getModule().getOrInsertComdat(VFTableName.str());
 
   // Only insert a pointer into the VFTable for RTTI data if we are not

diff  --git a/clang/test/CodeGenCXX/ms-local-vft-alias-comdat.cpp b/clang/test/CodeGenCXX/ms-local-vft-alias-comdat.cpp
new file mode 100644
index 000000000000000..7eaa05c02c102c0
--- /dev/null
+++ b/clang/test/CodeGenCXX/ms-local-vft-alias-comdat.cpp
@@ -0,0 +1,30 @@
+// RUN: %clang_cc1 -fcxx-exceptions -triple=x86_64-windows-msvc  \
+// RUN:  -Wmicrosoft-template -fms-compatibility -emit-llvm %s -o - \
+// RUN:  | FileCheck %s
+
+template <typename a> struct T {
+  virtual void c();
+  T(a h) {}
+};
+struct m {
+  template <typename j> void ab(j ac) {
+    using ad = T<j>;
+    ad j(ac);
+  }
+};
+template <typename ae> struct n {
+  template <typename j> n(j ac) { q.ab(ac); }
+  ae q;
+};
+class s : n<m> {
+  using ag = n<m>;
+public:
+  template <typename j> s(j ac) : ag(ac) {}
+};
+struct ah {
+  ah(s);
+} a([]{});
+
+//CHECK: @0 = private unnamed_addr constant { [2 x ptr] } { [2 x ptr] [ptr @"??_R4?$T at V<lambda_0>@@@@6B@", ptr @"?c@?$T at V<lambda_0>@@@@UEAAXXZ"] }
+//CHECK: @"??_7?$T at V<lambda_0>@@@@6B@" = internal unnamed_addr alias ptr, getelementptr inbounds ({ [2 x ptr] }, ptr @0, i32 0, i32 0, i32 1)
+//CHECK-NOT : "??_7?$e at V<lambda_0>@@@@6B@" = comdat any

diff  --git a/clang/test/CodeGenCXX/type-metadata.cpp b/clang/test/CodeGenCXX/type-metadata.cpp
index b93c4288bb9a5d2..4ddfc3c2e3a8fff 100644
--- a/clang/test/CodeGenCXX/type-metadata.cpp
+++ b/clang/test/CodeGenCXX/type-metadata.cpp
@@ -125,9 +125,9 @@
 // MS-TYPEMETADATA: comdat($"??_7B@@6B0@@"), !type [[B8:![0-9]+]]
 // MS-TYPEMETADATA: comdat($"??_7B@@6BA@@@"), !type [[A8]]
 // MS-TYPEMETADATA: comdat($"??_7C@@6B@"), !type [[A8]]
-// MS-TYPEMETADATA: comdat($"??_7D@?A0x{{[^@]*}}@@6BB@@@"), !type [[B8]], !type [[D8:![0-9]+]]
-// MS-TYPEMETADATA: comdat($"??_7D@?A0x{{[^@]*}}@@6BA@@@"), !type [[A8]]
-// MS-TYPEMETADATA: comdat($"??_7FA@?1??foo@@YAXXZ at 6B@"), !type [[A8]], !type [[FA8:![0-9]+]]
+// MS-TYPEMETADATA: private unnamed_addr constant { [3 x ptr] } { [3 x ptr] [ptr @"??_R4D@?{{.*}}@@6BB@@@", ptr @"?g at B@@UEAAXXZ", ptr @"?h at D@?{{.*}}@@UEAAXXZ"] }, !type [[B8]], !type [[D8:![0-9]+]]
+// MS-TYPEMETADATA: private unnamed_addr constant { [2 x ptr] } { [2 x ptr] [ptr @"??_R4D@?{{.*}}@@6BA@@@", ptr @"?f at D@?{{.*}}@@$4PPPPPPPM at A@EAAXXZ"] }, !type !0
+// MS: private unnamed_addr constant { [2 x ptr] } { [2 x ptr] [ptr @"??_R4FA@?1??foo@@YAXXZ at 6B@", ptr @"?f at FA@?1??foo@@YAXXZ at UEAAXXZ"] }, !type !0, !type [[FA8:![0-9]+]]
 
 struct A {
   A();


        


More information about the cfe-commits mailing list