Index: ELF/Config.h =================================================================== --- ELF/Config.h +++ ELF/Config.h @@ -167,6 +167,7 @@ bool WriteAddends; bool ZCombreloc; bool ZCopyreloc; + bool ZKeeptextsectionprefix; bool ZExecstack; bool ZHazardplt; bool ZNodelete; Index: ELF/Driver.cpp =================================================================== --- ELF/Driver.cpp +++ ELF/Driver.cpp @@ -761,6 +761,8 @@ Args.hasFlag(OPT_warn_symbol_ordering, OPT_no_warn_symbol_ordering, true); Config->ZCombreloc = getZFlag(Args, "combreloc", "nocombreloc", true); Config->ZCopyreloc = getZFlag(Args, "copyreloc", "nocopyreloc", true); + Config->ZKeeptextsectionprefix = getZFlag( + Args, "keep-text-section-prefix", "nokeep-text-section-prefix", false); Config->ZExecstack = getZFlag(Args, "execstack", "noexecstack", false); Config->ZHazardplt = hasZOption(Args, "hazardplt"); Config->ZNodelete = hasZOption(Args, "nodelete"); Index: ELF/Writer.cpp =================================================================== --- ELF/Writer.cpp +++ ELF/Writer.cpp @@ -88,6 +88,12 @@ }; } // anonymous namespace +static bool isSectionPrefix(StringRef PrefixName, StringRef SectionName) { + if (SectionName.startswith(PrefixName) || SectionName == PrefixName.drop_back()) + return true; + return false; +} + StringRef elf::getOutputSectionName(InputSectionBase *S) { if (Config->Relocatable) return S->Name; @@ -104,13 +110,23 @@ } } + // This check is for -z keep-text-section-prefix. This option separates text + // sections with prefix ".text.hot" or ".text.unlikely" or ".text.startup" or + // ".text.exit". + if (Config->ZKeeptextsectionprefix) { + for (StringRef V : + {".text.hot.", ".text.unlikely.", ".text.startup.", ".text.exit."}) { + if (isSectionPrefix(V, S->Name)) + return V.drop_back(); + } + } + for (StringRef V : {".text.", ".rodata.", ".data.rel.ro.", ".data.", ".bss.rel.ro.", ".bss.", ".init_array.", ".fini_array.", ".ctors.", ".dtors.", ".tbss.", ".gcc_except_table.", ".tdata.", ".ARM.exidx.", ".ARM.extab."}) { - StringRef Prefix = V.drop_back(); - if (S->Name.startswith(V) || S->Name == Prefix) - return Prefix; + if (isSectionPrefix(V, S->Name)) + return V.drop_back(); } // CommonSection is identified as "COMMON" in linker scripts.