From f5345a3f4c7d19649d930c7da26d5274ce726b1f Mon Sep 17 00:00:00 2001 From: George Rimar Date: Wed, 1 May 2019 09:45:55 +0000 Subject: [PATCH] [yaml2obj] - Report when unknown section is referenced from program header declaration block. Previously we did not report this. Also this removes multiple lookups in the map what cleanups the code. Differential revision: https://reviews.llvm.org/D61322 llvm-svn: 359663 --- .../tools/llvm-objcopy/ELF/no-build-id.test | 2 +- llvm/test/tools/yaml2obj/program-header.yaml | 19 ++++++- llvm/tools/yaml2obj/yaml2elf.cpp | 52 +++++++++---------- 3 files changed, 42 insertions(+), 31 deletions(-) diff --git a/llvm/test/tools/llvm-objcopy/ELF/no-build-id.test b/llvm/test/tools/llvm-objcopy/ELF/no-build-id.test index d75f3be17808..e555b102bbc6 100644 --- a/llvm/test/tools/llvm-objcopy/ELF/no-build-id.test +++ b/llvm/test/tools/llvm-objcopy/ELF/no-build-id.test @@ -18,4 +18,4 @@ ProgramHeaders: - Type: PT_NOTE Flags: [ PF_R ] Sections: - - Section: .note.gnu.foo + - Section: .note.foo diff --git a/llvm/test/tools/yaml2obj/program-header.yaml b/llvm/test/tools/yaml2obj/program-header.yaml index 045ea6deee85..b5fac89cdc0f 100644 --- a/llvm/test/tools/yaml2obj/program-header.yaml +++ b/llvm/test/tools/yaml2obj/program-header.yaml @@ -1,7 +1,7 @@ -# RUN: yaml2obj %s -o %t +# RUN: yaml2obj --docnum=1 %s -o %t # RUN: llvm-readobj -l %t | FileCheck %s -!ELF +--- !ELF FileHeader: Class: ELFCLASS64 Data: ELFDATA2LSB @@ -65,3 +65,18 @@ ProgramHeaders: #CHECK-NEXT: Alignment: 4096 #CHECK-NEXT: } #CHECK-NEXT:] + +## Check we do not allow referencing sections that do not exist. +# RUN: not yaml2obj --docnum=2 %s -o %t 2>&1 | FileCheck %s --check-prefix=ERR +# ERR: error: Unknown section referenced: '.foo' by program header. + +--- !ELF +FileHeader: + Class: ELFCLASS64 + Data: ELFDATA2LSB + Type: ET_EXEC + Machine: EM_X86_64 +ProgramHeaders: + - Type: PT_LOAD + Sections: + - Section: .foo diff --git a/llvm/tools/yaml2obj/yaml2elf.cpp b/llvm/tools/yaml2obj/yaml2elf.cpp index cb12cdd5385d..697a1773084c 100644 --- a/llvm/tools/yaml2obj/yaml2elf.cpp +++ b/llvm/tools/yaml2obj/yaml2elf.cpp @@ -390,7 +390,18 @@ void ELFState::setProgramHeaderLayout(std::vector &PHeaders, std::vector &SHeaders) { uint32_t PhdrIdx = 0; for (auto &YamlPhdr : Doc.ProgramHeaders) { - auto &PHeader = PHeaders[PhdrIdx++]; + Elf_Phdr &PHeader = PHeaders[PhdrIdx++]; + + std::vector Sections; + for (const ELFYAML::SectionName &SecName : YamlPhdr.Sections) { + unsigned Index; + if (SN2I.lookup(SecName.Section, Index)) { + WithColor::error() << "Unknown section referenced: '" << SecName.Section + << "' by program header.\n"; + exit(1); + } + Sections.push_back(&SHeaders[Index]); + } if (YamlPhdr.Offset) { PHeader.p_offset = *YamlPhdr.Offset; @@ -401,12 +412,8 @@ void ELFState::setProgramHeaderLayout(std::vector &PHeaders, PHeader.p_offset = 0; // Find the minimum offset for the program header. - for (auto SecName : YamlPhdr.Sections) { - uint32_t Index = 0; - SN2I.lookup(SecName.Section, Index); - const auto &SHeader = SHeaders[Index]; - PHeader.p_offset = std::min(PHeader.p_offset, SHeader.sh_offset); - } + for (Elf_Shdr *SHeader : Sections) + PHeader.p_offset = std::min(PHeader.p_offset, SHeader->sh_offset); } // Find the maximum offset of the end of a section in order to set p_filesz, @@ -415,15 +422,12 @@ void ELFState::setProgramHeaderLayout(std::vector &PHeaders, PHeader.p_filesz = *YamlPhdr.FileSize; } else { PHeader.p_filesz = 0; - for (auto SecName : YamlPhdr.Sections) { - uint32_t Index = 0; - SN2I.lookup(SecName.Section, Index); - const auto &SHeader = SHeaders[Index]; + for (Elf_Shdr *SHeader : Sections) { uint64_t EndOfSection; - if (SHeader.sh_type == llvm::ELF::SHT_NOBITS) - EndOfSection = SHeader.sh_offset; + if (SHeader->sh_type == llvm::ELF::SHT_NOBITS) + EndOfSection = SHeader->sh_offset; else - EndOfSection = SHeader.sh_offset + SHeader.sh_size; + EndOfSection = SHeader->sh_offset + SHeader->sh_size; uint64_t EndOfSegment = PHeader.p_offset + PHeader.p_filesz; EndOfSegment = std::max(EndOfSegment, EndOfSection); PHeader.p_filesz = EndOfSegment - PHeader.p_offset; @@ -437,13 +441,9 @@ void ELFState::setProgramHeaderLayout(std::vector &PHeaders, PHeader.p_memsz = *YamlPhdr.MemSize; } else { PHeader.p_memsz = PHeader.p_filesz; - for (auto SecName : YamlPhdr.Sections) { - uint32_t Index = 0; - SN2I.lookup(SecName.Section, Index); - const auto &SHeader = SHeaders[Index]; - if (SHeader.sh_offset == PHeader.p_offset + PHeader.p_filesz) - PHeader.p_memsz += SHeader.sh_size; - } + for (Elf_Shdr *SHeader : Sections) + if (SHeader->sh_offset == PHeader.p_offset + PHeader.p_filesz) + PHeader.p_memsz += SHeader->sh_size; } // Set the alignment of the segment to be the same as the maximum alignment @@ -453,13 +453,9 @@ void ELFState::setProgramHeaderLayout(std::vector &PHeaders, PHeader.p_align = *YamlPhdr.Align; } else { PHeader.p_align = 1; - for (auto SecName : YamlPhdr.Sections) { - uint32_t Index = 0; - SN2I.lookup(SecName.Section, Index); - const auto &SHeader = SHeaders[Index]; - if (SHeader.sh_offset == PHeader.p_offset) - PHeader.p_align = std::max(PHeader.p_align, SHeader.sh_addralign); - } + for (Elf_Shdr *SHeader : Sections) + if (SHeader->sh_offset == PHeader.p_offset) + PHeader.p_align = std::max(PHeader.p_align, SHeader->sh_addralign); } } }