diff options
author | Rafael Espindola <rafael.espindola@gmail.com> | 2017-02-02 21:26:06 +0000 |
---|---|---|
committer | Rafael Espindola <rafael.espindola@gmail.com> | 2017-02-02 21:26:06 +0000 |
commit | 13a79bbfe583e1d8cc85d241b580907260065eb8 (patch) | |
tree | 538d692317f9990cae5ae6bb23bc23fd3c5803ef /llvm/lib | |
parent | bb8dcc6aec4071c114ed4205f01c9163dbd1bf00 (diff) | |
download | bcm5719-llvm-13a79bbfe583e1d8cc85d241b580907260065eb8.tar.gz bcm5719-llvm-13a79bbfe583e1d8cc85d241b580907260065eb8.zip |
Change how we handle section symbols on ELF.
On ELF every section can have a corresponding section symbol. When in
an assembly file we have
.quad .text
the '.text' refers to that symbol.
The way we used to handle them is to leave .text an undefined symbol
until the very end when the object writer would map them to the
actual section symbol.
The problem with that is that anything before the end would see an
undefined symbol. This could result in bad diagnostics
(test/MC/AArch64/label-arithmetic-diags-elf.s), or incorrect results
when using the asm streamer (est/MC/Mips/expansion-jal-sym-pic.s).
Fixing this will also allow using the section symbol earlier for
setting sh_link of SHF_METADATA sections.
This patch includes a few hacks to avoid changing our behaviour when
handling conflicts between section symbols and other symbols. I
reported pr31850 to track that.
llvm-svn: 293936
Diffstat (limited to 'llvm/lib')
-rw-r--r-- | llvm/lib/MC/ELFObjectWriter.cpp | 16 | ||||
-rw-r--r-- | llvm/lib/MC/MCContext.cpp | 73 | ||||
-rw-r--r-- | llvm/lib/MC/MCELFStreamer.cpp | 11 | ||||
-rw-r--r-- | llvm/lib/MC/MCObjectFileInfo.cpp | 28 | ||||
-rw-r--r-- | llvm/lib/MC/MCParser/AsmParser.cpp | 1 | ||||
-rw-r--r-- | llvm/lib/MC/MCSymbolELF.cpp | 4 | ||||
-rw-r--r-- | llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp | 5 |
7 files changed, 63 insertions, 75 deletions
diff --git a/llvm/lib/MC/ELFObjectWriter.cpp b/llvm/lib/MC/ELFObjectWriter.cpp index 0e02cdb4ca0..e9f4f1cce33 100644 --- a/llvm/lib/MC/ELFObjectWriter.cpp +++ b/llvm/lib/MC/ELFObjectWriter.cpp @@ -371,22 +371,6 @@ uint64_t ELFObjectWriter::SymbolValue(const MCSymbol &Sym, void ELFObjectWriter::executePostLayoutBinding(MCAssembler &Asm, const MCAsmLayout &Layout) { - // Section symbols are used as definitions for undefined symbols with matching - // names. If there are multiple sections with the same name, the first one is - // used. - for (const MCSection &Sec : Asm) { - const MCSymbol *Begin = Sec.getBeginSymbol(); - if (!Begin) - continue; - - const MCSymbol *Alias = Asm.getContext().lookupSymbol(Begin->getName()); - if (!Alias || !Alias->isUndefined()) - continue; - - Renames.insert( - std::make_pair(cast<MCSymbolELF>(Alias), cast<MCSymbolELF>(Begin))); - } - // The presence of symbol versions causes undefined symbols and // versions declared with @@@ to be renamed. for (const MCSymbol &A : Asm.symbols()) { diff --git a/llvm/lib/MC/MCContext.cpp b/llvm/lib/MC/MCContext.cpp index 4798991ceed..16c2c99be67 100644 --- a/llvm/lib/MC/MCContext.cpp +++ b/llvm/lib/MC/MCContext.cpp @@ -80,7 +80,6 @@ void MCContext::reset() { MCSubtargetAllocator.DestroyAll(); UsedNames.clear(); Symbols.clear(); - SectionSymbols.clear(); Allocator.Reset(); Instances.clear(); CompilationDir.clear(); @@ -124,18 +123,6 @@ MCSymbol *MCContext::getOrCreateSymbol(const Twine &Name) { return Sym; } -MCSymbolELF *MCContext::getOrCreateSectionSymbol(const MCSectionELF &Section) { - MCSymbol *&Sym = SectionSymbols[&Section]; - if (Sym) - return cast<MCSymbolELF>(Sym); - - StringRef Name = Section.getSectionName(); - auto NameIter = UsedNames.insert(std::make_pair(Name, false)).first; - Sym = new (&*NameIter, *this) MCSymbolELF(&*NameIter, /*isTemporary*/ false); - - return cast<MCSymbolELF>(Sym); -} - MCSymbol *MCContext::getOrCreateFrameAllocSymbol(StringRef FuncName, unsigned Idx) { return getOrCreateSymbol(Twine(MAI->getPrivateGlobalPrefix()) + FuncName + @@ -316,6 +303,38 @@ void MCContext::renameELFSection(MCSectionELF *Section, StringRef Name) { const_cast<MCSectionELF *>(Section)->setSectionName(CachedName); } +MCSectionELF *MCContext::createELFSectionImpl(StringRef Section, unsigned Type, + unsigned Flags, SectionKind K, + unsigned EntrySize, + const MCSymbolELF *Group, + unsigned UniqueID, + const MCSectionELF *Associated) { + + MCSymbolELF *R; + MCSymbol *&Sym = Symbols[Section]; + if (Sym && Sym->isUndefined()) { + R = cast<MCSymbolELF>(Sym); + } else { + auto NameIter = UsedNames.insert(std::make_pair(Section, false)).first; + R = new (&*NameIter, *this) MCSymbolELF(&*NameIter, /*isTemporary*/ false); + if (!Sym) + Sym = R; + } + R->setBinding(ELF::STB_LOCAL); + R->setType(ELF::STT_SECTION); + R->setRedefinable(true); + + auto *Ret = new (ELFAllocator.Allocate()) MCSectionELF( + Section, Type, Flags, K, EntrySize, Group, UniqueID, R, Associated); + + auto *F = new MCDataFragment(); + Ret->getFragmentList().insert(Ret->begin(), F); + F->setParent(Ret); + R->setFragment(F); + + return Ret; +} + MCSectionELF *MCContext::createELFRelSection(const Twine &Name, unsigned Type, unsigned Flags, unsigned EntrySize, const MCSymbolELF *Group, @@ -325,9 +344,9 @@ MCSectionELF *MCContext::createELFRelSection(const Twine &Name, unsigned Type, std::tie(I, Inserted) = ELFRelSecNames.insert(std::make_pair(Name.str(), true)); - return new (ELFAllocator.Allocate()) - MCSectionELF(I->getKey(), Type, Flags, SectionKind::getReadOnly(), - EntrySize, Group, true, nullptr, Associated); + return createELFSectionImpl(I->getKey(), Type, Flags, + SectionKind::getReadOnly(), EntrySize, Group, + true, Associated); } MCSectionELF *MCContext::getELFNamedSection(const Twine &Prefix, @@ -339,21 +358,19 @@ MCSectionELF *MCContext::getELFNamedSection(const Twine &Prefix, MCSectionELF *MCContext::getELFSection(const Twine &Section, unsigned Type, unsigned Flags, unsigned EntrySize, - const Twine &Group, unsigned UniqueID, - const char *BeginSymName) { + const Twine &Group, unsigned UniqueID) { MCSymbolELF *GroupSym = nullptr; if (!Group.isTriviallyEmpty() && !Group.str().empty()) GroupSym = cast<MCSymbolELF>(getOrCreateSymbol(Group)); return getELFSection(Section, Type, Flags, EntrySize, GroupSym, UniqueID, - BeginSymName, nullptr); + nullptr); } MCSectionELF *MCContext::getELFSection(const Twine &Section, unsigned Type, unsigned Flags, unsigned EntrySize, const MCSymbolELF *GroupSym, unsigned UniqueID, - const char *BeginSymName, const MCSectionELF *Associated) { StringRef Group = ""; if (GroupSym) @@ -375,22 +392,16 @@ MCSectionELF *MCContext::getELFSection(const Twine &Section, unsigned Type, else Kind = SectionKind::getReadOnly(); - MCSymbol *Begin = nullptr; - if (BeginSymName) - Begin = createTempSymbol(BeginSymName, false); - - MCSectionELF *Result = new (ELFAllocator.Allocate()) - MCSectionELF(CachedName, Type, Flags, Kind, EntrySize, GroupSym, UniqueID, - Begin, Associated); + MCSectionELF *Result = createELFSectionImpl( + CachedName, Type, Flags, Kind, EntrySize, GroupSym, UniqueID, Associated); Entry.second = Result; return Result; } MCSectionELF *MCContext::createELFGroupSection(const MCSymbolELF *Group) { - MCSectionELF *Result = new (ELFAllocator.Allocate()) - MCSectionELF(".group", ELF::SHT_GROUP, 0, SectionKind::getReadOnly(), 4, - Group, ~0, nullptr, nullptr); - return Result; + return createELFSectionImpl(".group", ELF::SHT_GROUP, 0, + SectionKind::getReadOnly(), 4, Group, ~0, + nullptr); } MCSectionCOFF *MCContext::getCOFFSection(StringRef Section, diff --git a/llvm/lib/MC/MCELFStreamer.cpp b/llvm/lib/MC/MCELFStreamer.cpp index 0ef1b2a8bdc..47e9189415e 100644 --- a/llvm/lib/MC/MCELFStreamer.cpp +++ b/llvm/lib/MC/MCELFStreamer.cpp @@ -148,16 +148,7 @@ void MCELFStreamer::ChangeSection(MCSection *Section, Asm.registerSymbol(*Grp); this->MCObjectStreamer::ChangeSection(Section, Subsection); - MCContext &Ctx = getContext(); - auto *Begin = cast_or_null<MCSymbolELF>(Section->getBeginSymbol()); - if (!Begin) { - Begin = Ctx.getOrCreateSectionSymbol(*SectionELF); - Section->setBeginSymbol(Begin); - } - if (Begin->isUndefined()) { - Asm.registerSymbol(*Begin); - Begin->setType(ELF::STT_SECTION); - } + Asm.registerSymbol(*Section->getBeginSymbol()); } void MCELFStreamer::EmitWeakReference(MCSymbol *Alias, const MCSymbol *Symbol) { diff --git a/llvm/lib/MC/MCObjectFileInfo.cpp b/llvm/lib/MC/MCObjectFileInfo.cpp index 9238520cc59..5e81026ad40 100644 --- a/llvm/lib/MC/MCObjectFileInfo.cpp +++ b/llvm/lib/MC/MCObjectFileInfo.cpp @@ -506,10 +506,9 @@ void MCObjectFileInfo::initELFMCObjectFileInfo(const Triple &T) { COFFDebugTypesSection = nullptr; // Debug Info Sections. - DwarfAbbrevSection = Ctx->getELFSection(".debug_abbrev", ELF::SHT_PROGBITS, 0, - "section_abbrev"); - DwarfInfoSection = - Ctx->getELFSection(".debug_info", ELF::SHT_PROGBITS, 0, "section_info"); + DwarfAbbrevSection = + Ctx->getELFSection(".debug_abbrev", ELF::SHT_PROGBITS, 0); + DwarfInfoSection = Ctx->getELFSection(".debug_info", ELF::SHT_PROGBITS, 0); DwarfLineSection = Ctx->getELFSection(".debug_line", ELF::SHT_PROGBITS, 0); DwarfFrameSection = Ctx->getELFSection(".debug_frame", ELF::SHT_PROGBITS, 0); DwarfPubNamesSection = @@ -527,21 +526,21 @@ void MCObjectFileInfo::initELFMCObjectFileInfo(const Triple &T) { DwarfARangesSection = Ctx->getELFSection(".debug_aranges", ELF::SHT_PROGBITS, 0); DwarfRangesSection = - Ctx->getELFSection(".debug_ranges", ELF::SHT_PROGBITS, 0, "debug_range"); - DwarfMacinfoSection = Ctx->getELFSection(".debug_macinfo", ELF::SHT_PROGBITS, - 0, "debug_macinfo"); + Ctx->getELFSection(".debug_ranges", ELF::SHT_PROGBITS, 0); + DwarfMacinfoSection = + Ctx->getELFSection(".debug_macinfo", ELF::SHT_PROGBITS, 0); // DWARF5 Experimental Debug Info // Accelerator Tables DwarfAccelNamesSection = - Ctx->getELFSection(".apple_names", ELF::SHT_PROGBITS, 0, "names_begin"); + Ctx->getELFSection(".apple_names", ELF::SHT_PROGBITS, 0); DwarfAccelObjCSection = - Ctx->getELFSection(".apple_objc", ELF::SHT_PROGBITS, 0, "objc_begin"); - DwarfAccelNamespaceSection = Ctx->getELFSection( - ".apple_namespaces", ELF::SHT_PROGBITS, 0, "namespac_begin"); + Ctx->getELFSection(".apple_objc", ELF::SHT_PROGBITS, 0); + DwarfAccelNamespaceSection = + Ctx->getELFSection(".apple_namespaces", ELF::SHT_PROGBITS, 0); DwarfAccelTypesSection = - Ctx->getELFSection(".apple_types", ELF::SHT_PROGBITS, 0, "types_begin"); + Ctx->getELFSection(".apple_types", ELF::SHT_PROGBITS, 0); // Fission Sections DwarfInfoDWOSection = @@ -556,11 +555,10 @@ void MCObjectFileInfo::initELFMCObjectFileInfo(const Triple &T) { DwarfLineDWOSection = Ctx->getELFSection(".debug_line.dwo", ELF::SHT_PROGBITS, 0); DwarfLocDWOSection = - Ctx->getELFSection(".debug_loc.dwo", ELF::SHT_PROGBITS, 0, "skel_loc"); + Ctx->getELFSection(".debug_loc.dwo", ELF::SHT_PROGBITS, 0); DwarfStrOffDWOSection = Ctx->getELFSection(".debug_str_offsets.dwo", ELF::SHT_PROGBITS, 0); - DwarfAddrSection = - Ctx->getELFSection(".debug_addr", ELF::SHT_PROGBITS, 0, "addr_sec"); + DwarfAddrSection = Ctx->getELFSection(".debug_addr", ELF::SHT_PROGBITS, 0); // DWP Sections DwarfCUIndexSection = diff --git a/llvm/lib/MC/MCParser/AsmParser.cpp b/llvm/lib/MC/MCParser/AsmParser.cpp index f8744f5542e..f714aeef054 100644 --- a/llvm/lib/MC/MCParser/AsmParser.cpp +++ b/llvm/lib/MC/MCParser/AsmParser.cpp @@ -4417,6 +4417,7 @@ bool AsmParser::parseDirectiveComm(bool IsLocal) { return Error(Pow2AlignmentLoc, "invalid '.comm' or '.lcomm' directive " "alignment, can't be less than zero"); + Sym->redefineIfPossible(); if (!Sym->isUndefined()) return Error(IDLoc, "invalid symbol redefinition"); diff --git a/llvm/lib/MC/MCSymbolELF.cpp b/llvm/lib/MC/MCSymbolELF.cpp index ec7ef447ff8..ffa8260d434 100644 --- a/llvm/lib/MC/MCSymbolELF.cpp +++ b/llvm/lib/MC/MCSymbolELF.cpp @@ -42,6 +42,8 @@ enum { void MCSymbolELF::setBinding(unsigned Binding) const { setIsBindingSet(); + if (getType() == ELF::STT_SECTION && Binding != ELF::STB_LOCAL) + setType(ELF::STT_NOTYPE); unsigned Val; switch (Binding) { default: @@ -93,6 +95,8 @@ unsigned MCSymbolELF::getBinding() const { void MCSymbolELF::setType(unsigned Type) const { unsigned Val; + if (Type == ELF::STT_SECTION && getBinding() != ELF::STB_LOCAL) + return; switch (Type) { default: llvm_unreachable("Unsupported Binding"); diff --git a/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp b/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp index 7e56ba39eef..043b54b356a 100644 --- a/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp +++ b/llvm/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp @@ -1138,9 +1138,8 @@ inline void ARMELFStreamer::SwitchToEHSection(StringRef Prefix, const MCSymbolELF *Group = FnSection.getGroup(); if (Group) Flags |= ELF::SHF_GROUP; - MCSectionELF *EHSection = - getContext().getELFSection(EHSecName, Type, Flags, 0, Group, - FnSection.getUniqueID(), nullptr, &FnSection); + MCSectionELF *EHSection = getContext().getELFSection( + EHSecName, Type, Flags, 0, Group, FnSection.getUniqueID(), &FnSection); assert(EHSection && "Failed to get the required EH section"); |