[llvm] [llvm-objcopy,ELF] --discard-locals/--discard-all: allow and keep symbols referenced by relocations (PR #130704)

Fangrui Song via llvm-commits llvm-commits at lists.llvm.org
Tue Mar 11 21:17:37 PDT 2025


https://github.com/MaskRay updated https://github.com/llvm/llvm-project/pull/130704

>From 92f60df01d7e7689b1aaa5d02754e6e936bb4a11 Mon Sep 17 00:00:00 2001
From: Fangrui Song <i at maskray.me>
Date: Mon, 10 Mar 2025 20:11:53 -0700
Subject: [PATCH 1/3] =?UTF-8?q?[=F0=9D=98=80=F0=9D=97=BD=F0=9D=97=BF]=20in?=
 =?UTF-8?q?itial=20version?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Created using spr 1.3.5-bogner
---
 llvm/docs/CommandGuide/llvm-objcopy.rst       |  9 ++++---
 llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp           | 26 ++++++++++---------
 .../tools/llvm-objcopy/ELF/discard-all.test   | 19 ++++++++++++++
 .../llvm-objcopy/ELF/discard-locals-rel.test  | 26 -------------------
 .../llvm-objcopy/ELF/discard-locals.test      | 19 ++++++++++++++
 5 files changed, 57 insertions(+), 42 deletions(-)
 delete mode 100644 llvm/test/tools/llvm-objcopy/ELF/discard-locals-rel.test

diff --git a/llvm/docs/CommandGuide/llvm-objcopy.rst b/llvm/docs/CommandGuide/llvm-objcopy.rst
index 8dc1357635e1b..96f3247780b3b 100644
--- a/llvm/docs/CommandGuide/llvm-objcopy.rst
+++ b/llvm/docs/CommandGuide/llvm-objcopy.rst
@@ -57,9 +57,10 @@ multiple file formats.
 
 .. option:: --discard-all, -x
 
- Remove most local symbols from the output. Different file formats may limit
- this to a subset of the local symbols. For example, file and section symbols in
- ELF objects will not be discarded. Additionally, remove all debug sections.
+ Remove most local symbols not referenced by relocations from the output.
+ Different file formats may limit this to a subset of the local symbols. For
+ example, file and section symbols in ELF objects will not be discarded.
+ Additionally, remove all debug sections.
 
 .. option:: --dump-section <section>=<file>
 
@@ -386,7 +387,7 @@ them.
 
 .. option:: --discard-locals, -X
 
- Remove local symbols starting with ".L" from the output.
+ Remove local symbols starting with ".L" not referenced by relocations from the output.
 
 .. option:: --extract-dwo
 
diff --git a/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp b/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp
index 1a31bfa2e0db3..43aeff18c41b2 100644
--- a/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp
+++ b/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp
@@ -364,7 +364,7 @@ static Error updateAndRemoveSymbols(const CommonConfig &Config,
   // (like GroupSection or RelocationSection). This way, we know which
   // symbols are still 'needed' and which are not.
   if (Config.StripUnneeded || !Config.UnneededSymbolsToRemove.empty() ||
-      !Config.OnlySection.empty()) {
+      !Config.OnlySection.empty() || Config.DiscardMode != DiscardType::None) {
     for (SectionBase &Sec : Obj.sections())
       Sec.markSymbols();
   }
@@ -386,22 +386,24 @@ static Error updateAndRemoveSymbols(const CommonConfig &Config,
     if (Config.StripDebug && Sym.Type == STT_FILE)
       return true;
 
-    if ((Config.DiscardMode == DiscardType::All ||
-         (Config.DiscardMode == DiscardType::Locals &&
-          StringRef(Sym.Name).starts_with(".L"))) &&
-        Sym.Binding == STB_LOCAL && Sym.getShndx() != SHN_UNDEF &&
-        Sym.Type != STT_FILE && Sym.Type != STT_SECTION)
-      return true;
-
     if ((Config.StripUnneeded ||
          Config.UnneededSymbolsToRemove.matches(Sym.Name)) &&
         (!Obj.isRelocatable() || isUnneededSymbol(Sym)))
       return true;
 
-    // We want to remove undefined symbols if all references have been stripped.
-    if (!Config.OnlySection.empty() && !Sym.Referenced &&
-        Sym.getShndx() == SHN_UNDEF)
-      return true;
+    if (!Sym.Referenced) {
+      if ((Config.DiscardMode == DiscardType::All ||
+           (Config.DiscardMode == DiscardType::Locals &&
+            StringRef(Sym.Name).starts_with(".L"))) &&
+          Sym.Binding == STB_LOCAL && Sym.getShndx() != SHN_UNDEF &&
+          Sym.Type != STT_FILE && Sym.Type != STT_SECTION)
+        return true;
+      // We want to remove undefined symbols if all references have been
+      // stripped.
+      if (!Config.OnlySection.empty() && !Sym.Referenced &&
+          Sym.getShndx() == SHN_UNDEF)
+        return true;
+    }
 
     return false;
   };
diff --git a/llvm/test/tools/llvm-objcopy/ELF/discard-all.test b/llvm/test/tools/llvm-objcopy/ELF/discard-all.test
index 50cad3ae9f533..ce65026715f71 100644
--- a/llvm/test/tools/llvm-objcopy/ELF/discard-all.test
+++ b/llvm/test/tools/llvm-objcopy/ELF/discard-all.test
@@ -32,6 +32,14 @@ Sections:
     Address:         0x1000
     AddressAlign:    0x0000000000000010
     Size:            64
+  - Name:            .rela.text
+    Type:            SHT_RELA
+    Link:            .symtab
+    Info:            .text
+    Relocations:
+      - Offset: 0
+        Symbol: Referenced
+        Type:   R_X86_64_PC32
 Symbols:
   - Name:     Local
     Type:     STT_FUNC
@@ -49,6 +57,8 @@ Symbols:
     Section:  .text
     Value:    0x1010
     Binding:  STB_GLOBAL
+  - Name:     Referenced
+    Section:  .text
   - Name:     Weak
     Type:     STT_FUNC
     Size:     8
@@ -85,6 +95,15 @@ Symbols:
 #CHECK-NEXT:    Section: Undefined
 #CHECK-NEXT:  }
 #CHECK-NEXT:  Symbol {
+#CHECK-NEXT:    Name: Referenced
+#CHECK-NEXT:    Value: 0x0
+#CHECK-NEXT:    Size: 0
+#CHECK-NEXT:    Binding: Local
+#CHECK-NEXT:    Type: None
+#CHECK-NEXT:    Other: 0
+#CHECK-NEXT:    Section: .text
+#CHECK-NEXT:  }
+#CHECK-NEXT:  Symbol {
 #CHECK-NEXT:    Name: Global
 #CHECK-NEXT:    Value: 0x1010
 #CHECK-NEXT:    Size: 8
diff --git a/llvm/test/tools/llvm-objcopy/ELF/discard-locals-rel.test b/llvm/test/tools/llvm-objcopy/ELF/discard-locals-rel.test
deleted file mode 100644
index 00bb8fcf18205..0000000000000
--- a/llvm/test/tools/llvm-objcopy/ELF/discard-locals-rel.test
+++ /dev/null
@@ -1,26 +0,0 @@
-# RUN: yaml2obj %s -o %t
-# RUN: not llvm-objcopy --discard-locals %t %t2 2>&1 | FileCheck %s -DFILE=%t
-
-!ELF
-FileHeader:
-  Class:           ELFCLASS64
-  Data:            ELFDATA2LSB
-  Type:            ET_REL
-  Machine:         EM_X86_64
-Sections:
-  - Name:            .text
-    Type:            SHT_PROGBITS
-  - Name:            .rel.text
-    Type:            SHT_REL
-    Link:            .symtab
-    Info:            .text
-    Relocations:
-      - Offset: 0x1000
-        Symbol: .L.rel
-        Type:   R_X86_64_PC32
-Symbols:
-  - Name:     .L.rel
-    Type:     STT_FUNC
-    Section:  .text
-
-# CHECK: error: '[[FILE]]': not stripping symbol '.L.rel' because it is named in a relocation
diff --git a/llvm/test/tools/llvm-objcopy/ELF/discard-locals.test b/llvm/test/tools/llvm-objcopy/ELF/discard-locals.test
index 4aba1cd1c782a..c1fe0f2b02b6e 100644
--- a/llvm/test/tools/llvm-objcopy/ELF/discard-locals.test
+++ b/llvm/test/tools/llvm-objcopy/ELF/discard-locals.test
@@ -29,6 +29,14 @@ FileHeader:
 Sections:
   - Name:            .text
     Type:            SHT_PROGBITS
+  - Name:            .rela.text
+    Type:            SHT_RELA
+    Link:            .symtab
+    Info:            .text
+    Relocations:
+      - Offset: 0
+        Symbol: .L.referenced
+        Type:   R_X86_64_PC32
   - Name:            .LLVM.Custom.Section
     Type:            SHT_PROGBITS
 Symbols:
@@ -48,6 +56,8 @@ Symbols:
   - Name:     .L.undefined
   - Name:     .L.abs
     Index:    SHN_ABS
+  - Name:     .L.referenced
+    Section:  .text
   - Name:     .L.Global
     Type:     STT_FUNC
     Section:  .text
@@ -109,6 +119,15 @@ Symbols:
 # CHECK-NEXT:     Section: Undefined
 # CHECK-NEXT:   }
 # CHECK-NEXT:   Symbol {
+# CHECK-NEXT:     Name: .L.referenced
+# CHECK-NEXT:     Value:
+# CHECK-NEXT:     Size:
+# CHECK-NEXT:     Binding: Local
+# CHECK-NEXT:     Type: None
+# CHECK-NEXT:     Other:
+# CHECK-NEXT:     Section: .text
+# CHECK-NEXT:   }
+# CHECK-NEXT:   Symbol {
 # CHECK-NEXT:     Name: .L.Global
 # CHECK-NEXT:     Value:
 # CHECK-NEXT:     Size:

>From 11a297b4acebbe38f70d63520c82b3371ccf98d0 Mon Sep 17 00:00:00 2001
From: Fangrui Song <i at maskray.me>
Date: Mon, 10 Mar 2025 20:13:12 -0700
Subject: [PATCH 2/3] .

Created using spr 1.3.5-bogner
---
 llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp b/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp
index 43aeff18c41b2..5a785d7afd1e4 100644
--- a/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp
+++ b/llvm/lib/ObjCopy/ELF/ELFObjcopy.cpp
@@ -400,8 +400,7 @@ static Error updateAndRemoveSymbols(const CommonConfig &Config,
         return true;
       // We want to remove undefined symbols if all references have been
       // stripped.
-      if (!Config.OnlySection.empty() && !Sym.Referenced &&
-          Sym.getShndx() == SHN_UNDEF)
+      if (!Config.OnlySection.empty() && Sym.getShndx() == SHN_UNDEF)
         return true;
     }
 

>From 6115e9b35a200c3327791d1cf85c457473f95b52 Mon Sep 17 00:00:00 2001
From: Fangrui Song <i at maskray.me>
Date: Tue, 11 Mar 2025 21:16:23 -0700
Subject: [PATCH 3/3] fix typo

Created using spr 1.3.5-bogner
---
 llvm/docs/ReleaseNotes.md | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/llvm/docs/ReleaseNotes.md b/llvm/docs/ReleaseNotes.md
index 9d79a54eff78a..3d608c636a8f6 100644
--- a/llvm/docs/ReleaseNotes.md
+++ b/llvm/docs/ReleaseNotes.md
@@ -160,7 +160,7 @@ Changes to the LLVM tools
 
 * llvm-objcopy now supports the `--update-section` flag for intermediate Mach-O object files.
 * llvm-strip now supports continuing to process files on encountering an error.
-* In llvm-objcopy's ELF port, `--discard-locals` and `--discard-all` now allow and preserve symbols references by relocations.
+* In llvm-objcopy's ELF port, `--discard-locals` and `--discard-all` now allow and preserve symbols referenced by relocations.
 
 Changes to LLDB
 ---------------------------------



More information about the llvm-commits mailing list