1//===- ELFObject.cpp ------------------------------------------------------===// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7//===----------------------------------------------------------------------===// 26#include <unordered_set> 38 Obj.ProgramHdrSegment.Offset + Seg.
Index *
sizeof(Elf_Phdr);
39 Elf_Phdr &Phdr = *
reinterpret_cast<Elf_Phdr *
>(
B);
40 Phdr.p_type = Seg.
Type;
41 Phdr.p_flags = Seg.
Flags;
42 Phdr.p_offset = Seg.
Offset;
43 Phdr.p_vaddr = Seg.
VAddr;
44 Phdr.p_paddr = Seg.
PAddr;
47 Phdr.p_align = Seg.
Align;
69 Elf_Shdr &
Shdr = *
reinterpret_cast<Elf_Shdr *
>(
B);
103// Align to the largest field in Elf_Sym. 104 Sec.
Align = ELFT::Is64Bits ?
sizeof(Elf_Xword) :
sizeof(Elf_Word);
110usinguint = std::conditional_t<Is64, uint64_t, uint32_t>;
113 ELF::encodeCrel<Is64>(
OS, Relocations, [&](
constRelocation &R) {
114uint32_t CurSymIdx = R.RelocSymbol ? R.RelocSymbol->Index : 0;
116 std::make_signed_t<uint>(R.Addend)};
124 Sec.
Size = encodeCrel<ELFT::Is64Bits>(Sec.Relocations).size();
128// Align to the largest field in Elf_Rel(a). 129 Sec.
Align = ELFT::Is64Bits ?
sizeof(Elf_Xword) :
sizeof(Elf_Word);
140 Sec.
Size =
sizeof(Elf_Word) + Sec.GroupMembers.size() *
sizeof(Elf_Word);
160"cannot write symbol section index table '" +
166"cannot write symbol table '" + Sec.
Name +
172"cannot write relocation section '" + Sec.
Name +
178"cannot write '" + Sec.
Name +
"' out to binary");
183"cannot write '" + Sec.
Name +
"' out to binary");
194// Sign extended 32 bit addresses (e.g 0xFFFFFFFF80000000) are ok 195returnAddr > UINT32_MAX &&
Addr + 0x80000000 > UINT32_MAX;
206// Fills exactly Len bytes of buffer with hexadecimal characters 207// representing value 'X' 208template <
class T,
class Iterator>
210// Fill range with '0' 211 std::fill(It, It + Len,
'0');
213for (
longI = Len - 1;
I >= 0; --
I) {
214unsignedcharMod =
static_cast<unsignedchar>(
X) & 15;
215 *(It +
I) = hexdigit(
Mod,
false);
226 Checksum += checkedGetHex<uint8_t>(S.
take_front(2));
236auto Iter = Line.begin();
243StringRef S(Line.data() + 1, std::distance(Line.begin() + 1, Iter));
247assert(Iter == Line.end());
254if (R.HexData.size() == 0)
257"zero data length is not allowed for data records");
262// 20-bit segment address. Data length must be 2 bytes 264if (R.HexData.size() != 4)
267"segment address data should be 2 bytes in size");
271if (R.HexData.size() != 8)
273"start address data should be 4 bytes in size");
274// According to Intel HEX specification '03' record 275// only specifies the code address within the 20-bit 276// segmented address space of the 8086/80186. This 277// means 12 high order bits should be zeroes. 279 R.HexData.take_front(3) !=
"000")
281"start address exceeds 20 bit for 80x86");
284// 16-31 bits of linear base address 285if (R.HexData.size() != 4)
288"extended address data should be 2 bytes in size");
291// Unknown record type 293static_cast<unsigned>(R.Type));
298// Checks that IHEX line contains valid characters. 299// This allows converting hexadecimal data to integers 300// without extra verification. 305"missing ':' in the beginning of line.");
307for (
size_t Pos = 1; Pos < Line.size(); ++Pos)
308if (hexDigitValue(Line[Pos]) == -1U)
310"invalid character at position %zu.", Pos + 1);
317// ':' + Length + Address + Type + Checksum with empty data ':LLAAAATTCC' 320"line is too short: %zu chars.", Line.size());
326size_t DataLen = checkedGetHex<uint8_t>(Line.substr(1, 2));
329"invalid line length %zu (should be %zu)",
332 Rec.
Addr = checkedGetHex<uint16_t>(Line.substr(3, 4));
333 Rec.
Type = checkedGetHex<uint8_t>(Line.substr(7, 2));
334 Rec.
HexData = Line.substr(9, DataLen * 2);
356while (!
Data.empty()) {
357uint64_t DataSize = std::min<uint64_t>(
Data.size(), ChunkSize);
358if (
Addr > SegmentAddr + BaseAddr + 0xFFFFU) {
359if (
Addr > 0xFFFFFU) {
360// Write extended address record, zeroing segment address 363 SegmentAddr = writeSegmentAddr(0U);
364 BaseAddr = writeBaseAddr(
Addr);
366// We can still remain 16-bit 367 SegmentAddr = writeSegmentAddr(
Addr);
371assert(SegOffset <= 0xFFFFU);
372 DataSize = std::min(DataSize, 0x10000U - SegOffset);
383returnAddr & 0xF0000U;
411// Check that sizer has already done its work 413// We are free to pass an invalid pointer to writeSection as long 414// as we don't actually write any data. The real writer class has 415// to override this method . 441return Visitor.
visit(*
this);
445return Visitor.
visit(*
this);
450assert(LinkSection ==
nullptr);
451 LinkSection = &SymTab;
475"--decompress-debug-sections: ch_type (" +
477 Sec.
Name +
"' is unsupported");
482"failed to decompress section '" + Sec.
Name +
485static_cast<size_t>(Sec.
Size)))
487"failed to decompress section '" + Sec.
Name +
491 std::copy(Decompressed.
begin(), Decompressed.
end(), Buf);
498"cannot write compressed section '" + Sec.
Name +
503return Visitor.
visit(*
this);
507return Visitor.
visit(*
this);
511return Visitor.
visit(*
this);
515return Visitor.
visit(*
this);
520while (!HexData.
empty()) {
521 Data.push_back(checkedGetHex<uint8_t>(HexData.
take_front(2)));
529"cannot write compressed section '" + Sec.
Name +
537switch (Sec.CompressionType) {
548 Chdr.ch_size = Sec.DecompressedSize;
549 Chdr.ch_addralign = Sec.DecompressedAlign;
550 memcpy(Buf, &Chdr,
sizeof(Chdr));
553 std::copy(Sec.CompressedData.begin(), Sec.CompressedData.end(), Buf);
560 :
SectionBase(Sec), CompressionType(CompressionType),
561 DecompressedSize(Sec.OriginalData.
size()), DecompressedAlign(Sec.
Align) {
569Size = ChdrSize + CompressedData.
size();
577 DecompressedSize(DecompressedSize), DecompressedAlign(DecompressedAlign) {
582return Visitor.
visit(*
this);
586return Visitor.
visit(*
this);
607return Visitor.
visit(*
this);
611return Visitor.
visit(*
this);
617llvm::copy(Sec.Indexes,
reinterpret_cast<Elf_Word *
>(Buf));
629" is not a symbol table");
641return Visitor.
visit(*
this);
645return Visitor.
visit(*
this);
681// Large indexes force us to clarify exactly what this function should do. This 682// function should return the value that will appear in st_shndx when written 692// This means that we don't have a defined section but we do need to 693// output a legitimate section index. 705void SymbolTableSection::assignIndices() {
722Sym.DefinedIn = DefinedIn;
723if (DefinedIn !=
nullptr)
725if (DefinedIn ==
nullptr) {
732Sym.Visibility = Visibility;
733Sym.Size = SymbolSize;
735Symbols.emplace_back(std::make_unique<Symbol>(
Sym));
744if (!AllowBrokenLinks)
747"string table '%s' cannot be removed because it is " 748"referenced by the symbol table '%s'",
759 std::stable_partition(
791"Symbol table has link index of " +
Twine(
Link) +
792" which is not a valid index",
793"Symbol table has link index of " +
Twine(
Link) +
794" which is not a string table");
808 MaxLocalIndex = std::max(MaxLocalIndex,
Sym->Index);
810// Now we need to set the Link and Info fields. 812Info = MaxLocalIndex + 1;
816// Reserve proper amount of space in section index table, so we can 817// layout sections correctly. We will fill the table with correct 818// indexes later in fillShdnxTable. 822// Add all of our strings to SymbolNames so that SymbolNames has the right 823// size before layout is decided. 824// If the symbol names section has been removed, don't try to add strings to 834// Fill section index table with real section indexes. This function must 835// be called after assignOffsets. 836for (
const std::unique_ptr<Symbol> &
Sym :
Symbols) {
856returnSym.takeError();
858returnconst_cast<Symbol *
>(*Sym);
863 Elf_Sym *
Sym =
reinterpret_cast<Elf_Sym *
>(Out.getBufferStart() + Sec.
Offset);
864// Loop though symbols setting each entry of the symbol table. 879return Visitor.
visit(*
this);
883return Visitor.
visit(*
this);
902if (!AllowBrokenLinks)
905"symbol table '%s' cannot be removed because it is " 906"referenced by the relocation section '%s'",
912if (!R.RelocSymbol || !R.RelocSymbol->DefinedIn ||
913 !
ToRemove(R.RelocSymbol->DefinedIn))
916"section '%s' cannot be removed: (%s+0x%" PRIx64
917") has relocation against symbol '%s'",
918 R.RelocSymbol->DefinedIn->Name.data(),
920 R.RelocSymbol->Name.c_str());
926template <
class SymTabType>
932"Link field value " +
Twine(Link) +
" in section " +
Name +
934"Link field value " +
Twine(Link) +
" in section " +
Name +
935" is not a symbol table");
945" in section " +
Name +
" is invalid");
956template <
class SymTabType>
958 this->Link = Symbols ? Symbols->Index : 0;
960if (SecToApplyRel !=
nullptr)
961 this->
Info = SecToApplyRel->Index;
969 Rela.r_addend = Addend;
972template <
class RelRange,
class T>
973staticvoidwriteRel(
const RelRange &Relocations,
T *Buf,
bool IsMips64EL) {
974for (
constauto &Reloc : Relocations) {
975 Buf->r_offset = Reloc.Offset;
977 Buf->setSymbolAndType(Reloc.RelocSymbol ? Reloc.RelocSymbol->Index : 0,
978 Reloc.Type, IsMips64EL);
987autoContent = encodeCrel<ELFT::Is64Bits>(Sec.Relocations);
990writeRel(Sec.Relocations,
reinterpret_cast<Elf_Rel *
>(Buf),
993writeRel(Sec.Relocations,
reinterpret_cast<Elf_Rela *
>(Buf),
1000return Visitor.
visit(*
this);
1004return Visitor.
visit(*
this);
1010if (Reloc.RelocSymbol &&
ToRemove(*Reloc.RelocSymbol))
1013"not stripping symbol '%s' because it is named in a relocation",
1014 Reloc.RelocSymbol->Name.data());
1020if (Reloc.RelocSymbol)
1021 Reloc.RelocSymbol->Referenced =
true;
1026// Update the target section if it was replaced. 1037return Visitor.
visit(*
this);
1041return Visitor.
visit(*
this);
1047if (!AllowBrokenLinks)
1050"symbol table '%s' cannot be removed because it is " 1051"referenced by the relocation section '%s'",
1056// SecToApplyRel contains a section referenced by sh_info field. It keeps 1057// a section to which the relocation section applies. When we remove any 1058// sections we also remove their relocation sections. Since we do that much 1059// earlier, this assert should never be triggered. 1065bool AllowBrokenDependency,
1068if (!AllowBrokenDependency)
1070"section '%s' cannot be removed because it is " 1071"referenced by the section '%s'",
1072 LinkSection->
Name.data(), this->Name.data());
1073 LinkSection =
nullptr;
1080 this->
Link = SymTab ? SymTab->
Index : 0;
1081// Linker deduplication for GRP_COMDAT is based on Sym->Name. The local/global 1082// status is not part of the equation. If Sym is localized, the intention is 1083// likely to make the group fully localized. Drop GRP_COMDAT to suppress 1084// deduplication. See https://groups.google.com/g/generic-abi/c/2X6mR-s2zoc 1086 this->FlagWord &= ~GRP_COMDAT;
1092if (!AllowBrokenLinks)
1095"section '.symtab' cannot be removed because it is " 1096"referenced by the group section '%s'",
1108"symbol '%s' cannot be removed because it is " 1109"referenced by the section '%s[%d]'",
1110 Sym->
Name.data(), this->Name.data(), this->Index);
1127// As the header section of the group is removed, drop the Group flag in its 1130 Sec->
Flags &= ~SHF_GROUP;
1139" in section " +
Name +
" is invalid");
1146 HasSymTabLink =
true;
1147 LinkSection =
nullptr;
1157// The format for the .gnu_debuglink starts with the file name and is 1158// followed by a null terminator and then the CRC32 of the file. The CRC32 1159// should be 4 byte aligned. So we add the FileName size, a 1 for the null 1160// byte, and then finally push the size to alignment and add 4. 1162// The CRC32 will only be aligned if we align the whole section. 1165Name =
".gnu_debuglink";
1166// For sections not found in segments, OriginalOffset is only used to 1167// establish the order that sections should go in. By using the maximum 1168// possible offset we cause this section to wind up at the end. 1174 : FileName(
File), CRC32(PrecomputedCRC) {
1178template <
class ELFT>
1181reinterpret_cast<uint8_t *
>(Out.getBufferStart()) + Sec.
Offset;
1183reinterpret_cast<Elf_Word *
>(Buf + Sec.
Size -
sizeof(Elf_Word));
1190return Visitor.
visit(*
this);
1194return Visitor.
visit(*
this);
1197template <
class ELFT>
1201 endian::write32<ELFT::Endianness>(Buf++, Sec.FlagWord);
1203 endian::write32<ELFT::Endianness>(Buf++, S->
Index);
1208return Visitor.
visit(*
this);
1212return Visitor.
visit(*
this);
1215// Returns true IFF a section is wholly inside the range of a segment 1217// If a section is empty it should be treated like it has a size of 1. This is 1218// to clarify the case when an empty section lies on a boundary between two 1219// segments and ensures that the section "belongs" to the second segment and 1223// Ignore just added sections. 1233if (SectionIsTLS != SegmentIsTLS)
1244// Returns true IFF a segment's original offset is inside of another segment's 1254// Any segment without a parent segment should come before a segment 1255// that has a parent segment. 1256if (
A->OriginalOffset <
B->OriginalOffset)
1258if (
A->OriginalOffset >
B->OriginalOffset)
1260// If alignments are different, the one with a smaller alignment cannot be the 1261// parent; otherwise, layoutSegments will not respect the larger alignment 1262// requirement. This rule ensures that PT_LOAD/PT_INTERP/PT_GNU_RELRO/PT_TLS 1263// segments at the same offset will be aligned correctly. 1264if (
A->Align !=
B->Align)
1265returnA->Align >
B->Align;
1266returnA->Index <
B->Index;
1283 StrTab.
Name =
".strtab";
1285Obj->SectionNames = &StrTab;
1292 SymTab.
Name =
".symtab";
1293 SymTab.Link = StrTab->
Index;
1295// The symbol table always needs a null symbol 1296 SymTab.addSymbol(
"", 0, 0,
nullptr, 0, 0, 0, 0);
1298Obj->SymbolTable = &SymTab;
1315 DataSection.
Name =
".data";
1317 DataSection.Size =
Data.size();
1322 std::begin(SanitizedFilename), std::end(SanitizedFilename),
1323 [](
charC) {
return !isAlnum(
C); },
'_');
1324Twine Prefix =
Twine(
"_binary_") + SanitizedFilename;
1327/*Value=*/0, NewSymbolVisibility, 0, 0);
1329/*Value=*/DataSection.Size, NewSymbolVisibility, 0, 0);
1331/*Value=*/DataSection.Size, NewSymbolVisibility,
SHN_ABS,
1341return std::move(Err);
1344return std::move(
Obj);
1347// Adds sections from IHEX data file. Data should have been 1348// fully validated by this time. 1349void IHexELFBuilder::addDataSections() {
1351uint64_t SegmentAddr = 0, BaseAddr = 0;
1358// Ignore empty data records 1359if (R.HexData.empty())
1361 RecAddr = R.Addr + SegmentAddr + BaseAddr;
1363// OriginalOffset field is only used to sort sections before layout, so 1364// instead of keeping track of real offsets in IHEX file, and as 1365// layoutSections() and layoutSectionsForOnlyKeepDebug() use 1366// llvm::stable_sort(), we can just set it to a constant (zero). 1368".sec" + std::to_string(SecNo), RecAddr,
1372Section->appendHexData(R.HexData);
1377// 20-bit segment address. 1378 SegmentAddr = checkedGetHex<uint16_t>(R.HexData) << 4;
1382Obj->Entry = checkedGetHex<uint32_t>(R.HexData);
1386// 16-31 bits of linear base address 1387 BaseAddr = checkedGetHex<uint16_t>(R.HexData) << 16;
1401return std::move(Err);
1404return std::move(
Obj);
1407template <
class ELFT>
1409 std::optional<StringRef> ExtractPartition)
1410 : ElfFile(ElfObj.getELFFile()), Obj(Obj),
1411 ExtractPartition(ExtractPartition) {
1416for (
Segment &Parent : Obj.segments()) {
1417// Every segment will overlap with itself but we don't want a segment to 1418// be its own parent so we avoid that situation. 1420// We want a canonical "most parental" segment but this requires 1421// inspecting the ParentSegment. 1432if (!ExtractPartition)
1442"could not find partition named '" +
1443 *ExtractPartition +
"'");
1446template <
class ELFT>
1456if (Phdr.p_offset + Phdr.p_filesz > HeadersFile.
getBufSize())
1461" goes past the end of the file");
1464 (size_t)Phdr.p_filesz};
1466 Seg.
Type = Phdr.p_type;
1467 Seg.
Flags = Phdr.p_flags;
1469 Seg.
Offset = Phdr.p_offset + EhdrOffset;
1470 Seg.
VAddr = Phdr.p_vaddr;
1471 Seg.
PAddr = Phdr.p_paddr;
1474 Seg.
Align = Phdr.p_align;
1484auto &ElfHdr = Obj.ElfHdrSegment;
1486 ElfHdr.OriginalOffset = ElfHdr.Offset = EhdrOffset;
1488consttypename ELFT::Ehdr &Ehdr = HeadersFile.
getHeader();
1489auto &PrHdr = Obj.ProgramHdrSegment;
1492// The spec requires us to have p_vaddr % p_align == p_offset % p_align. 1493// Whereas this works automatically for ElfHdr, here OriginalOffset is 1494// always non-zero and to ensure the equation we assign the same value to 1496 PrHdr.OriginalOffset = PrHdr.Offset = PrHdr.VAddr = EhdrOffset + Ehdr.e_phoff;
1498 PrHdr.FileSize = PrHdr.MemSize = Ehdr.e_phentsize * Ehdr.e_phnum;
1499// The spec requires us to naturally align all the fields. 1500 PrHdr.Align =
sizeof(Elf_Addr);
1501 PrHdr.Index =
Index++;
1503// Now we do an O(n^2) loop through the segments in order to match up 1505for (
Segment &Child : Obj.segments())
1506 setParentSegment(Child);
1507 setParentSegment(ElfHdr);
1508 setParentSegment(PrHdr);
1513template <
class ELFT>
1517"invalid alignment " +
Twine(GroupSec->
Align) +
1518" of group section '" + GroupSec->
Name +
"'");
1521auto SymTab = SecTable.template getSectionOfType<SymbolTableSection>(
1523"link field value '" +
Twine(GroupSec->
Link) +
"' in section '" +
1524 GroupSec->
Name +
"' is invalid",
1525"link field value '" +
Twine(GroupSec->
Link) +
"' in section '" +
1526 GroupSec->
Name +
"' is not a symbol table");
1528return SymTab.takeError();
1533"info field value '" +
Twine(GroupSec->
Info) +
1534"' in section '" + GroupSec->
Name +
1535"' is not a valid symbol index");
1542"the content of the section " + GroupSec->
Name +
1548 GroupSec->
setFlagWord(endian::read32<ELFT::Endianness>(Word++));
1550uint32_tIndex = support::endian::read32<ELFT::Endianness>(Word);
1552 Index,
"group member index " +
Twine(Index) +
" in section '" +
1553 GroupSec->
Name +
"' is invalid");
1563template <
class ELFT>
1567returnShdr.takeError();
1576 ElfFile.symbols(*
Shdr);
1578return Symbols.takeError();
1585returnName.takeError();
1591"' has index SHN_XINDEX but no " 1592"SHT_SYMTAB_SHNDX section exists");
1593if (ShndxData.
data() ==
nullptr) {
1600 ElfFile.template getSectionContentsAsArray<Elf_Word>(**ShndxSec);
1602returnData.takeError();
1605if (ShndxData.
size() != Symbols->size())
1608"symbol section index table does not have the same number of " 1609"entries as the symbol table");
1611 Elf_Word
Index = ShndxData[&
Sym - Symbols->begin()];
1614"symbol '" + *
Name +
"' has invalid section index " +
Twine(Index));
1624"' has unsupported value greater than or equal " 1625"to SHN_LORESERVE: " +
1630Sym.st_shndx,
"symbol '" + *
Name +
1631"' is defined has invalid section index " +
1646template <
class ELFT>
1649template <
class ELFT>
1651 ToSet = Rela.r_addend;
1656for (
constauto &Rel : RelRange) {
1658 ToAdd.
Offset = Rel.r_offset;
1666"'" + Relocs->
Name +
"': relocation references symbol with index " +
1667Twine(
Sym) +
", but there is no symbol table");
1684if (Index ==
SHN_UNDEF || Index > Sections.size())
1686return Sections[Index - 1].get();
1697if (
T *Sec = dyn_cast<T>(*BaseSec))
1703template <
class ELFT>
1705switch (
Shdr.sh_type) {
1713returnData.takeError();
1717// If a string table is allocated we don't want to mess with it. That would 1718// mean altering the memory image. There are no special link types or 1719// anything so we can just use a Section. 1724returnData.takeError();
1729// Hash tables should refer to SHT_DYNSYM which we're not going to change. 1730// Because of this we don't need to mess with the hash tables either. 1734returnData.takeError();
1739returnData.takeError();
1744returnData.takeError();
1749returnData.takeError();
1751// Multiple SHT_SYMTAB sections are forbidden by the ELF gABI. 1752if (Obj.SymbolTable !=
nullptr)
1754"found multiple SHT_SYMTAB sections");
1756 Obj.SymbolTable = &SymTab;
1761 Obj.SectionIndexTable = &ShndxSection;
1769returnData.takeError();
1773returnName.takeError();
1779 *
Data, Chdr->ch_type, Chdr->ch_size, Chdr->ch_addralign));
1803 Sec->Name = SecName->str();
1804 Sec->Type = Sec->OriginalType =
Shdr.sh_type;
1805 Sec->Flags = Sec->OriginalFlags =
Shdr.sh_flags;
1806 Sec->Addr =
Shdr.sh_addr;
1807 Sec->Offset =
Shdr.sh_offset;
1808 Sec->OriginalOffset =
Shdr.sh_offset;
1809 Sec->Size =
Shdr.sh_size;
1810 Sec->Link =
Shdr.sh_link;
1811 Sec->Info =
Shdr.sh_info;
1812 Sec->Align =
Shdr.sh_addralign;
1813 Sec->EntrySize =
Shdr.sh_entsize;
1814 Sec->Index =
Index++;
1815 Sec->OriginalIndex = Sec->Index;
1817 ElfFile.base() +
Shdr.sh_offset,
1825uint32_t ShstrIndex = ElfFile.getHeader().e_shstrndx;
1831 ShstrIndex = (*Sec)->sh_link;
1835 Obj.HadShdrs =
false;
1838 Obj.sections().template getSectionOfType<StringTableSection>(
1840"e_shstrndx field value " +
Twine(ShstrIndex) +
" in elf header " +
1842"e_shstrndx field value " +
Twine(ShstrIndex) +
" in elf header " +
1843" does not reference a string table");
1847 Obj.SectionNames = *Sec;
1850// If a section index table exists we'll need to initialize it before we 1851// initialize the symbol table because the symbol table might need to 1853if (Obj.SectionIndexTable)
1854if (
Error Err = Obj.SectionIndexTable->initialize(Obj.sections()))
1857// Now that all of the sections have been added we can fill out some extra 1858// details about symbol tables. We need the symbol table filled out before 1860if (Obj.SymbolTable) {
1861if (
Error Err = Obj.SymbolTable->initialize(Obj.sections()))
1863if (
Error Err = initSymbolTable(Obj.SymbolTable))
1865 }
elseif (EnsureSymtab) {
1866if (
Error Err = Obj.addNewSymbolTable())
1870// Now that all sections and symbols have been added we can add 1871// relocations that reference symbols and set the link and info fields for 1872// relocation sections. 1874if (&Sec == Obj.SymbolTable)
1876if (
Error Err = Sec.initialize(Obj.sections()))
1878if (
auto RelSec = dyn_cast<RelocationSection>(&Sec)) {
1885 Sections->begin() + RelSec->Index;
1887auto RelsOrRelas = ElfFile.crels(*
Shdr);
1889return RelsOrRelas.takeError();
1894 }
elseif (RelSec->Type ==
SHT_REL) {
1896 ElfFile.rels(*
Shdr);
1904 ElfFile.relas(*
Shdr);
1911 }
elseif (
auto GroupSec = dyn_cast<GroupSection>(&Sec)) {
1912if (
Error Err = initGroupSection(GroupSec))
1921if (
Error E = readSectionHeaders())
1923if (
Error E = findEhdrOffset())
1926// The ELFFile whose ELF headers and program headers are copied into the 1927// output file. Normally the same as ElfFile, but if we're extracting a 1928// loadable partition it will point to the partition's headers. 1930 {ElfFile.base() + EhdrOffset, ElfFile.getBufSize() - EhdrOffset}));
1936 Obj.OSABI = Ehdr.e_ident[
EI_OSABI];
1938 Obj.Type = Ehdr.e_type;
1939 Obj.Machine = Ehdr.e_machine;
1940 Obj.Version = Ehdr.e_version;
1941 Obj.Entry = Ehdr.e_entry;
1942 Obj.Flags = Ehdr.e_flags;
1944if (
Error E = readSections(EnsureSymtab))
1946return readProgramHeaders(*HeadersFile);
1960 std::vector<IHexRecord> Records;
1961bool HasSections =
false;
1964 Records.reserve(Lines.size());
1965for (
size_t LineNo = 1; LineNo <= Lines.size(); ++LineNo) {
1966StringRef Line = Lines[LineNo - 1].trim();
1972return parseError(LineNo, R.takeError());
1976 Records.push_back(*R);
1979return parseError(-1U,
"no sections");
1981return std::move(Records);
1988return Records.takeError();
1994auto Obj = std::make_unique<Object>();
1998return std::move(Err);
1999return std::move(Obj);
2003return std::move(Err);
2004return std::move(Obj);
2008return std::move(Err);
2009return std::move(Obj);
2013return std::move(Err);
2014return std::move(Obj);
2020 Elf_Ehdr &Ehdr = *
reinterpret_cast<Elf_Ehdr *
>(Buf->getBufferStart());
2021 std::fill(Ehdr.e_ident, Ehdr.e_ident + 16, 0);
2030 Ehdr.e_ident[
EI_OSABI] = Obj.OSABI;
2033 Ehdr.e_type = Obj.Type;
2034 Ehdr.e_machine = Obj.Machine;
2035 Ehdr.e_version = Obj.Version;
2036 Ehdr.e_entry = Obj.Entry;
2037// We have to use the fully-qualified name llvm::size 2038// since some compilers complain on ambiguous resolution. 2040 Ehdr.e_phoff = (Ehdr.e_phnum != 0) ? Obj.ProgramHdrSegment.Offset : 0;
2041 Ehdr.e_phentsize = (Ehdr.e_phnum != 0) ?
sizeof(Elf_Phdr) : 0;
2042 Ehdr.e_flags = Obj.Flags;
2043 Ehdr.e_ehsize =
sizeof(Elf_Ehdr);
2044if (WriteSectionHeaders && Obj.sections().size() != 0) {
2045 Ehdr.e_shentsize =
sizeof(Elf_Shdr);
2046 Ehdr.e_shoff = Obj.SHOff;
2048// If the number of sections is greater than or equal to 2049// SHN_LORESERVE (0xff00), this member has the value zero and the actual 2050// number of section header table entries is contained in the sh_size field 2051// of the section header at index 0. 2053auto Shnum = Obj.sections().size() + 1;
2057 Ehdr.e_shnum = Shnum;
2059// If the section name string table section index is greater than or equal 2060// to SHN_LORESERVE (0xff00), this member has the value SHN_XINDEX (0xffff) 2061// and the actual index of the section name string table section is 2062// contained in the sh_link field of the section header at index 0. 2067 Ehdr.e_shstrndx = Obj.SectionNames->Index;
2069 Ehdr.e_shentsize = 0;
2072 Ehdr.e_shstrndx = 0;
2077for (
auto &Seg : Obj.segments())
2082// This reference serves to write the dummy section header at the begining 2083// of the file. It is not used for anything else 2085 *
reinterpret_cast<Elf_Shdr *
>(Buf->getBufferStart() + Obj.SHOff);
2091// See writeEhdr for why we do this. 2092uint64_t Shnum = Obj.sections().size() + 1;
2094Shdr.sh_size = Shnum;
2097// See writeEhdr for why we do this. 2098if (Obj.SectionNames !=
nullptr && Obj.SectionNames->Index >=
SHN_LORESERVE)
2099Shdr.sh_link = Obj.SectionNames->Index;
2103Shdr.sh_addralign = 0;
2112// Segments are responsible for writing their contents, so only write the 2113// section data if the section is not in a segment. Note that this renders 2114// sections in segments effectively immutable. 2115if (Sec.ParentSegment ==
nullptr)
2116if (
Error Err = Sec.accept(*SecWriter))
2123for (
Segment &Seg : Obj.segments()) {
2129for (
constauto &it : Obj.getUpdatedSections()) {
2134assert(Parent &&
"This section should've been part of a segment.");
2140// Iterate over removed sections and overwrite their old data with zeroes. 2141for (
auto &Sec : Obj.removedSections()) {
2142Segment *Parent = Sec.ParentSegment;
2143if (Parent ==
nullptr || Sec.Type ==
SHT_NOBITS || Sec.Size == 0)
2147 std::memset(Buf->getBufferStart() +
Offset, 0, Sec.Size);
2151template <
class ELFT>
2154 :
Writer(Obj, Buf), WriteSectionHeaders(WSH && Obj.HadShdrs),
2155 OnlyKeepDebug(OnlyKeepDebug) {}
2158if (!Sec->hasContents())
2161"section '%s' cannot be updated because it does not have contents",
2164if (
Data.size() > Sec->Size && Sec->ParentSegment)
2166"cannot fit data of size %zu into section '%s' " 2167"with size %" PRIu64
" that is part of a segment",
2168Data.size(), Sec->Name.c_str(), Sec->Size);
2170if (!Sec->ParentSegment) {
2171 Sec = std::make_unique<OwnedDataSection>(*Sec,
Data);
2173// The segment writer will be in charge of updating these contents. 2174 Sec->Size =
Data.size();
2175 UpdatedSections[Sec.get()] =
Data;
2183 [&](
const SecPtr &Sec) {
return Sec->Name ==
Name; });
2184if (It == Sections.end())
2187return updateSectionData(*It,
Data);
2192 [&](
const SecPtr &Sec) {
return Sec.
get() == &S; });
2193assert(It != Sections.end() &&
"The section should belong to the object");
2194return updateSectionData(*It,
Data);
2200auto Iter = std::stable_partition(
2201 std::begin(Sections), std::end(Sections), [=](
const SecPtr &Sec) {
2204// TODO: A compressed relocation section may be recognized as 2205// RelocationSectionBase. We don't want such a section to be removed. 2206if (isa<CompressedSection>(Sec))
2208if (
auto RelSec = dyn_cast<RelocationSectionBase>(Sec.get())) {
2209 if (auto ToRelSec = RelSec->getSection())
2210 return !ToRemove(*ToRelSec);
2212// Remove empty group sections. 2214 auto GroupSec = cast<GroupSection>(Sec.get());
2215 return !llvm::all_of(GroupSec->members(), ToRemove);
2225// Now make sure there are no remaining references to the sections that will 2226// be removed. Sometimes it is impossible to remove a reference so we emit 2227// an error here instead. 2228 std::unordered_set<const SectionBase *> RemoveSections;
2229 RemoveSections.
reserve(std::distance(Iter, std::end(Sections)));
2230for (
auto &RemoveSec :
make_range(Iter, std::end(Sections))) {
2233 RemoveSec->onRemove();
2234 RemoveSections.insert(RemoveSec.get());
2237// For each section that remains alive, we want to remove the dead references. 2238// This either might update the content of the section (e.g. remove symbols 2239// from symbol table that belongs to removed section) or trigger an error if 2240// a live section critically depends on a section being removed somehow 2241// (e.g. the removed section is referenced by a relocation). 2242for (
auto &KeepSec :
make_range(std::begin(Sections), Iter)) {
2243if (
Error E = KeepSec->removeSectionReferences(
2244 AllowBrokenLinks, [&RemoveSections](
constSectionBase *Sec) {
2245 return RemoveSections.find(Sec) != RemoveSections.end();
2250// Transfer removed sections into the Object RemovedSections container for use 2252 std::move(Iter, Sections.end(), std::back_inserter(RemovedSections));
2253// Now finally get rid of them all together. 2254 Sections.erase(Iter, std::end(Sections));
2260auto SectionIndexLess = [](
const SecPtr &Lhs,
const SecPtr &Rhs) {
2261return Lhs->Index < Rhs->Index;
2264"Sections are expected to be sorted by Index");
2265// Set indices of new sections so that they can be later sorted into positions 2267for (
auto &
I : FromTo)
2268I.second->Index =
I.first->Index;
2270// Notify all sections about the replacement. 2271for (
auto &Sec : Sections)
2272 Sec->replaceSectionReferences(FromTo);
2275/*AllowBrokenLinks=*/false,
2284for (
const SecPtr &Sec : Sections)
2293// Reuse an existing SHT_STRTAB section if it exists. 2299// Prefer a string table that is not the section header string table, if 2300// such a table exists. 2306 StrTab = &addSection<StringTableSection>();
2309 SymTab.
Name =
".symtab";
2313 SymTab.
addSymbol(
"", 0, 0,
nullptr, 0, 0, 0, 0);
2320// Orders segments such that if x = y->ParentSegment then y comes before x. 2325// This function finds a consistent layout for a list of segments starting from 2326// an Offset. It assumes that Segments have been sorted by orderSegments and 2327// returns an Offset one past the end of the last segment. 2331// The only way a segment should move is if a section was between two 2332// segments and that section was removed. If that section isn't in a segment 2333// then it's acceptable, but not ideal, to simply move it to after the 2334// segments. So we can simply layout segments one after the other accounting 2336for (
Segment *Seg : Segments) {
2337// We assume that segments have been ordered by OriginalOffset and Index 2338// such that a parent segment will always come before a child segment in 2339// OrderedSegments. This means that the Offset of the ParentSegment should 2340// already be set and we can set our offset relative to it. 2354// This function finds a consistent layout for a list of sections. It assumes 2355// that the ->ParentSegment of each section has already been laid out. The 2356// supplied starting Offset is used for the starting offset of any section that 2357// does not have a ParentSegment. It returns either the offset given if all 2358// sections had a ParentSegment or an offset one past the last section if there 2359// was a section that didn't have a ParentSegment. 2360template <
class Range>
2362// Now the offset of every segment has been set we can assign the offsets 2363// of each section. For sections that are covered by a segment we should use 2364// the segment's original offset and the section's original offset to compute 2365// the offset from the start of the segment. Using the offset from the start 2366// of the segment we can assign a new offset to the section. For sections not 2367// covered by segments we can just bump Offset to the next valid location. 2368// While it is not necessary, layout the sections in the order based on their 2369// original offsets to resemble the input file as close as possible. 2370 std::vector<SectionBase *> OutOfSegmentSections;
2372for (
auto &Sec : Sections) {
2373 Sec.Index = Index++;
2374if (Sec.ParentSegment !=
nullptr) {
2379 OutOfSegmentSections.push_back(&Sec);
2386for (
auto *Sec : OutOfSegmentSections) {
2395// Rewrite sh_offset after some sections are changed to SHT_NOBITS and thus 2396// occupy no space in the file. 2398// The layout algorithm requires the sections to be handled in the order of 2399// their offsets in the input file, at least inside segments. 2400 std::vector<SectionBase *> Sections;
2404 Sec.Index = Index++;
2405 Sections.push_back(&Sec);
2412for (
auto *Sec : Sections) {
2413auto *FirstSec = Sec->ParentSegment && Sec->ParentSegment->Type ==
PT_LOAD 2414 ? Sec->ParentSegment->firstSection()
2417// The first section in a PT_LOAD has to have congruent offset and address 2418// modulo the alignment, which usually equals the maximum page size. 2419if (FirstSec && FirstSec == Sec)
2420 Off =
alignTo(Off, Sec->ParentSegment->Align, Sec->Addr);
2422// sh_offset is not significant for SHT_NOBITS sections, but the congruence 2423// rule must be followed if it is the first section in a PT_LOAD. Do not 2431// FirstSec being nullptr generally means that Sec does not have the 2433 Off = Sec->Align ?
alignTo(Off, Sec->Align) : Off;
2434 }
elseif (FirstSec != Sec) {
2435// The offset is relative to the first section in the PT_LOAD segment. Use 2436// sh_offset for non-SHF_ALLOC sections. 2437 Off = Sec->OriginalOffset - FirstSec->OriginalOffset + FirstSec->Offset;
2445// Rewrite p_offset and p_filesz of non-PT_PHDR segments after sh_offset values 2446// have been updated. 2450for (
Segment *Seg : Segments) {
2454// The segment offset is generally the offset of the first section. 2456// For a segment containing no section (see sectionWithinSegment), if it has 2457// a parent segment, copy the parent segment's offset field. This works for 2458// empty PT_TLS. If no parent segment, use 0: the segment is not useful for 2462 FirstSec ? FirstSec->
Offset 2471// If the segment includes EHDR and program headers, don't make it smaller 2476 FileSize = std::max(FileSize, HdrEnd -
Offset);
2481 MaxOffset = std::max(MaxOffset,
Offset + FileSize);
2487Segment &ElfHdr = Obj.ElfHdrSegment;
2497// We need a temporary list of segments that has a special order to it 2498// so that we know that anytime ->ParentSegment is set that segment has 2499// already had its offset properly set. 2500 std::vector<Segment *> OrderedSegments;
2502 OrderedSegments.push_back(&
Segment);
2503 OrderedSegments.push_back(&Obj.ElfHdrSegment);
2504 OrderedSegments.push_back(&Obj.ProgramHdrSegment);
2509// For --only-keep-debug, the sections that did not preserve contents were 2510// changed to SHT_NOBITS. We now rewrite sh_offset fields of sections, and 2511// then rewrite p_offset/p_filesz of program headers. 2513sizeof(Elf_Ehdr) +
llvm::size(Obj.segments()) *
sizeof(Elf_Phdr);
2518// Offset is used as the start offset of the first segment to be laid out. 2519// Since the ELF Header (ElfHdrSegment) must be at the start of the file, 2520// we start at offset 0. 2524// If we need to write the section header table out then we need to align the 2525// Offset so that SHOffset is valid. 2526if (WriteSectionHeaders)
2532// We already have the section header offset so we can calculate the total 2533// size by just adding up the size of each section header. 2534if (!WriteSectionHeaders)
2536size_t ShdrCount = Obj.sections().size() + 1;
// Includes null shdr. 2537return Obj.SHOff + ShdrCount *
sizeof(Elf_Shdr);
2541// Segment data must be written first, so that the ELF header and program 2542// header tables can overwrite it, if covered by a segment. 2546if (
Error E = writeSectionData())
2548if (WriteSectionHeaders)
2551// TODO: Implement direct writing to the output stream (without intermediate 2552// memory buffer Buf). 2553 Out.write(Buf->getBufferStart(), Buf->getBufferSize());
2558// We can remove an empty symbol table from non-relocatable objects. 2559// Relocatable objects typically have relocation sections whose 2560// sh_link field points to .symtab, so we can't remove .symtab 2561// even if it is empty. 2566// .strtab can be used for section names. In such a case we shouldn't 2577// It could happen that SectionNames has been removed and yet the user wants 2578// a section header table output. We need to throw an error if a user tries 2580if (Obj.SectionNames ==
nullptr && WriteSectionHeaders)
2582"cannot write section header table because " 2583"section header string table was removed");
2588// If the .symtab indices have not been changed, restore the sh_link to 2589// .symtab for sections that were linked to .symtab. 2590if (Obj.SymbolTable && !Obj.SymbolTable->indicesChanged())
2592 Sec.restoreSymTabLink(*Obj.SymbolTable);
2594// We need to assign indexes before we perform layout because we need to know 2595// if we need large indexes or not. We can assign indexes first and check as 2596// we go to see if we will actully need large indexes. 2597bool NeedsLargeIndexes =
false;
2600// Sections doesn't include the null section header, so account for this 2601// when skipping the first N sections. 2605// TODO: handle case where only one section needs the large index table but 2606// only needs it because the large index table hasn't been removed yet. 2609if (NeedsLargeIndexes) {
2610// This means we definitely need to have a section index table but if we 2611// already have one then we should use it instead of making a new one. 2612if (Obj.SymbolTable !=
nullptr && Obj.SectionIndexTable ==
nullptr) {
2613// Addition of a section to the end does not invalidate the indexes of 2614// other sections and assigns the correct index to the new section. 2616 Obj.SymbolTable->setShndxTable(&Shndx);
2620// Since we don't need SectionIndexTable we should remove it and all 2622if (Obj.SectionIndexTable !=
nullptr) {
2623// We do not support sections referring to the section index table. 2624if (
Error E = Obj.removeSections(
false/*AllowBrokenLinks*/,
2626 return &Sec == Obj.SectionIndexTable;
2632// Make sure we add the names of all the sections. Importantly this must be 2633// done after we decide to add or remove SectionIndexes. 2634if (Obj.SectionNames !=
nullptr)
2636 Obj.SectionNames->addString(Sec.Name);
2640// Before we can prepare for layout the indexes need to be finalized. 2641// Also, the output arch may not be the same as the input arch, so fix up 2642// size-related fields before doing layout calculations. 2644auto SecSizer = std::make_unique<ELFSectionSizer<ELFT>>();
2646 Sec.Index = Index++;
2647if (
Error Err = Sec.accept(*SecSizer))
2651// The symbol table does not update all other sections on update. For 2652// instance, symbol names are not added as new symbols are added. This means 2653// that some sections, like .strtab, don't yet have their final size. 2654if (Obj.SymbolTable !=
nullptr)
2655 Obj.SymbolTable->prepareForLayout();
2657// Now that all strings are added we want to finalize string table builders, 2658// because that affects section sizes which in turn affects section offsets. 2660if (
auto StrTab = dyn_cast<StringTableSection>(&Sec))
2661 StrTab->prepareForLayout();
2665// layoutSections could have modified section indexes, so we need 2666// to fill the index table after assignOffsets. 2667if (Obj.SymbolTable !=
nullptr)
2668 Obj.SymbolTable->fillShndxTable();
2670// Finally now that all offsets and indexes have been set we can finalize any 2674 Sec.HeaderOffset =
Offset;
2675Offset +=
sizeof(Elf_Shdr);
2676if (WriteSectionHeaders)
2677 Sec.NameIndex = Obj.SectionNames->findIndex(Sec.Name);
2681size_t TotalSize = totalSize();
2685"failed to allocate memory buffer of " +
2688 SecWriter = std::make_unique<ELFSectionWriter<ELFT>>(*Buf);
2699if (SectionsToWrite.
empty())
2704returnLHS->Offset <
RHS->Offset;
2709for (
size_t i = 0; i != SectionsToWrite.
size(); ++i) {
2716 ? SectionsToWrite[i + 1]->
Offset 2717 :
Buf->getBufferSize();
2718assert(PadOffset <= Buf->getBufferSize());
2721Buf->getBufferStart() + PadOffset, GapFill);
2724// TODO: Implement direct writing to the output stream (without intermediate 2725// memory buffer Buf). 2731// Compute the section LMA based on its sh_offset and the containing segment's 2732// p_offset and p_paddr. Also compute the minimum LMA of all non-empty 2733// sections as MinAddr. In the output, the contents between address 0 and 2734// MinAddr will be skipped. 2737if (Sec.ParentSegment !=
nullptr)
2739 Sec.Offset - Sec.ParentSegment->Offset + Sec.ParentSegment->PAddr;
2741 MinAddr = std::min(MinAddr, Sec.Addr);
2744// Now that every section has been laid out we just need to compute the total 2745// file size. This might not be the same as the offset returned by 2746// layoutSections, because we want to truncate the last segment to the end of 2747// its last non-empty section, to match GNU objcopy's behaviour. 2748 TotalSize = PadTo > MinAddr ? PadTo - MinAddr : 0;
2751 Sec.Offset = Sec.Addr - MinAddr;
2752 TotalSize = std::max(TotalSize, Sec.Offset + Sec.Size);
2758"failed to allocate memory buffer of " +
2760 SecWriter = std::make_unique<BinarySectionWriter>(*
Buf);
2769"section '%s' address range [0x%llx, 0x%llx] is not 32 bit",
2775// We can't write 64-bit addresses. 2778"entry point address 0x%llx overflows 32 bits",
2793 std::unique_ptr<WritableMemoryBuffer> EmptyBuffer =
2797"failed to allocate memory buffer of 0 bytes");
2807"failed to allocate memory buffer of 0x" +
2815// We don't write entry point record if entry is zero. 2830return HexData.
size();
2836return HexData.
size();
2843if (
Error Err = Sec->accept(LengthCalc))
2844return std::move(Err);
2846// We need space to write section records + StartAddress record 2847// (if start adress is not zero) + EndOfFile record. 2848return LengthCalc.getBufferOffset() +
2861// Write entry point address. 2862Offset += writeEntryPointRecord(
2865Offset += writeEndOfFileRecord(
2869// TODO: Implement direct writing to the output stream (without intermediate 2870// memory buffer Buf). 2876// Check that the sizer has already done its work. 2878"Expected section size to have been finalized");
2879// We don't need to write anything here because the real writer has already 2905// The ELF header could contain an entry point outside of the sections we have 2906// seen that does not fit the current record Type. 2923while (!
Data.empty()) {
2924uint64_t DataSize = std::min<uint64_t>(
Data.size(), ChunkSize);
2934"Section size does not match the section's string table builder size");
2935 std::vector<uint8_t>
Data(Sec.
Size);
2943auto *Iter = Line.begin();
2946// Write 1 byte (2 hex characters) record count. 2948// Write the address field with length depending on record type. 2950// Write data byte by byte. 2953// Write the 1 byte checksum. 2957assert(Iter == Line.end());
2963 Sum += (
Address >> 24) & 0xFF;
2964 Sum += (
Address >> 16) & 0xFF;
2969return 0xFF - (Sum & 0xFF);
2973// Type, Count, Checksum, and CRLF are two characters each. 3007// Header is a record with Type S0, Address 0, and Data that is a 3008// vendor-specific text comment. For the comment we will use the output file 3009// name truncated to 40 characters to match the behavior of GNU objcopy. 3012reinterpret_cast<constuint8_t *
>(HeaderContents.
data()),
3013 HeaderContents.
size());
3017size_t SRECWriter::writeHeader(
uint8_t *Buf) {
3025"Invalid record type for terminator");
3036if (
Error Err = Sec->accept(SizeCalc))
3037return std::move(Err);
3040// We need to add the size of the Header and Terminator records. 3042uint8_t TerminatorType = 10 - SizeCalc.getType();
3044return Header.getSize() + SizeCalc.getBufferOffset() +
Terminator.getSize();
3049 writeHeader(
reinterpret_cast<uint8_t *
>(
Buf->getBufferStart()));
3058// An S1 record terminates with an S9 record, S2 with S8, and S3 with S7. 3060Offset += writeTerminator(
3082}
// end namespace elf 3083}
// end namespace objcopy 3084}
// end namespace llvm ReachingDefAnalysis InstSet & ToRemove
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
COFF::MachineTypes Machine
Analysis containing CSE Info
static bool segmentOverlapsSegment(const Segment &Child, const Segment &Parent)
static void setAddend(Elf_Rel_Impl< ELFT, false > &, uint64_t)
static Error checkChars(StringRef Line)
static void orderSegments(std::vector< Segment * > &Segments)
static uint64_t layoutSegments(std::vector< Segment * > &Segments, uint64_t Offset)
static bool compareSegmentsByOffset(const Segment *A, const Segment *B)
static uint64_t layoutSections(Range Sections, uint64_t Offset)
static uint64_t layoutSectionsForOnlyKeepDebug(Object &Obj, uint64_t Off)
static bool isValidReservedSectionIndex(uint16_t Index, uint16_t Machine)
static uint64_t layoutSegmentsForOnlyKeepDebug(std::vector< Segment * > &Segments, uint64_t HdrEnd)
static void getAddend(uint64_t &, const Elf_Rel_Impl< ELFT, false > &)
static void writeRel(const RelRange &Relocations, T *Buf, bool IsMips64EL)
static bool addressOverflows32bit(uint64_t Addr)
static T checkedGetHex(StringRef S)
static uint64_t sectionPhysicalAddr(const SectionBase *Sec)
static Iterator toHexStr(T X, Iterator It, size_t Len)
static Error checkRecord(const IHexRecord &R)
static Error initRelocations(RelocationSection *Relocs, T RelRange)
static Error removeUnneededSections(Object &Obj)
static bool sectionWithinSegment(const SectionBase &Sec, const Segment &Seg)
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
ConstantRange Range(APInt(BitWidth, Low), APInt(BitWidth, High))
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This file contains some templates that are useful if you are working with the STL at all.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
size_t size() const
size - Get the array size.
bool empty() const
empty - Check if the array is empty.
ArrayRef< T > slice(size_t N, size_t M) const
slice(n, m) - Chop off the first N elements of the array, and keep M elements in the array.
ValueT lookup(const_arg_type_t< KeyT > Val) const
lookup - Return the entry for the specified key, or a default constructed value if no such entry exis...
size_type count(const_arg_type_t< KeyT > Val) const
Return 1 if the specified key is in the map, 0 otherwise.
Lightweight error class with error context and mandatory checking.
static ErrorSuccess success()
Create a success value.
Tagged union holding either a T or a Error.
Error takeError()
Take ownership of the stored error.
reference get()
Returns a reference to the stored T value.
virtual StringRef getBufferIdentifier() const
Return an identifier for this buffer, typically the filename it was read from.
size_t getBufferSize() const
StringRef getBuffer() const
const char * getBufferStart() const
void push_back(const T &Elt)
pointer data()
Return a pointer to the vector's buffer, even if empty().
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
std::pair< StringRef, StringRef > split(char Separator) const
Split into two substrings around the first occurrence of a separator character.
bool getAsInteger(unsigned Radix, T &Result) const
Parse the current string as an integer of the specified radix.
std::string str() const
str - Get the contents as an std::string.
constexpr bool empty() const
empty - Check if the string is empty.
StringRef drop_front(size_t N=1) const
Return a StringRef equal to 'this' but with the first N elements dropped.
StringRef slice(size_t Start, size_t End) const
Return a reference to the substring from [Start, End).
constexpr size_t size() const
size - Get the string size.
constexpr const char * data() const
data - Get a pointer to the start of the string (which may not be null terminated).
StringRef take_front(size_t N=1) const
Return a StringRef equal to 'this' but with only the first N elements remaining.
size_t getOffset(CachedHashStringRef S) const
Get the offest of a string in the string table.
void write(raw_ostream &OS) const
size_t add(CachedHashStringRef S)
Add a string to the builder.
void finalize()
Analyze the strings and build the final table.
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
static Twine utohexstr(const uint64_t &Val)
The instances of the Type class are immutable: once they are created, they are never changed.
LLVM Value Representation.
This class is an extension of MemoryBuffer, which allows copy-on-write access to the underlying conte...
static std::unique_ptr< WritableMemoryBuffer > getNewMemBuffer(size_t Size, const Twine &BufferName="")
Allocate a new zero-initialized MemoryBuffer of the specified size.
An efficient, type-erasing, non-owning reference to a callable.
Error checkSection(const SectionBase &S) const
Error finalize() override
std::vector< const SectionBase * > Sections
virtual Expected< size_t > getTotalSize(WritableMemoryBuffer &EmptyBuffer) const =0
StringTableSection * addStrTab()
SymbolTableSection * addSymTab(StringTableSection *StrTab)
std::unique_ptr< Object > Obj
Expected< std::unique_ptr< Object > > build()
Expected< std::unique_ptr< Object > > create(bool EnsureSymtab) const override
Error visit(const SymbolTableSection &Sec) override
Error finalize() override
Error accept(SectionVisitor &Visitor) const override
CompressedSection(const SectionBase &Sec, DebugCompressionType CompressionType, bool Is64Bits)
Error accept(SectionVisitor &Visitor) const override
Error accept(SectionVisitor &) const override
Error removeSectionReferences(bool AllowBrokenLinks, function_ref< bool(const SectionBase *)> ToRemove) override
ELFBuilder(const ELFObjectFile< ELFT > &ElfObj, Object &Obj, std::optional< StringRef > ExtractPartition)
Error build(bool EnsureSymtab)
Expected< std::unique_ptr< Object > > create(bool EnsureSymtab) const override
Error visit(Section &Sec) override
Error visit(const SymbolTableSection &Sec) override
Error finalize() override
ELFWriter(Object &Obj, raw_ostream &Out, bool WSH, bool OnlyKeepDebug)
Error accept(SectionVisitor &Visitor) const override
GnuDebugLinkSection(StringRef File, uint32_t PrecomputedCRC)
void setSymTab(const SymbolTableSection *SymTabSec)
void setSymbol(Symbol *S)
void replaceSectionReferences(const DenseMap< SectionBase *, SectionBase * > &FromTo) override
Error accept(SectionVisitor &) const override
void markSymbols() override
ArrayRef< uint8_t > Contents
void addMember(SectionBase *Sec)
Error removeSectionReferences(bool AllowBrokenLinks, function_ref< bool(const SectionBase *)> ToRemove) override
void setFlagWord(ELF::Elf32_Word W)
Error removeSymbols(function_ref< bool(const Symbol &)> ToRemove) override
Expected< std::unique_ptr< Object > > build()
Expected< std::unique_ptr< Object > > create(bool EnsureSymtab) const override
void writeSection(const SectionBase *Sec, ArrayRef< uint8_t > Data)
Error visit(const Section &Sec) final
virtual void writeData(uint8_t Type, uint16_t Addr, ArrayRef< uint8_t > Data)
void writeData(uint8_t Type, uint16_t Addr, ArrayRef< uint8_t > Data) override
Error visit(const StringTableSection &Sec) override
virtual Error visit(Section &Sec)=0
SectionTableRef sections() const
StringTableSection * SectionNames
bool isRelocatable() const
iterator_range< filter_iterator< pointee_iterator< std::vector< SecPtr >::const_iterator >, decltype(§ionIsAlloc)> > allocSections() const
Error updateSection(StringRef Name, ArrayRef< uint8_t > Data)
SectionIndexSection * SectionIndexTable
Error removeSymbols(function_ref< bool(const Symbol &)> ToRemove)
Error removeSections(bool AllowBrokenLinks, std::function< bool(const SectionBase &)> ToRemove)
SymbolTableSection * SymbolTable
Error addNewSymbolTable()
Error replaceSections(const DenseMap< SectionBase *, SectionBase * > &FromTo)
void appendHexData(StringRef HexData)
Error accept(SectionVisitor &Sec) const override
Error initialize(SectionTableRef SecTable) override
SymbolTableSection * Symbols
SectionBase * SecToApplyRel
StringRef getNamePrefix() const
void markSymbols() override
const Object & getObject() const
void addRelocation(const Relocation &Rel)
Error accept(SectionVisitor &Visitor) const override
Error removeSymbols(function_ref< bool(const Symbol &)> ToRemove) override
void replaceSectionReferences(const DenseMap< SectionBase *, SectionBase * > &FromTo) override
Error removeSectionReferences(bool AllowBrokenLinks, function_ref< bool(const SectionBase *)> ToRemove) override
std::vector< SRecord > Records
virtual void writeRecord(SRecord &Record, uint64_t Off)=0
void writeSection(const SectionBase &S, ArrayRef< uint8_t > Data)
Error visit(const Section &S) override
void writeRecords(uint32_t Entry)
Error visit(const StringTableSection &Sec) override
void writeRecord(SRecord &Record, uint64_t Off) override
virtual void markSymbols()
ArrayRef< uint8_t > OriginalData
virtual Error initialize(SectionTableRef SecTable)
virtual Error removeSectionReferences(bool AllowBrokenLinks, function_ref< bool(const SectionBase *)> ToRemove)
virtual void replaceSectionReferences(const DenseMap< SectionBase *, SectionBase * > &)
virtual Error removeSymbols(function_ref< bool(const Symbol &)> ToRemove)
virtual Error accept(SectionVisitor &Visitor) const =0
void addIndex(uint32_t Index)
void setSymTab(SymbolTableSection *SymTab)
Error accept(SectionVisitor &Visitor) const override
void reserve(size_t NumSymbols)
Error initialize(SectionTableRef SecTable) override
Expected< T * > getSectionOfType(uint32_t Index, Twine IndexErrMsg, Twine TypeErrMsg)
Expected< SectionBase * > getSection(uint32_t Index, Twine ErrMsg)
virtual Error visit(const Section &Sec)=0
Error visit(const Section &Sec) override
WritableMemoryBuffer & Out
Error removeSectionReferences(bool AllowBrokenLinks, function_ref< bool(const SectionBase *)> ToRemove) override
Error initialize(SectionTableRef SecTable) override
void restoreSymTabLink(SymbolTableSection &SymTab) override
Error accept(SectionVisitor &Visitor) const override
void addSection(const SectionBase *Sec)
void removeSection(const SectionBase *Sec)
const SectionBase * firstSection() const
ArrayRef< uint8_t > getContents() const
std::set< const SectionBase *, SectionCompare > Sections
void addString(StringRef Name)
uint32_t findIndex(StringRef Name) const
Error accept(SectionVisitor &Visitor) const override
const SectionBase * getStrTab() const
Error removeSectionReferences(bool AllowBrokenLinks, function_ref< bool(const SectionBase *)> ToRemove) override
const SectionIndexSection * getShndxTable() const
std::vector< std::unique_ptr< Symbol > > Symbols
SectionIndexSection * SectionIndexTable
Error accept(SectionVisitor &Visitor) const override
void addSymbol(Twine Name, uint8_t Bind, uint8_t Type, SectionBase *DefinedIn, uint64_t Value, uint8_t Visibility, uint16_t Shndx, uint64_t SymbolSize)
void updateSymbols(function_ref< void(Symbol &)> Callable)
Expected< const Symbol * > getSymbolByIndex(uint32_t Index) const
Error removeSymbols(function_ref< bool(const Symbol &)> ToRemove) override
Error initialize(SectionTableRef SecTable) override
void replaceSectionReferences(const DenseMap< SectionBase *, SectionBase * > &FromTo) override
std::unique_ptr< Symbol > SymPtr
void setShndxTable(SectionIndexSection *ShndxTable)
StringTableSection * SymbolNames
std::unique_ptr< WritableMemoryBuffer > Buf
const Elf_Ehdr & getHeader() const
static Expected< ELFFile > create(StringRef Object)
Expected< Elf_Phdr_Range > program_headers() const
Iterate over program header table.
size_t getBufSize() const
const uint8_t * base() const
Represents a GOFF physical record.
This class implements an extremely fast bulk output stream that can only output to a stream.
raw_ostream & write(unsigned char C)
A raw_ostream that writes to an SmallVector or SmallString.
This provides a very simple, boring adaptor for a begin and end iterator into a range type.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ C
The default llvm calling convention, compatible with C.
void encodeCrel(raw_ostream &OS, RelocsTy Relocs, F ToCrel)
const char * getReasonIfUnsupported(Format F)
Error decompress(DebugCompressionType T, ArrayRef< uint8_t > Input, uint8_t *Output, size_t UncompressedSize)
Format formatFor(DebugCompressionType Type)
void compress(Params P, ArrayRef< uint8_t > Input, SmallVectorImpl< uint8_t > &Output)
support::ulittle32_t Word
void write(void *memory, value_type value, endianness endian)
Write a value to memory with a particular endianness.
StringRef filename(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)
Get filename.
This is an optimization pass for GlobalISel generic memory operations.
auto drop_begin(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the first N elements excluded.
void stable_sort(R &&Range)
auto size(R &&Range, std::enable_if_t< std::is_base_of< std::random_access_iterator_tag, typename std::iterator_traits< decltype(Range.begin())>::iterator_category >::value, void > *=nullptr)
Get the size of a range.
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
Error createStringError(std::error_code EC, char const *Fmt, const Ts &... Vals)
Create formatted StringError object.
@ operation_not_permitted
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
void sort(IteratorTy Start, IteratorTy End)
bool is_sorted(R &&Range, Compare C)
Wrapper function around std::is_sorted to check if elements in a range R are sorted with respect to a...
@ Mod
The access may modify the value stored in memory.
uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.
OutputIt copy(R &&Range, OutputIt Out)
auto find_if(R &&Range, UnaryPredicate P)
Provide wrappers to std::find_if which take ranges instead of having to pass begin/end explicitly.
void erase_if(Container &C, UnaryPredicate P)
Provide a container algorithm similar to C++ Library Fundamentals v2's erase_if which is equivalent t...
const char * toString(DWARFSectionKind Kind)
This struct is a compact representation of a valid (non-zero power of two) alignment.
static IHexLineData getLine(uint8_t Type, uint16_t Addr, ArrayRef< uint8_t > Data)
static uint8_t getChecksum(StringRef S)
static Expected< IHexRecord > parse(StringRef Line)
static size_t getLength(size_t DataSize)
static size_t getLineLength(size_t DataSize)
uint8_t getAddressSize() const
static SRecord getHeader(StringRef FileName)
uint8_t getChecksum() const
SRecLineData toString() const
static uint8_t getType(uint32_t Address)
uint16_t getShndx() const
SymbolShndxType ShndxType