From 6868ca795390aeee525210e017bd03f57147e0f7 Mon Sep 17 00:00:00 2001 From: John Reiser Date: Wed, 15 Apr 2020 13:29:01 -0700 Subject: [PATCH] getElfSections concentrates on _Shdr[.e_shstrndx] https://github.com/upx/upx/issues/363 modified: p_vmlinx.cpp --- src/p_vmlinx.cpp | 54 ++++++++++++++++++++++-------------------------- 1 file changed, 25 insertions(+), 29 deletions(-) diff --git a/src/p_vmlinx.cpp b/src/p_vmlinx.cpp index c8f9a9d0..c6a8f5c1 100644 --- a/src/p_vmlinx.cpp +++ b/src/p_vmlinx.cpp @@ -104,42 +104,38 @@ PackVmlinuxBase::compare_Phdr(void const *aa, void const *bb) template typename T::Shdr const *PackVmlinuxBase::getElfSections() { - Shdr const *p, *shstrsec=0; + Shdr const *p; + unsigned const e_shnum = ehdri.e_shnum; if (ehdri.e_shentsize != sizeof(*shdri) || (unsigned long)file_size < ehdri.e_shoff - || (unsigned long)file_size < ehdri.e_shoff + ehdri.e_shentsize * ehdri.e_shnum) { + || (unsigned long)file_size < ehdri.e_shoff + ehdri.e_shentsize * e_shnum) { throwCantPack("bad ElfXX_Shdrs"); } - shdri = new Shdr[(unsigned) ehdri.e_shnum]; + shdri = new Shdr[(unsigned) e_shnum]; fi->seek(ehdri.e_shoff, SEEK_SET); - fi->readx(shdri, ehdri.e_shnum * sizeof(*shdri)); - unsigned e_shnum = ehdri.e_shnum; - unsigned j; - for (p = shdri, j = 0; j < e_shnum; ++j, ++p) { - if (Shdr::SHT_STRTAB==p->sh_type - && p->sh_offset <= ((unsigned long)file_size - sizeof(*shdri)) - && p->sh_size <= ((unsigned long)file_size - p->sh_offset) - && p->sh_name <= ((unsigned long)file_size - p->sh_offset) - && 10 <= ((unsigned long)file_size - p->sh_name) - // 10 == (1+ strlen(".shstrtab")) - ) { - if (p->sh_size <= p->sh_name) { - char msg[50]; snprintf(msg, sizeof(msg), - "bad SHT_STRTAB[%u]", j); - throwCantPack(msg); - } - delete [] shstrtab; - shstrtab = new char[1+ p->sh_size]; - fi->seek(p->sh_offset, SEEK_SET); - fi->readx(shstrtab, p->sh_size); - shstrtab[p->sh_size] = '\0'; - if (0==strcmp(".shstrtab", shstrtab + p->sh_name)) { - shstrsec = p; - break; - } + fi->readx(shdri, e_shnum * sizeof(*shdri)); + p = &shdri[ehdri.e_shstrndx]; // supposed + if (Shdr::SHT_STRTAB==p->sh_type + && p->sh_offset <= ((unsigned long)file_size - sizeof(*shdri)) + && p->sh_size <= ((unsigned long)file_size - p->sh_offset) + && p->sh_name <= ((unsigned long)file_size - p->sh_offset) + && 10 <= ((unsigned long)file_size - p->sh_name) + // 10 == (1+ strlen(".shstrtab")) + ) { + if (p->sh_size <= p->sh_name) { + char msg[50]; snprintf(msg, sizeof(msg), + "bad .shstrtab _Shdr[%u]", (unsigned)ehdri.e_shstrndx); + throwCantPack(msg); + } + shstrtab = new char[1+ p->sh_size]; + fi->seek(p->sh_offset, SEEK_SET); + fi->readx(shstrtab, p->sh_size); + shstrtab[p->sh_size] = '\0'; + if (0==strcmp(".shstrtab", shstrtab + p->sh_name)) { + return p; } } - return shstrsec; + return 0; } template