diff options
| author | Nick Kledzik <kledzik@apple.com> | 2014-11-18 00:30:29 +0000 |
|---|---|---|
| committer | Nick Kledzik <kledzik@apple.com> | 2014-11-18 00:30:29 +0000 |
| commit | b072c3673a39dfd6c954e2cbd4344e93478451de (patch) | |
| tree | d38f14189654aa9ca17a30063cd9583fa3d27ca3 | |
| parent | 63adb08c2ca3b8a4c119643e225fe45c856571b9 (diff) | |
| download | bcm5719-llvm-b072c3673a39dfd6c954e2cbd4344e93478451de.tar.gz bcm5719-llvm-b072c3673a39dfd6c954e2cbd4344e93478451de.zip | |
[mach-o] zero-fill sections have no file offset
In mach-o, sections of type S_ZEROFILL are special cased and to always have
their section.offset field be zero.
llvm-svn: 222202
| -rw-r--r-- | lld/lib/ReaderWriter/MachO/MachONormalizedFileBinaryWriter.cpp | 26 | ||||
| -rw-r--r-- | lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp | 7 | ||||
| -rw-r--r-- | lld/test/mach-o/exe-offsets.yaml | 4 |
3 files changed, 24 insertions, 13 deletions
diff --git a/lld/lib/ReaderWriter/MachO/MachONormalizedFileBinaryWriter.cpp b/lld/lib/ReaderWriter/MachO/MachONormalizedFileBinaryWriter.cpp index 102b185df52..3bc341ffa3a 100644 --- a/lld/lib/ReaderWriter/MachO/MachONormalizedFileBinaryWriter.cpp +++ b/lld/lib/ReaderWriter/MachO/MachONormalizedFileBinaryWriter.cpp @@ -284,15 +284,21 @@ MachOFileLayout::MachOFileLayout(const NormalizedFile &file) _endOfLoadCommands += sizeof(linkedit_data_command); _countOfLoadCommands++; } - // Accumulate size of each section. + // Assign file offsets to each section. _startOfSectionsContent = _endOfLoadCommands; - _endOfSectionsContent = _startOfSectionsContent; unsigned relocCount = 0; + uint64_t offset = _startOfSectionsContent; for (const Section § : file.sections) { - _sectInfo[§].fileOffset = _endOfSectionsContent; - _endOfSectionsContent += sect.content.size(); + if (sect.type != llvm::MachO::S_ZEROFILL) { + offset = llvm::RoundUpToAlignment(offset, 1 << sect.alignment); + _sectInfo[§].fileOffset = offset; + offset += sect.content.size(); + } else { + _sectInfo[§].fileOffset = 0; + } relocCount += sect.relocations.size(); } + _endOfSectionsContent = offset; computeSymbolTableSizes(); computeDataInCodeSize(); @@ -580,7 +586,8 @@ std::error_code MachOFileLayout::writeSingleSegmentLoadCommand(uint8_t *&lc) { uint8_t *next = lc + seg->cmdsize; memset(seg->segname, 0, 16); seg->vmaddr = 0; - seg->vmsize = _endOfSectionsContent - _endOfLoadCommands; + seg->vmsize = _file.sections.back().address + + _file.sections.back().content.size(); seg->fileoff = _endOfLoadCommands; seg->filesize = seg->vmsize; seg->maxprot = VM_PROT_READ|VM_PROT_WRITE|VM_PROT_EXECUTE; @@ -592,14 +599,13 @@ std::error_code MachOFileLayout::writeSingleSegmentLoadCommand(uint8_t *&lc) { typename T::section *sout = reinterpret_cast<typename T::section*> (lc+sizeof(typename T::command)); uint32_t relOffset = _startOfRelocations; - uint32_t contentOffset = _startOfSectionsContent; uint32_t indirectSymRunningIndex = 0; for (const Section &sin : _file.sections) { setString16(sin.sectionName, sout->sectname); setString16(sin.segmentName, sout->segname); sout->addr = sin.address; sout->size = sin.content.size(); - sout->offset = contentOffset; + sout->offset = _sectInfo[&sin].fileOffset; sout->align = sin.alignment; sout->reloff = sin.relocations.empty() ? 0 : relOffset; sout->nreloc = sin.relocations.size(); @@ -607,7 +613,6 @@ std::error_code MachOFileLayout::writeSingleSegmentLoadCommand(uint8_t *&lc) { sout->reserved1 = indirectSymbolIndex(sin, indirectSymRunningIndex); sout->reserved2 = indirectSymbolElementSize(sin); relOffset += sin.relocations.size() * sizeof(any_relocation_info); - contentOffset += sin.content.size(); if (_swap) swapStruct(*sout); ++sout; @@ -645,7 +650,10 @@ std::error_code MachOFileLayout::writeSegmentLoadCommands(uint8_t *&lc) { setString16(section->segmentName, sect->segname); sect->addr = section->address; sect->size = section->content.size(); - sect->offset = section->address - seg.address + segInfo.fileOffset; + if (section->type == llvm::MachO::S_ZEROFILL) + sect->offset = 0; + else + sect->offset = section->address - seg.address + segInfo.fileOffset; sect->align = section->alignment; sect->reloff = 0; sect->nreloc = 0; diff --git a/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp b/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp index 780c9c02fc8..a668dadb129 100644 --- a/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp +++ b/lld/lib/ReaderWriter/MachO/MachONormalizedFileFromAtoms.cpp @@ -573,11 +573,14 @@ void Util::copySectionContent(NormalizedFile &file) { }; for (SectionInfo *si : _sectionInfos) { - if (si->type == llvm::MachO::S_ZEROFILL) + Section *normSect = &file.sections[si->normalizedSectionIndex]; + if (si->type == llvm::MachO::S_ZEROFILL) { + const uint8_t *empty = nullptr; + normSect->content = llvm::makeArrayRef(empty, si->size); continue; + } // Copy content from atoms to content buffer for section. uint8_t *sectionContent = file.ownedAllocations.Allocate<uint8_t>(si->size); - Section *normSect = &file.sections[si->normalizedSectionIndex]; normSect->content = llvm::makeArrayRef(sectionContent, si->size); for (AtomInfo &ai : si->atomsAndOffsets) { uint8_t *atomContent = reinterpret_cast<uint8_t*> diff --git a/lld/test/mach-o/exe-offsets.yaml b/lld/test/mach-o/exe-offsets.yaml index 4ab4faba308..a751507432e 100644 --- a/lld/test/mach-o/exe-offsets.yaml +++ b/lld/test/mach-o/exe-offsets.yaml @@ -41,5 +41,5 @@ defined-atoms: # CHECK-LABEL: Section { # CHECK: Name: __bss # CHECK: Segment: __DATA -# CHECK: Size: 0x0 -# CHECK: Offset: 4101 +# CHECK: Size: 0x2064 +# CHECK: Offset: 0 |

