[PATCH] D95198: [ELF] Fix program header alloc when first PT_LOAD is not at lowest VMA

Patrick Oppenlander via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Wed Mar 17 22:46:00 PDT 2021


pattop updated this revision to Diff 331468.
pattop added a comment.

Reduce changes, update test, clarify intent.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D95198/new/

https://reviews.llvm.org/D95198

Files:
  lld/ELF/LinkerScript.cpp
  lld/test/ELF/linkerscript/offset-headers.s


Index: lld/test/ELF/linkerscript/offset-headers.s
===================================================================
--- /dev/null
+++ lld/test/ELF/linkerscript/offset-headers.s
@@ -0,0 +1,31 @@
+# REQUIRES: x86
+# RUN: split-file %s %t
+# RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %t/test.s -o %t.o
+# RUN: ld.lld -o %t1 --script %t/test.lds %t.o
+# RUN: llvm-readelf -l %t1 | FileCheck %s
+
+# CHECK:      Type Offset   VirtAddr           PhysAddr           FileSiz  MemSiz   Flg Align
+# CHECK-NEXT: LOAD 0x000000 0x0000000000001000 0x0000000000001000 0x0010b0 0x0010b0 R E 0x1000
+# CHECK-NEXT: LOAD 0x002000 0x0000000000000000 0x0000000000000000 0x001000 0x001000 RW  0x1000
+
+#--- test.s
+.global _start
+_start:
+ .rept 0x1000
+ nop
+ .endr
+
+.data
+ .rept 0x1000
+ .byte 0
+ .endr
+
+#--- test.lds
+PHDRS {
+    ph1 PT_LOAD FILEHDR PHDRS;
+    ph2 PT_LOAD;
+}
+SECTIONS {
+    .data 0 : {*(.data*)} :ph2
+    .text 0x1000 + SIZEOF_HEADERS : {*(.text*)} :ph1
+}
Index: lld/ELF/LinkerScript.cpp
===================================================================
--- lld/ELF/LinkerScript.cpp
+++ lld/ELF/LinkerScript.cpp
@@ -1149,9 +1149,16 @@
 // and we'll also remove the PT_PHDR segment.
 void LinkerScript::allocateHeaders(std::vector<PhdrEntry *> &phdrs) {
   uint64_t min = std::numeric_limits<uint64_t>::max();
-  for (OutputSection *sec : outputSections)
-    if (sec->flags & SHF_ALLOC)
-      min = std::min<uint64_t>(min, sec->addr);
+  auto hdrs = {Out::elfHeader, Out::programHeaders};
+  for (OutputSection *hdr : hdrs)
+    if (hdr->ptLoad)
+      for (OutputSection *sec : hdr->ptLoad->sections)
+        if (llvm::find(hdrs, sec) == hdrs.end())
+          min = std::min(min, sec->addr);
+  if (min == std::numeric_limits<uint64_t>::max())
+    for (OutputSection *sec : outputSections)
+      if (sec->flags & SHF_ALLOC)
+        min = std::min<uint64_t>(min, sec->addr);
 
   auto it = llvm::find_if(
       phdrs, [](const PhdrEntry *e) { return e->p_type == PT_LOAD; });


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D95198.331468.patch
Type: text/x-patch
Size: 2015 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20210318/0eea63f4/attachment.bin>


More information about the llvm-commits mailing list