[llvm] [PowerPC] Do not string pool globals that are part of llvm used. (PR #66848)

Stefan Pintilie via llvm-commits llvm-commits at lists.llvm.org
Tue Sep 19 19:25:30 PDT 2023


https://github.com/stefanp-ibm created https://github.com/llvm/llvm-project/pull/66848

The string pooling pass was incorrectly pooling global varables that were part of llvm.used or llvm.compiler.used. This patch fixes the pass to prevent that by checking each candidate to make sure that it is not in either of those lists.

>From 5ae27d2a0d7225458bec91d5737a65e02b07c6c8 Mon Sep 17 00:00:00 2001
From: Stefan Pintilie <stefanp at ca.ibm.com>
Date: Tue, 19 Sep 2023 21:09:36 -0500
Subject: [PATCH] [PowerPC] Do not string pool globals that are part of llvm
 used.

The string pooling pass was incorrectly pooling global varables that
were part of llvm.used or llvm.compiler.used. This patch fixes the pass
to prevent that by checking each candidate to make sure that it is not
in either of those lists.
---
 .../lib/Target/PowerPC/PPCMergeStringPool.cpp | 14 +++++
 .../PowerPC/aix-xcoff-used-with-stringpool.ll | 57 +++++++++++++++++++
 2 files changed, 71 insertions(+)
 create mode 100644 llvm/test/CodeGen/PowerPC/aix-xcoff-used-with-stringpool.ll

diff --git a/llvm/lib/Target/PowerPC/PPCMergeStringPool.cpp b/llvm/lib/Target/PowerPC/PPCMergeStringPool.cpp
index dba44c6a37d026f..a2e0fb6a345b951 100644
--- a/llvm/lib/Target/PowerPC/PPCMergeStringPool.cpp
+++ b/llvm/lib/Target/PowerPC/PPCMergeStringPool.cpp
@@ -142,6 +142,16 @@ static bool hasReplaceableUsers(GlobalVariable &GV) {
 // valid candidates to be merged into the string pool. Valid candidates will
 // be added to MergeableStrings.
 void PPCMergeStringPool::collectCandidateConstants(Module &M) {
+  SmallVector<GlobalValue *, 4> UsedV;
+  collectUsedGlobalVariables(M, UsedV, /*CompilerUsed=*/false);
+  SmallVector<GlobalValue *, 4> UsedVCompiler;
+  collectUsedGlobalVariables(M, UsedVCompiler, /*CompilerUsed=*/true);
+  // Combine all of the Global Variables marked as used into a SmallPtrSet for
+  // faster lookup inside the loop.
+  SmallPtrSet<GlobalValue*, 8> AllUsedGlobals;
+  AllUsedGlobals.insert(UsedV.begin(), UsedV.end());
+  AllUsedGlobals.insert(UsedVCompiler.begin(), UsedVCompiler.end());
+
   for (GlobalVariable &Global : M.globals()) {
     LLVM_DEBUG(dbgs() << "Looking at global:");
     LLVM_DEBUG(Global.dump());
@@ -173,6 +183,10 @@ void PPCMergeStringPool::collectCandidateConstants(Module &M) {
     if (!ConstData)
       continue;
 
+    // Do not pool globals that are part of llvm.used or llvm.compiler.end.
+    if (AllUsedGlobals.contains(&Global))
+      continue;
+
     if (!hasReplaceableUsers(Global))
       continue;
 
diff --git a/llvm/test/CodeGen/PowerPC/aix-xcoff-used-with-stringpool.ll b/llvm/test/CodeGen/PowerPC/aix-xcoff-used-with-stringpool.ll
new file mode 100644
index 000000000000000..e29fd9234566ae0
--- /dev/null
+++ b/llvm/test/CodeGen/PowerPC/aix-xcoff-used-with-stringpool.ll
@@ -0,0 +1,57 @@
+;; Test that the string pooling pass does not pool globals that are
+;; in llvm.used or in llvm.compiler.used.
+
+; RUN: llc -verify-machineinstrs -mcpu=pwr8 -mtriple powerpc-ibm-aix-xcoff -data-sections=false < %s | \
+; RUN:   FileCheck %s
+
+; RUN: llc -verify-machineinstrs -mcpu=pwr8 -mtriple powerpc64-ibm-aix-xcoff -data-sections=false < %s | \
+; RUN:   FileCheck %s
+
+ at keep_this = internal constant [5 x i8] c"keep1", align 1
+ at keep_this2 = internal constant [5 x i8] c"keep2", align 1
+ at .str.1 = private unnamed_addr constant [12 x i8] c"str1_STRING\00", align 1
+ at .str.2 = private unnamed_addr constant [12 x i8] c"str2_STRING\00", align 1
+ at .str.3 = private unnamed_addr constant [12 x i8] c"str3_STRING\00", align 1
+ at llvm.used = appending global [1 x ptr] [ptr @keep_this], section "llvm.metadata"
+ at llvm.compiler.used = appending global [1 x ptr] [ptr @keep_this2], section "llvm.metadata"
+
+declare signext i32 @callee(ptr noundef) local_unnamed_addr
+
+define dso_local signext i32 @keep1() local_unnamed_addr #0 {
+entry:
+  %call = tail call signext i32 @callee(ptr noundef nonnull @keep_this)
+  ret i32 %call
+}
+
+define dso_local signext i32 @keep2() local_unnamed_addr #0 {
+entry:
+  %call = tail call signext i32 @callee(ptr noundef nonnull @keep_this2)
+  ret i32 %call
+}
+
+define dso_local signext i32 @str1() local_unnamed_addr #0 {
+entry:
+  %call = tail call signext i32 @callee(ptr noundef nonnull @.str.1)
+  ret i32 %call
+}
+
+define dso_local signext i32 @str2() local_unnamed_addr #0 {
+entry:
+  %call = tail call signext i32 @callee(ptr noundef nonnull @.str.2)
+  ret i32 %call
+}
+
+define dso_local signext i32 @str3() local_unnamed_addr #0 {
+entry:
+  %call = tail call signext i32 @callee(ptr noundef nonnull @.str.3)
+  ret i32 %call
+}
+
+; CHECK:    .lglobl keep_this
+; CHECK:  keep_this:
+; CHECK:    .lglobl keep_this2
+; CHECK:  keep_this2:
+; CHECK:  L..__ModuleStringPool:
+; CHECK:    .string "str1_STRING"
+; CHECK:    .string "str2_STRING"
+; CHECK:    .string "str3_STRING"



More information about the llvm-commits mailing list