Skip to content

Commit 6605523

Browse files
committed
[TargetLoweringObjectFileImpl] Produce .text.hot. instead of .text.hot for -fno-unique-section-names
GNU ld's internal linker script uses (https://sourceware.org/git/?p=binutils-gdb.git;a=commit;h=add44f8d5c5c05e08b11e033127a744d61c26aee) .text : { *(.text.unlikely .text.*_unlikely .text.unlikely.*) *(.text.exit .text.exit.*) *(.text.startup .text.startup.*) *(.text.hot .text.hot.*) *(SORT(.text.sorted.*)) *(.text .stub .text.* .gnu.linkonce.t.*) /* .gnu.warning sections are handled specially by elf.em. */ *(.gnu.warning) } Because `*(.text.exit .text.exit.*)` is ordered before `*(.text .text.*)`, in a -ffunction-sections build, the C library function `exit` will be placed before other functions. gold's `-z keep-text-section-prefix` has the same problem. In lld, `-z keep-text-section-prefix` recognizes `.text.{exit,hot,startup,unlikely,unknown}.*`, but not `.text.{exit,hot,startup,unlikely,unknown}`, to avoid the strange placement problem. In -fno-function-sections or -fno-unique-section-names mode, a function whose `function_section_prefix` is set to `.exit"` will go to the output section `.text` instead of `.text.exit` when linked by lld. To address the problem, append a dot to become `.text.exit.` Reviewed By: grimar Differential Revision: https://reviews.llvm.org/D79600
1 parent 363393c commit 6605523

File tree

2 files changed

+12
-2
lines changed

2 files changed

+12
-2
lines changed

llvm/lib/CodeGen/TargetLoweringObjectFileImpl.cpp

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -611,15 +611,19 @@ getELFSectionNameForGlobal(const GlobalObject *GO, SectionKind Kind,
611611
Name = getSectionPrefixForGlobal(Kind);
612612
}
613613

614+
bool HasPrefix = false;
614615
if (const auto *F = dyn_cast<Function>(GO)) {
615-
if (Optional<StringRef> Prefix = F->getSectionPrefix())
616+
if (Optional<StringRef> Prefix = F->getSectionPrefix()) {
616617
Name += *Prefix;
618+
HasPrefix = true;
619+
}
617620
}
618621

619622
if (UniqueSectionName) {
620623
Name.push_back('.');
621624
TM.getNameWithPrefix(Name, GO, Mang, /*MayAlwaysUsePrivate*/true);
622-
}
625+
} else if (HasPrefix)
626+
Name.push_back('.');
623627
return Name;
624628
}
625629

llvm/test/Transforms/CodeGenPrepare/X86/section.ll

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,14 @@
11
; RUN: opt < %s -codegenprepare -S | FileCheck %s
2+
; RUN: llc < %s | FileCheck --check-prefix=ASM1 %s
3+
; RUN: llc < %s -function-sections | FileCheck --check-prefix=ASM2 %s
24

35
target triple = "x86_64-pc-linux-gnu"
46

57
; This tests that hot/cold functions get correct section prefix assigned
68

79
; CHECK: hot_func1{{.*}}!section_prefix ![[HOT_ID:[0-9]+]]
10+
; ASM1: .section .text.hot.,"ax",@progbits
11+
; ASM2: .section .text.hot.hot_func1,"ax",@progbits
812
; The entry is hot
913
define void @hot_func1() !prof !15 {
1014
ret void
@@ -40,6 +44,8 @@ for.end:
4044
; not call site VP metadata (which can exist on value profiled memcpy,
4145
; or possibly left behind after static analysis based devirtualization).
4246
; CHECK: cold_func1{{.*}}!section_prefix ![[COLD_ID:[0-9]+]]
47+
; ASM1: .section .text.unlikely.,"ax",@progbits
48+
; ASM2: .section .text.unlikely.cold_func1,"ax",@progbits
4349
define void @cold_func1() !prof !16 {
4450
call void @hot_func1(), !prof !17
4551
call void @hot_func1(), !prof !17

0 commit comments

Comments
 (0)