Index: lld/trunk/ELF/LinkerScript.cpp =================================================================== --- lld/trunk/ELF/LinkerScript.cpp +++ lld/trunk/ELF/LinkerScript.cpp @@ -746,10 +746,15 @@ if (!Cmd) continue; - if (Cmd->Phdrs.empty()) - Cmd->Phdrs = DefPhdrs; - else + if (Cmd->Phdrs.empty()) { + OutputSection *Sec = Cmd->Sec; + // To match the bfd linker script behaviour, only propagate program + // headers to sections that are allocated. + if (Sec && (Sec->Flags & SHF_ALLOC)) + Cmd->Phdrs = DefPhdrs; + } else { DefPhdrs = Cmd->Phdrs; + } } removeEmptyCommands(); @@ -880,8 +885,6 @@ // Add output sections to program headers. for (OutputSectionCommand *Cmd : OutputSectionCommands) { OutputSection *Sec = Cmd->Sec; - if (!(Sec->Flags & SHF_ALLOC)) - break; // Assign headers specified by linker script for (size_t Id : getPhdrIndices(Sec)) { Index: lld/trunk/test/ELF/linkerscript/non-alloc-segment.s =================================================================== --- lld/trunk/test/ELF/linkerscript/non-alloc-segment.s +++ lld/trunk/test/ELF/linkerscript/non-alloc-segment.s @@ -0,0 +1,44 @@ +# REQUIRES: x86 +# RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %s -o %t.o + +################################################################################ +## Test that non-alloc section .foo can be assigned to a segment. Check that +## the values of the offset and file size of this segment's PHDR are correct. +## +## This functionality allows non-alloc metadata, which is not required at +## run-time, to be added to a custom segment in a file. This metadata may be +## read/edited by tools/loader using the values of the offset and file size from +## the custom segment's PHDR. This is particularly important if section headers +## have been stripped. +# RUN: echo "PHDRS {text PT_LOAD; foo 0x12345678;} \ +# RUN: SECTIONS { \ +# RUN: .text : {*(.text .text*)} :text \ +# RUN: .foo : {*(.foo)} :foo \ +# RUN: }" > %t.script +# RUN: ld.lld -o %t --script %t.script %t.o +# RUN: llvm-readobj -elf-output-style=GNU -s -l %t | FileCheck %s +# RUN: llvm-readobj -l %t | FileCheck --check-prefix=PHDR %s + +# CHECK: Program Headers: +# CHECK-NEXT: Type +# CHECK-NEXT: LOAD +# CHECK-NEXT: : 0x12345678 + +# CHECK: Section to Segment mapping: +# CHECK-NEXT: Segment Sections... +# CHECK-NEXT: 00 .text +# CHECK-NEXT: 01 .foo + +# PHDR: Type: (0x12345678) +# PHDR-NEXT: Offset: 0x1004 +# PHDR-NEXT: VirtualAddress +# PHDR-NEXT: PhysicalAddress +# PHDR-NEXT: FileSize: 4 + +.global _start +_start: + nop + +.section .foo + .align 4 + .long 0