When the assembler generates an unresolved fixup for a local symbol, it can convert the relocation to reference the section symbol (`STT_SECTION`) instead, folding the original symbol's offset within the section into the addend. This allows the original local symbol to be omitted from `.symtab`. The tradeoff is that the `STT_SECTION` symbol itself must be present, so the conversion saves `.symtab` entries only when a section has more than one local symbol referenced by relocations. This is common in practice: * Text sections often contain labels for jump targets or C++ exception handling. * DWARF `.debug_*` sections contain labels referenced by other `.debug_*` sections. * `SHF_STRINGS` sections (`.rodata.str1.1`, `.debug_str`, `.debug_line_str`) have a label for each string literal. ( Not all relocations are eligible for this conversion. PLT-generating and GOT-generating relocations, for example, may require dynamic relocations where the symbol identity is significant, so they must reference the original symbol. In GNU Assembler, the backend hook `tc_fix_adjustable` controls which relocation types are excluded from the conversion.) In certain scenarios, disabling the STT_SECTION adjustment is preferable. For instance, when range extension thunks for x86-64 are available, retaining the original foo0 and foo1 symbols in R_X86_64_PLT32 relocations allows the linker to generate descriptive thunk names like __X86_64CallThunk_foo0 With the unnamed section symbol, the linker cannot easily generate a descriptive name (if clang is used with -ffunction-sections and -fno-unique-section-names, the section will be .text instead of .text.foo0). call foo0 call foo1 .section .text.foo0,"ax" foo0: .section .text.foo1,"ax" foo1: (In lld/ELF's --branch-to-branch optimization https://github.com/llvm/llvm-project/pull/145579/ , it would be simpler if no assembler generated R_X86_64_PLT32 referencing STT_SECTION symbol.)
Added the write-up to https://maskray.me/blog/2025-03-16-relocation-generation-in-assemblers#section-symbol-adjustment Candidate option name: --adjust-reloc-syms={none,nonlocal,all} * all: adjust all eligible relocations to reference STT_SECTION * nonlocal: adjust eligible relocations that reference a non-local symbol * none: don't adjust relocations