summaryrefslogtreecommitdiffstats
path: root/llvm/tools/llvm-objcopy/ELF/Object.cpp
diff options
context:
space:
mode:
authorJames Henderson <jh7370@my.bristol.ac.uk>2019-04-02 14:11:13 +0000
committerJames Henderson <jh7370@my.bristol.ac.uk>2019-04-02 14:11:13 +0000
commit38cb238f752cefe5fde8bf6cb73dacc3fec8f89d (patch)
tree44472d3158aeffed95ebcef7854b3c1ef93960ed /llvm/tools/llvm-objcopy/ELF/Object.cpp
parent68ad5c34e076475cf5691ead29c1ae6515272b75 (diff)
downloadbcm5719-llvm-38cb238f752cefe5fde8bf6cb73dacc3fec8f89d.tar.gz
bcm5719-llvm-38cb238f752cefe5fde8bf6cb73dacc3fec8f89d.zip
[llvm-objcopy]Allow llvm-objcopy to be used on an ELF file with no section headers
This patch fixes https://bugs.llvm.org/show_bug.cgi?id=41293 and https://bugs.llvm.org/show_bug.cgi?id=41045. llvm-objcopy assumed that it could always read a section header string table. This isn't the case when the sections were previously all stripped, and the e_shstrndx field was set to 0. This patch fixes this. It also fixes a double space in an error message relating to this issue, and prevents llvm-objcopy from adding extra space for non-existent section headers, meaning that --strip-sections on the output of a previous --strip-sections run produces identical output, simplifying the test. Reviewed by: rupprecht, grimar Differential Revision: https://reviews.llvm.org/D59989 llvm-svn: 357475
Diffstat (limited to 'llvm/tools/llvm-objcopy/ELF/Object.cpp')
-rw-r--r--llvm/tools/llvm-objcopy/ELF/Object.cpp28
1 files changed, 18 insertions, 10 deletions
diff --git a/llvm/tools/llvm-objcopy/ELF/Object.cpp b/llvm/tools/llvm-objcopy/ELF/Object.cpp
index 321adf6fff0..de51851ecfe 100644
--- a/llvm/tools/llvm-objcopy/ELF/Object.cpp
+++ b/llvm/tools/llvm-objcopy/ELF/Object.cpp
@@ -1212,13 +1212,16 @@ template <class ELFT> void ELFBuilder<ELFT>::build() {
if (ShstrIndex == SHN_XINDEX)
ShstrIndex = unwrapOrError(ElfFile.getSection(0))->sh_link;
- Obj.SectionNames =
- Obj.sections().template getSectionOfType<StringTableSection>(
- ShstrIndex,
- "e_shstrndx field value " + Twine(Ehdr.e_shstrndx) +
- " in elf header " + " is invalid",
- "e_shstrndx field value " + Twine(Ehdr.e_shstrndx) +
- " in elf header " + " is not a string table");
+ if (ShstrIndex == SHN_UNDEF)
+ Obj.HadShdrs = false;
+ else
+ Obj.SectionNames =
+ Obj.sections().template getSectionOfType<StringTableSection>(
+ ShstrIndex,
+ "e_shstrndx field value " + Twine(Ehdr.e_shstrndx) +
+ " in elf header is invalid",
+ "e_shstrndx field value " + Twine(Ehdr.e_shstrndx) +
+ " in elf header is not a string table");
}
Writer::~Writer() {}
@@ -1372,6 +1375,10 @@ template <class ELFT> void ELFWriter<ELFT>::writeSegmentData() {
}
}
+template <class ELFT>
+ELFWriter<ELFT>::ELFWriter(Object &Obj, Buffer &Buf, bool WSH)
+ : Writer(Obj, Buf), WriteSectionHeaders(WSH && Obj.HadShdrs) {}
+
Error Object::removeSections(
std::function<bool(const SectionBase &)> ToRemove) {
@@ -1558,9 +1565,10 @@ template <class ELFT> void ELFWriter<ELFT>::assignOffsets() {
template <class ELFT> size_t ELFWriter<ELFT>::totalSize() const {
// We already have the section header offset so we can calculate the total
// size by just adding up the size of each section header.
- auto NullSectionSize = WriteSectionHeaders ? sizeof(Elf_Shdr) : 0;
- return Obj.SHOffset + Obj.sections().size() * sizeof(Elf_Shdr) +
- NullSectionSize;
+ if (!WriteSectionHeaders)
+ return Obj.SHOffset;
+ size_t ShdrCount = Obj.sections().size() + 1; // Includes null shdr.
+ return Obj.SHOffset + ShdrCount * sizeof(Elf_Shdr);
}
template <class ELFT> Error ELFWriter<ELFT>::write() {
OpenPOWER on IntegriCloud