[llvm] Avoid merging instrumentation profiler globals (PR #172835)

via llvm-commits llvm-commits at lists.llvm.org
Fri Dec 19 10:04:03 PST 2025


https://github.com/eleviant updated https://github.com/llvm/llvm-project/pull/172835

>From 34eae322bb51a3be68d11ab3a09dd3926e9721f3 Mon Sep 17 00:00:00 2001
From: Evgeny Leviant <eleviant at accesssoftek.com>
Date: Thu, 18 Dec 2025 12:04:43 +0100
Subject: [PATCH] Avoid merging instrumentation profiler globals

The global-merge pass attempts to merge instumentation profiler counters,
e.g __profc_foo and __profc_bar, which results in their corresponding
__llvm_prf_cnts sections being merged into a single one and moved out
from a comdat group, which originally gropus __llvm_prf_cnts and
__llvm_prf_data sections. This, in turn, results in __llvm_prf_data
becoming an orphaned section, which is garbage-collected when
--gc-sections linker flag is used.
---
 llvm/lib/CodeGen/GlobalMerge.cpp                  | 15 ++++++++-------
 .../AArch64/global-merge-profile-sections.ll      | 11 +++++++++++
 2 files changed, 19 insertions(+), 7 deletions(-)
 create mode 100644 llvm/test/CodeGen/AArch64/global-merge-profile-sections.ll

diff --git a/llvm/lib/CodeGen/GlobalMerge.cpp b/llvm/lib/CodeGen/GlobalMerge.cpp
index b8b0d4d612742..e32a09013e05e 100644
--- a/llvm/lib/CodeGen/GlobalMerge.cpp
+++ b/llvm/lib/CodeGen/GlobalMerge.cpp
@@ -677,7 +677,8 @@ bool GlobalMergeImpl::run(Module &M) {
   IsMachO = M.getTargetTriple().isOSBinFormatMachO();
 
   auto &DL = M.getDataLayout();
-  MapVector<std::pair<unsigned, StringRef>, SmallVector<GlobalVariable *, 0>>
+  MapVector<std::tuple<unsigned, StringRef, Comdat *>,
+            SmallVector<GlobalVariable *, 0>>
       Globals, ConstGlobals, BSSGlobals;
   bool Changed = false;
   setMustKeepGlobalVariables(M);
@@ -735,11 +736,11 @@ bool GlobalMergeImpl::run(Module &M) {
     if (CanMerge) {
       if (TM &&
           TargetLoweringObjectFile::getKindForGlobal(&GV, *TM).isBSS())
-        BSSGlobals[{AddressSpace, Section}].push_back(&GV);
+        BSSGlobals[{AddressSpace, Section, GV.getComdat()}].push_back(&GV);
       else if (GV.isConstant())
-        ConstGlobals[{AddressSpace, Section}].push_back(&GV);
+        ConstGlobals[{AddressSpace, Section, GV.getComdat()}].push_back(&GV);
       else
-        Globals[{AddressSpace, Section}].push_back(&GV);
+        Globals[{AddressSpace, Section, GV.getComdat()}].push_back(&GV);
     }
     LLVM_DEBUG(dbgs() << "GV " << (CanMerge ? "" : "not ") << "to merge: " << GV
                       << "\n");
@@ -747,16 +748,16 @@ bool GlobalMergeImpl::run(Module &M) {
 
   for (auto &P : Globals)
     if (P.second.size() > 1)
-      Changed |= doMerge(P.second, M, false, P.first.first);
+      Changed |= doMerge(P.second, M, false, std::get<0>(P.first));
 
   for (auto &P : BSSGlobals)
     if (P.second.size() > 1)
-      Changed |= doMerge(P.second, M, false, P.first.first);
+      Changed |= doMerge(P.second, M, false, std::get<0>(P.first));
 
   if (Opt.MergeConstantGlobals)
     for (auto &P : ConstGlobals)
       if (P.second.size() > 1)
-        Changed |= doMerge(P.second, M, true, P.first.first);
+        Changed |= doMerge(P.second, M, true, std::get<0>(P.first));
 
   return Changed;
 }
diff --git a/llvm/test/CodeGen/AArch64/global-merge-profile-sections.ll b/llvm/test/CodeGen/AArch64/global-merge-profile-sections.ll
new file mode 100644
index 0000000000000..7108d82ddaa2e
--- /dev/null
+++ b/llvm/test/CodeGen/AArch64/global-merge-profile-sections.ll
@@ -0,0 +1,11 @@
+; RUN: llc -mtriple=aarch64-linux-gnu -aarch64-enable-global-merge  -global-merge-group-by-use=false < %s | FileCheck %s
+; CHECK-NOT: _MergedGlobals
+
+$__profc_begin = comdat nodeduplicate
+$__profc_end = comdat nodeduplicate
+
+ at __profc_begin = private global [2 x i64] zeroinitializer, section "__llvm_prf_cnts", comdat, align 8
+ at __profd_begin = private global { i64, i64, i64, i64, ptr, ptr, i32, [3 x i16], i32 } { i64 -1301828029439649651, i64 172590168, i64 sub (i64 ptrtoint (ptr @__profc_begin to i64), i64 ptrtoint (ptr @__profd_begin to i64)), i64 0, ptr null, ptr null, i32 2, [3 x i16] zeroinitializer, i32 0 }, section "__llvm_prf_data", comdat($__profc_begin), align 8
+ at __profc_end = private global [2 x i64] zeroinitializer, section "__llvm_prf_cnts", comdat, align 8
+ at __profd_end = private global { i64, i64, i64, i64, ptr, ptr, i32, [3 x i16], i32 } { i64 3274037854792712831, i64 172590168, i64 sub (i64 ptrtoint (ptr @__profc_end to i64), i64 ptrtoint (ptr @__profd_end to i64)), i64 0, ptr null, ptr null, i32 2, [3 x i16] zeroinitializer, i32 0 }, section "__llvm_prf_data", comdat($__profc_end), align 8
+



More information about the llvm-commits mailing list