src: clang-format pefile

This commit is contained in:
Markus F.X.J. Oberhumer 2023-01-29 12:34:05 +01:00
parent 19147963b9
commit 3fa18c1799
5 changed files with 1166 additions and 1565 deletions

View File

@ -81,7 +81,7 @@ ifeq ($(shell uname),Linux)
# Markus loves clang-format, but John hates it; find a compromise
CLANG_FORMAT_EXCLUDE_FILES += conf.h miniacc.h version.h help.cpp
CLANG_FORMAT_EXCLUDE_FILES += p_elf.h p_elf_enum.h p_lx_% p_mach% p_unix% p_vmli%
CLANG_FORMAT_EXCLUDE_FILES += p_w32pe.cpp p_w64pep.cpp packer_c.cpp packer_f.cpp pefile%
CLANG_FORMAT_EXCLUDE_FILES += packer_c.cpp packer_f.cpp
CLANG_FORMAT_EXCLUDE_FILES += compress/compress.h filter/filter_impl.cpp
CLANG_FORMAT_FILES := $(sort $(wildcard *.[ch]* ../maint/src/*.[ch]* [cu]*/*.[ch]*))
CLANG_FORMAT_FILES := $(filter-out $(CLANG_FORMAT_EXCLUDE_FILES),$(CLANG_FORMAT_FILES))

View File

@ -25,7 +25,6 @@
<markus@oberhumer.com> <ezerotven+github@gmail.com>
*/
#include "conf.h"
#include "file.h"
#include "filter.h"
@ -34,50 +33,35 @@
#include "p_w32pe.h"
#include "linker.h"
static const
static const CLANG_FORMAT_DUMMY_STATEMENT
#include "stub/i386-win32.pe.h"
/*************************************************************************
//
**************************************************************************/
PackW32Pe::PackW32Pe(InputFile *f) : super(f)
{}
PackW32Pe::PackW32Pe(InputFile *f) : super(f) {}
PackW32Pe::~PackW32Pe() {}
PackW32Pe::~PackW32Pe()
{}
const int *PackW32Pe::getCompressionMethods(int method, int level) const
{
const int *PackW32Pe::getCompressionMethods(int method, int level) const {
bool small = ih.codesize + ih.datasize <= 256 * 1024;
return Packer::getDefaultCompressionMethods_le32(method, level, small);
}
const int *PackW32Pe::getFilters() const
{
static const int filters[] = {
0x26, 0x24, 0x49, 0x46, 0x16, 0x13, 0x14, 0x11,
FT_ULTRA_BRUTE, 0x25, 0x15, 0x12,
FT_END };
const int *PackW32Pe::getFilters() const {
static const int filters[] = {0x26, 0x24, 0x49, 0x46, 0x16, 0x13, 0x14,
0x11, FT_ULTRA_BRUTE, 0x25, 0x15, 0x12, FT_END};
return filters;
}
Linker* PackW32Pe::newLinker() const
{
return new ElfLinkerX86;
}
Linker *PackW32Pe::newLinker() const { return new ElfLinkerX86; }
/*************************************************************************
// util
**************************************************************************/
int PackW32Pe::readFileHeader()
{
int PackW32Pe::readFileHeader() {
if (fi->st_size() >= 0x206) {
char buf[6];
fi->seek(0x200, SEEK_SET);
@ -91,16 +75,13 @@ int PackW32Pe::readFileHeader()
// pack
**************************************************************************/
bool PackW32Pe::canPack()
{
bool PackW32Pe::canPack() {
if (!readFileHeader() || ih.cpu < 0x14c || ih.cpu > 0x150)
return false;
return true;
}
void PackW32Pe::buildLoader(const Filter *ft)
{
void PackW32Pe::buildLoader(const Filter *ft) {
// recompute tlsindex (see pack() below)
unsigned tmp_tlsindex = tlsindex;
const unsigned oam1 = ih.objectalign - 1;
@ -112,50 +93,29 @@ void PackW32Pe::buildLoader(const Filter *ft)
initLoader(stub_i386_win32_pe, sizeof(stub_i386_win32_pe), 2);
if (isdll)
addLoader("PEISDLL1");
addLoader("PEMAIN01",
use_stub_relocs ? "PESOCREL" : "PESOCPIC",
"PESOUNC0",
addLoader("PEMAIN01", use_stub_relocs ? "PESOCREL" : "PESOCPIC", "PESOUNC0",
icondir_count > 1 ? (icondir_count == 2 ? "PEICONS1" : "PEICONS2") : "",
tmp_tlsindex ? "PETLSHAK" : "",
"PEMAIN02",
ph.first_offset_found == 1 ? "PEMAIN03" : "",
getDecompressorSections(),
tmp_tlsindex ? "PETLSHAK" : "", "PEMAIN02",
ph.first_offset_found == 1 ? "PEMAIN03" : "", getDecompressorSections(),
// multipass ? "PEMULTIP" : "",
"PEMAIN10",
nullptr
);
"PEMAIN10", nullptr);
addLoader(tmp_tlsindex ? "PETLSHAK2" : "");
if (ft->id)
{
if (ft->id) {
const unsigned texv = ih.codebase - rvamin;
assert(ft->calls > 0);
addLoader(texv ? "PECTTPOS" : "PECTTNUL", nullptr);
addFilter32(ft->id);
}
if (soimport)
addLoader("PEIMPORT",
importbyordinal ? "PEIBYORD" : "",
kernel32ordinal ? "PEK32ORD" : "",
importbyordinal ? "PEIMORD1" : "",
"PEIMPOR2",
isdll ? "PEIERDLL" : "PEIEREXE",
"PEIMDONE",
nullptr
);
if (sorelocs)
{
addLoader("PEIMPORT", importbyordinal ? "PEIBYORD" : "", kernel32ordinal ? "PEK32ORD" : "",
importbyordinal ? "PEIMORD1" : "", "PEIMPOR2", isdll ? "PEIERDLL" : "PEIEREXE",
"PEIMDONE", nullptr);
if (sorelocs) {
addLoader(soimport == 0 || soimport + cimports != crelocs ? "PERELOC1" : "PERELOC2",
"PERELOC3,RELOC320",
big_relocs ? "REL32BIG" : "",
"RELOC32J",
nullptr
);
"PERELOC3,RELOC320", big_relocs ? "REL32BIG" : "", "RELOC32J", nullptr);
// FIXME: the following should be moved out of the above if
addLoader(big_relocs&6 ? "PERLOHI0" : "",
big_relocs&4 ? "PERELLO0" : "",
big_relocs&2 ? "PERELHI0" : "",
nullptr
);
addLoader(big_relocs & 6 ? "PERLOHI0" : "", big_relocs & 4 ? "PERELLO0" : "",
big_relocs & 2 ? "PERELHI0" : "", nullptr);
}
if (use_dep_hack)
addLoader("PEDEPHAK", nullptr);
@ -176,33 +136,28 @@ void PackW32Pe::buildLoader(const Filter *ft)
addLoader("PETLSC2", nullptr);
addLoader("IDENTSTR,UPX1HEAD", nullptr);
}
bool PackW32Pe::handleForceOption()
{
return (ih.cpu < 0x14c || ih.cpu > 0x150)
|| (ih.opthdrsize != 0xe0)
|| ((ih.flags & EXECUTABLE) == 0)
|| ((ih.flags & BITS_32_MACHINE) == 0) //NEW: 32 bit machine flag must be set - Stefan Widmann
|| (ih.coffmagic != 0x10B) //COFF magic is 0x10B in PE files, 0x20B in PE32+ files - Stefan Widmann
|| (ih.entry == 0 && !isdll)
|| (ih.ddirsentries != 16)
|| IDSIZE(PEDIR_EXCEPTION) // is this used on i386?
bool PackW32Pe::handleForceOption() {
return (ih.cpu < 0x14c || ih.cpu > 0x150) || (ih.opthdrsize != 0xe0) ||
((ih.flags & EXECUTABLE) == 0) ||
((ih.flags & BITS_32_MACHINE) ==
0) // NEW: 32 bit machine flag must be set - Stefan Widmann
|| (ih.coffmagic !=
0x10B) // COFF magic is 0x10B in PE files, 0x20B in PE32+ files - Stefan Widmann
|| (ih.entry == 0 && !isdll) || (ih.ddirsentries != 16) ||
IDSIZE(PEDIR_EXCEPTION) // is this used on i386?
// || IDSIZE(PEDIR_COPYRIGHT)
;
}
void PackW32Pe::defineSymbols(unsigned ncsection, unsigned upxsection,
unsigned sizeof_oh, unsigned ic,
unsigned s1addr)
{
void PackW32Pe::defineSymbols(unsigned ncsection, unsigned upxsection, unsigned sizeof_oh,
unsigned ic, unsigned s1addr) {
const unsigned myimport = ncsection + soresources - rvamin;
// patch loader
linker->defineSymbol("original_entry", ih.entry);
if (use_dep_hack)
{
if (use_dep_hack) {
// This works around a "protection" introduced in MSVCRT80, which
// works like this:
// When the compiler detects that it would link in some code from its
@ -225,24 +180,24 @@ void PackW32Pe::defineSymbols(unsigned ncsection, unsigned upxsection,
linker->defineSymbol("swri", addr & 0xfff); // page offset
// check whether osection[0].flags and osection[1].flags
// are on the same page
linker->defineSymbol("vp_size", ((addr & 0xfff) + 0x28 >= 0x1000) ?
0x2000 : 0x1000); // 2 pages or 1 page
linker->defineSymbol(
"vp_size", ((addr & 0xfff) + 0x28 >= 0x1000) ? 0x2000 : 0x1000); // 2 pages or 1 page
linker->defineSymbol("vp_base", addr & ~0xfff); // page mask
linker->defineSymbol("VirtualProtect", 0u-rvamin +
ilinkerGetAddress("kernel32.dll", "VirtualProtect"));
linker->defineSymbol("VirtualProtect",
0u - rvamin + ilinkerGetAddress("kernel32.dll", "VirtualProtect"));
}
linker->defineSymbol("reloc_delt", 0u - (unsigned) ih.imagebase - rvamin);
linker->defineSymbol("start_of_relocs", crelocs);
if (ilinker) {
if (!isdll)
linker->defineSymbol("ExitProcess", 0u-rvamin +
ilinkerGetAddress("kernel32.dll", "ExitProcess"));
linker->defineSymbol("GetProcAddress", 0u-rvamin +
ilinkerGetAddress("kernel32.dll", "GetProcAddress"));
linker->defineSymbol("ExitProcess",
0u - rvamin + ilinkerGetAddress("kernel32.dll", "ExitProcess"));
linker->defineSymbol("GetProcAddress",
0u - rvamin + ilinkerGetAddress("kernel32.dll", "GetProcAddress"));
linker->defineSymbol("kernel32_ordinals", myimport);
linker->defineSymbol("LoadLibraryA", 0u-rvamin +
ilinkerGetAddress("kernel32.dll", "LoadLibraryA"));
linker->defineSymbol("LoadLibraryA",
0u - rvamin + ilinkerGetAddress("kernel32.dll", "LoadLibraryA"));
linker->defineSymbol("start_of_imports", myimport);
linker->defineSymbol("compressed_imports", cimports);
}
@ -253,8 +208,8 @@ void PackW32Pe::defineSymbols(unsigned ncsection, unsigned upxsection,
// in case of overlapping decompression, this hack is needed,
// because windoze zeroes the word pointed by tlsindex before
// it starts programs
linker->defineSymbol("tls_value", (tlsindex + 4 > s1addr) ?
get_le32(obuf + tlsindex - s1addr - ic) : 0);
linker->defineSymbol("tls_value",
(tlsindex + 4 > s1addr) ? get_le32(obuf + tlsindex - s1addr - ic) : 0);
linker->defineSymbol("tls_address", tlsindex - rvamin);
linker->defineSymbol("icon_delta", icondir_count - 1);
@ -264,8 +219,7 @@ void PackW32Pe::defineSymbols(unsigned ncsection, unsigned upxsection,
linker->defineSymbol("start_of_uncompressed", 0u - esi0 + rvamin);
linker->defineSymbol("start_of_compressed", use_stub_relocs ? esi0 + ih.imagebase : esi0);
if (use_tls_callbacks)
{
if (use_tls_callbacks) {
// esi is ih.imagebase + rvamin
linker->defineSymbol("tls_callbacks_ptr", tlscb_ptr);
linker->defineSymbol("tls_module_base", 0u - rvamin);
@ -275,33 +229,24 @@ void PackW32Pe::defineSymbols(unsigned ncsection, unsigned upxsection,
// linker->dumpSymbols();
}
void PackW32Pe::addNewRelocations(Reloc &rel, unsigned base)
{
void PackW32Pe::addNewRelocations(Reloc &rel, unsigned base) {
if (use_stub_relocs)
rel.add(base + linker->getSymbolOffset("PESOCREL") + 1, 3);
}
void PackW32Pe::setOhDataBase(const pe_section_t *osection)
{
oh.database = osection[2].vaddr;
}
void PackW32Pe::setOhDataBase(const pe_section_t *osection) { oh.database = osection[2].vaddr; }
void PackW32Pe::setOhHeaderSize(const pe_section_t *osection)
{
void PackW32Pe::setOhHeaderSize(const pe_section_t *osection) {
oh.headersize = ALIGN_UP(pe_offset + sizeof(oh) + sizeof(*osection) * oh.objects, oh.filealign);
}
void PackW32Pe::pack(OutputFile *fo)
{
super::pack0(fo
, (1u<<IMAGE_SUBSYSTEM_WINDOWS_GUI)
| (1u<<IMAGE_SUBSYSTEM_WINDOWS_CUI)
| (1u<<IMAGE_SUBSYSTEM_EFI_APPLICATION)
| (1u<<IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER)
| (1u<<IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER)
| (1u<<IMAGE_SUBSYSTEM_EFI_ROM)
, 0x400000
, false);
void PackW32Pe::pack(OutputFile *fo) {
super::pack0(fo,
(1u << IMAGE_SUBSYSTEM_WINDOWS_GUI) | (1u << IMAGE_SUBSYSTEM_WINDOWS_CUI) |
(1u << IMAGE_SUBSYSTEM_EFI_APPLICATION) |
(1u << IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER) |
(1u << IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER) | (1u << IMAGE_SUBSYSTEM_EFI_ROM),
0x400000, false);
}
/* vim:set ts=4 sw=4 et: */

View File

@ -30,7 +30,6 @@
*/
#include "conf.h"
#include "file.h"
#include "filter.h"
@ -39,58 +38,41 @@
#include "p_w64pep.h"
#include "linker.h"
static const
static const CLANG_FORMAT_DUMMY_STATEMENT
#include "stub/amd64-win64.pep.h"
/*************************************************************************
//
**************************************************************************/
PackW64Pep::PackW64Pep(InputFile *f) : super(f)
{
use_stub_relocs = false;
}
PackW64Pep::PackW64Pep(InputFile *f) : super(f) { use_stub_relocs = false; }
PackW64Pep::~PackW64Pep() {}
PackW64Pep::~PackW64Pep()
{}
const int *PackW64Pep::getCompressionMethods(int method, int level) const
{
const int *PackW64Pep::getCompressionMethods(int method, int level) const {
bool small = ih.codesize + ih.datasize <= 256 * 1024;
return Packer::getDefaultCompressionMethods_le32(method, level, small);
}
const int *PackW64Pep::getFilters() const
{
const int *PackW64Pep::getFilters() const {
static const int filters[] = {0x49, FT_END};
return filters;
}
Linker* PackW64Pep::newLinker() const
{
return new ElfLinkerAMD64;
}
Linker *PackW64Pep::newLinker() const { return new ElfLinkerAMD64; }
/*************************************************************************
// pack
**************************************************************************/
bool PackW64Pep::canPack()
{
bool PackW64Pep::canPack() {
// just check if machine type is 0x8664
if (!readFileHeader() || ih.cpu != 0x8664) // CPU magic of AMD64 is 0x8664
return false;
return true;
}
void PackW64Pep::buildLoader(const Filter *ft)
{
void PackW64Pep::buildLoader(const Filter *ft) {
// recompute tlsindex (see pack() below)
unsigned tmp_tlsindex = tlsindex;
const unsigned oam1 = ih.objectalign - 1;
@ -105,54 +87,34 @@ void PackW64Pep::buildLoader(const Filter *ft)
addLoader("PEISDLL0");
if (isefi)
addLoader("PEISEFI0");
addLoader(isdll ? "PEISDLL1" : "",
"PEMAIN01",
addLoader(isdll ? "PEISDLL1" : "", "PEMAIN01",
icondir_count > 1 ? (icondir_count == 2 ? "PEICONS1" : "PEICONS2") : "",
tmp_tlsindex ? "PETLSHAK" : "",
"PEMAIN02",
tmp_tlsindex ? "PETLSHAK" : "", "PEMAIN02",
// ph.first_offset_found == 1 ? "PEMAIN03" : "",
M_IS_LZMA(ph.method) ? "LZMA_HEAD,LZMA_ELF00,LZMA_DEC20,LZMA_TAIL" :
M_IS_NRV2B(ph.method) ? "NRV_HEAD,NRV2B" :
M_IS_NRV2D(ph.method) ? "NRV_HEAD,NRV2D" :
M_IS_NRV2E(ph.method) ? "NRV_HEAD,NRV2E" : "UNKNOWN_COMPRESSION_METHOD",
M_IS_LZMA(ph.method) ? "LZMA_HEAD,LZMA_ELF00,LZMA_DEC20,LZMA_TAIL"
: M_IS_NRV2B(ph.method) ? "NRV_HEAD,NRV2B"
: M_IS_NRV2D(ph.method) ? "NRV_HEAD,NRV2D"
: M_IS_NRV2E(ph.method) ? "NRV_HEAD,NRV2E"
: "UNKNOWN_COMPRESSION_METHOD",
// getDecompressorSections(),
/*multipass ? "PEMULTIP" : */ "",
"PEMAIN10",
nullptr
);
/*multipass ? "PEMULTIP" : */ "", "PEMAIN10", nullptr);
addLoader(tmp_tlsindex ? "PETLSHAK2" : "");
if (ft->id)
{
if (ft->id) {
const unsigned texv = ih.codebase - rvamin;
assert(ft->calls > 0);
addLoader(texv ? "PECTTPOS" : "PECTTNUL", nullptr);
addLoader("PEFILTER49");
}
if (soimport)
addLoader("PEIMPORT",
importbyordinal ? "PEIBYORD" : "",
kernel32ordinal ? "PEK32ORD" : "",
importbyordinal ? "PEIMORD1" : "",
"PEIMPOR2",
isdll ? "PEIERDLL" : "PEIEREXE",
"PEIMDONE",
nullptr
);
if (sorelocs)
{
addLoader("PEIMPORT", importbyordinal ? "PEIBYORD" : "", kernel32ordinal ? "PEK32ORD" : "",
importbyordinal ? "PEIMORD1" : "", "PEIMPOR2", isdll ? "PEIERDLL" : "PEIEREXE",
"PEIMDONE", nullptr);
if (sorelocs) {
addLoader(soimport == 0 || soimport + cimports != crelocs ? "PERELOC1" : "PERELOC2",
"PERELOC3",
big_relocs ? "REL64BIG" : "",
"RELOC64J",
nullptr
);
if __acc_cte(0)
{
addLoader(big_relocs&6 ? "PERLOHI0" : "",
big_relocs&4 ? "PERELLO0" : "",
big_relocs&2 ? "PERELHI0" : "",
nullptr
);
"PERELOC3", big_relocs ? "REL64BIG" : "", "RELOC64J", nullptr);
if __acc_cte (0) {
addLoader(big_relocs & 6 ? "PERLOHI0" : "", big_relocs & 4 ? "PERELLO0" : "",
big_relocs & 2 ? "PERELHI0" : "", nullptr);
}
}
if (use_dep_hack)
@ -180,28 +142,25 @@ void PackW64Pep::buildLoader(const Filter *ft)
addLoader("IDENTSTR,UPX1HEAD", nullptr);
}
bool PackW64Pep::handleForceOption()
{
bool PackW64Pep::handleForceOption() {
return (ih.cpu != 0x8664) // CPU magic of AMD64 is 0x8664
|| (ih.opthdrsize != 0xF0) //optional header size is 0xF0 in PE32+ files - Stefan Widmann
|| (ih.coffmagic != 0x20B) //COFF magic is 0x20B in PE+ files, 0x10B in "normal" 32 bit PE files - Stefan Widmann
|| ((ih.flags & EXECUTABLE) == 0)
|| ((ih.flags & BITS_32_MACHINE) != 0) //NEW: 32 bit machine flag may not be set - Stefan Widmann
|| (ih.entry == 0 && !isdll)
|| (ih.ddirsentries != 16)
;
||
(ih.opthdrsize != 0xF0) // optional header size is 0xF0 in PE32+ files - Stefan Widmann
|| (ih.coffmagic != 0x20B) // COFF magic is 0x20B in PE+ files, 0x10B in "normal" 32 bit
// PE files - Stefan Widmann
|| ((ih.flags & EXECUTABLE) == 0) ||
((ih.flags & BITS_32_MACHINE) !=
0) // NEW: 32 bit machine flag may not be set - Stefan Widmann
|| (ih.entry == 0 && !isdll) || (ih.ddirsentries != 16);
}
void PackW64Pep::defineSymbols(unsigned ncsection, unsigned upxsection,
unsigned sizeof_oh, unsigned ic,
unsigned s1addr)
{
void PackW64Pep::defineSymbols(unsigned ncsection, unsigned upxsection, unsigned sizeof_oh,
unsigned ic, unsigned s1addr) {
const unsigned myimport = ncsection + soresources - rvamin;
// patch loader
linker->defineSymbol("original_entry", ih.entry);
if (use_dep_hack)
{
if (use_dep_hack) {
// This works around a "protection" introduced in MSVCRT80, which
// works like this:
// When the compiler detects that it would link in some code from its
@ -224,29 +183,24 @@ void PackW64Pep::defineSymbols(unsigned ncsection, unsigned upxsection,
linker->defineSymbol("swri", addr & 0xfff); // page offset
// check whether osection[0].flags and osection[1].flags
// are on the same page
linker->defineSymbol("vp_size", ((addr & 0xfff) + 0x28 >= 0x1000) ?
0x2000 : 0x1000); // 2 pages or 1 page
linker->defineSymbol(
"vp_size", ((addr & 0xfff) + 0x28 >= 0x1000) ? 0x2000 : 0x1000); // 2 pages or 1 page
linker->defineSymbol("vp_base", addr & ~0xfff); // page mask
linker->defineSymbol("VirtualProtect",
ilinkerGetAddress("kernel32.dll", "VirtualProtect"));
linker->defineSymbol("VirtualProtect", ilinkerGetAddress("kernel32.dll", "VirtualProtect"));
}
linker->defineSymbol("start_of_relocs", crelocs);
if (ilinker) {
if (!isdll)
linker->defineSymbol("ExitProcess",
ilinkerGetAddress("kernel32.dll", "ExitProcess"));
linker->defineSymbol("GetProcAddress",
ilinkerGetAddress("kernel32.dll", "GetProcAddress"));
linker->defineSymbol("ExitProcess", ilinkerGetAddress("kernel32.dll", "ExitProcess"));
linker->defineSymbol("GetProcAddress", ilinkerGetAddress("kernel32.dll", "GetProcAddress"));
linker->defineSymbol("kernel32_ordinals", myimport);
linker->defineSymbol("LoadLibraryA",
ilinkerGetAddress("kernel32.dll", "LoadLibraryA"));
linker->defineSymbol("LoadLibraryA", ilinkerGetAddress("kernel32.dll", "LoadLibraryA"));
linker->defineSymbol("start_of_imports", myimport);
linker->defineSymbol("compressed_imports", cimports);
}
if (M_IS_LZMA(ph.method))
{
if (M_IS_LZMA(ph.method)) {
linker->defineSymbol("lzma_c_len", ph.c_len - 2);
linker->defineSymbol("lzma_u_len", ph.u_len);
}
@ -255,8 +209,8 @@ void PackW64Pep::defineSymbols(unsigned ncsection, unsigned upxsection,
// in case of overlapping decompression, this hack is needed,
// because windoze zeroes the word pointed by tlsindex before
// it starts programs
linker->defineSymbol("tls_value", (tlsindex + 4 > s1addr) ?
get_le32(obuf + tlsindex - s1addr - ic) : 0);
linker->defineSymbol("tls_value",
(tlsindex + 4 > s1addr) ? get_le32(obuf + tlsindex - s1addr - ic) : 0);
linker->defineSymbol("tls_address", tlsindex - rvamin);
linker->defineSymbol("icon_delta", icondir_count - 1);
@ -266,8 +220,7 @@ void PackW64Pep::defineSymbols(unsigned ncsection, unsigned upxsection,
linker->defineSymbol("start_of_uncompressed", 0u - esi0 + rvamin);
linker->defineSymbol("start_of_compressed", esi0);
if (use_tls_callbacks)
{
if (use_tls_callbacks) {
linker->defineSymbol("tls_callbacks_ptr", tlscb_ptr - ih.imagebase);
linker->defineSymbol("tls_module_base", 0u - rvamin);
}
@ -275,21 +228,17 @@ void PackW64Pep::defineSymbols(unsigned ncsection, unsigned upxsection,
linker->defineSymbol("START", upxsection);
}
void PackW64Pep::setOhHeaderSize(const pe_section_t *osection)
{
void PackW64Pep::setOhHeaderSize(const pe_section_t *osection) {
oh.headersize = ALIGN_UP(pe_offset + sizeof(oh) + sizeof(*osection) * oh.objects, oh.filealign);
}
void PackW64Pep::pack(OutputFile *fo)
{
super::pack0(fo
, (1u<<IMAGE_SUBSYSTEM_WINDOWS_GUI)
| (1u<<IMAGE_SUBSYSTEM_WINDOWS_CUI)
| (1u<<IMAGE_SUBSYSTEM_EFI_APPLICATION)
| (1u<<IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER)
| (1u<<IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER)
| (1u<<IMAGE_SUBSYSTEM_EFI_ROM)
, 0x0000000140000000ULL);
void PackW64Pep::pack(OutputFile *fo) {
super::pack0(fo,
(1u << IMAGE_SUBSYSTEM_WINDOWS_GUI) | (1u << IMAGE_SUBSYSTEM_WINDOWS_CUI) |
(1u << IMAGE_SUBSYSTEM_EFI_APPLICATION) |
(1u << IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER) |
(1u << IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER) | (1u << IMAGE_SUBSYSTEM_EFI_ROM),
0x0000000140000000ULL);
}
/* vim:set ts=4 sw=4 et: */

File diff suppressed because it is too large Load Diff

View File

@ -25,19 +25,17 @@
<markus@oberhumer.com> <ezerotven+github@gmail.com>
*/
#ifndef __UPX_PEFILE_H
#define __UPX_PEFILE_H 1
#pragma once
#ifndef UPX_PEFILE_H__
#define UPX_PEFILE_H__ 1
#include "util/membuffer.h"
/*************************************************************************
// general/pe handling
**************************************************************************/
class PeFile : public Packer
{
class PeFile : public Packer {
typedef Packer super;
public:
virtual int getVersion() const override { return 13; }
@ -53,20 +51,17 @@ protected:
virtual ~PeFile();
void readSectionHeaders(unsigned objs, unsigned sizeof_ih);
unsigned readSections(unsigned objs, unsigned usize,
unsigned ih_filealign, unsigned ih_datasize);
void checkHeaderValues(unsigned subsystem, unsigned mask,
unsigned ih_entry, unsigned ih_filealign);
unsigned handleStripRelocs(upx_uint64_t ih_imagebase,
upx_uint64_t default_imagebase,
unsigned readSections(unsigned objs, unsigned usize, unsigned ih_filealign,
unsigned ih_datasize);
void checkHeaderValues(unsigned subsystem, unsigned mask, unsigned ih_entry,
unsigned ih_filealign);
unsigned handleStripRelocs(upx_uint64_t ih_imagebase, upx_uint64_t default_imagebase,
LE16 &dllflags);
virtual bool handleForceOption() = 0;
virtual void callCompressWithFilters(Filter &, int filter_strategy,
unsigned ih_codebase);
virtual void defineSymbols(unsigned ncsection, unsigned upxsection,
unsigned sizeof_oh, unsigned isize_isplit,
unsigned s1addr) = 0;
virtual void callCompressWithFilters(Filter &, int filter_strategy, unsigned ih_codebase);
virtual void defineSymbols(unsigned ncsection, unsigned upxsection, unsigned sizeof_oh,
unsigned isize_isplit, unsigned s1addr) = 0;
virtual void addNewRelocations(Reloc &, unsigned) {}
void callProcessRelocs(Reloc &rel, unsigned &ic);
void callProcessResources(Resource &res, unsigned &ic);
@ -75,20 +70,18 @@ protected:
virtual void setOhHeaderSize(const pe_section_t *osection) = 0;
template <typename LEXX, typename ht>
void pack0(OutputFile *fo, ht &ih, ht &oh,
unsigned subsystem_mask, upx_uint64_t default_imagebase,
bool last_section_rsrc_only);
void pack0(OutputFile *fo, ht &ih, ht &oh, unsigned subsystem_mask,
upx_uint64_t default_imagebase, bool last_section_rsrc_only);
template <typename ht, typename LEXX, typename ord_mask_t>
void unpack0(OutputFile *fo, const ht &ih, ht &oh,
ord_mask_t ord_mask, bool set_oft);
void unpack0(OutputFile *fo, const ht &ih, ht &oh, ord_mask_t ord_mask, bool set_oft);
// unpacker capabilities
virtual bool canUnpackVersion(int version) const override
{ return (version >= 12 && version <= 13); }
virtual bool canUnpackVersion(int version) const override {
return (version >= 12 && version <= 13);
}
int canUnpack0(unsigned max_sections, unsigned objs,
unsigned ih_entry, unsigned ih_size);
int canUnpack0(unsigned max_sections, unsigned objs, unsigned ih_entry, unsigned ih_size);
protected:
virtual int readFileHeader();
@ -101,8 +94,7 @@ protected:
unsigned processImports0(ord_mask_t ord_mask);
template <typename LEXX, typename ord_mask_t>
void rebuildImports(SPAN_S(upx_byte) & extrainfo,
ord_mask_t ord_mask, bool set_oft);
void rebuildImports(SPAN_S(upx_byte) & extrainfo, ord_mask_t ord_mask, bool set_oft);
virtual unsigned processImports() = 0;
virtual void processImports2(unsigned, unsigned);
MemBuffer mb_oimport;
@ -118,8 +110,7 @@ protected:
virtual void processRelocs() = 0;
void processRelocs(Reloc *);
void rebuildRelocs(SPAN_S(upx_byte) &, unsigned bits,
unsigned flags, upx_uint64_t imagebase);
void rebuildRelocs(SPAN_S(upx_byte) &, unsigned bits, unsigned flags, upx_uint64_t imagebase);
MemBuffer mb_orelocs;
SPAN_0(upx_byte) orelocs = nullptr;
unsigned sorelocs;
@ -143,8 +134,7 @@ protected:
template <typename>
struct tls_traits;
template <typename LEXX>
void processTls1(Interval *iv,
typename tls_traits<LEXX>::cb_value_t imagebase,
void processTls1(Interval *iv, typename tls_traits<LEXX>::cb_value_t imagebase,
unsigned imagesize); // pass 1
template <typename LEXX>
void processTls2(Reloc *rel, const Interval *iv, unsigned newaddr,
@ -217,7 +207,6 @@ protected:
bool use_clear_dirty_stack;
bool use_stub_relocs;
static unsigned virta2objnum(unsigned, SPAN_0(pe_section_t), unsigned);
unsigned tryremove(unsigned, unsigned);
@ -302,20 +291,35 @@ protected:
// predefined resource types
enum {
RT_CURSOR = 1, RT_BITMAP, RT_ICON, RT_MENU, RT_DIALOG, RT_STRING,
RT_FONTDIR, RT_FONT, RT_ACCELERATOR, RT_RCDATA, RT_MESSAGETABLE,
RT_GROUP_CURSOR, RT_GROUP_ICON = 14, RT_VERSION = 16, RT_DLGINCLUDE,
RT_PLUGPLAY = 19, RT_VXD, RT_ANICURSOR, RT_ANIICON, RT_HTML,
RT_MANIFEST, RT_LAST
RT_CURSOR = 1,
RT_BITMAP,
RT_ICON,
RT_MENU,
RT_DIALOG,
RT_STRING,
RT_FONTDIR,
RT_FONT,
RT_ACCELERATOR,
RT_RCDATA,
RT_MESSAGETABLE,
RT_GROUP_CURSOR,
RT_GROUP_ICON = 14,
RT_VERSION = 16,
RT_DLGINCLUDE,
RT_PLUGPLAY = 19,
RT_VXD,
RT_ANICURSOR,
RT_ANIICON,
RT_HTML,
RT_MANIFEST,
RT_LAST
};
class Interval : private noncopyable
{
class Interval : private noncopyable {
unsigned capacity;
void *base;
public:
struct interval
{
struct interval {
unsigned start, len;
} *ivarr;
@ -337,8 +341,7 @@ protected:
static int __acc_cdecl_qsort compare(const void *p1, const void *p2);
};
class Reloc : private noncopyable
{
class Reloc : private noncopyable {
upx_byte *start;
unsigned size;
@ -360,8 +363,7 @@ protected:
void finish(upx_byte *&p, unsigned &size);
};
class Resource : private noncopyable
{
class Resource : private noncopyable {
struct res_dir_entry;
struct res_dir;
struct res_data;
@ -392,8 +394,7 @@ protected:
public:
Resource(const upx_byte *ibufstart, const upx_byte *ibufen);
Resource(const upx_byte *p, const upx_byte *ibufstart,
const upx_byte *ibufend);
Resource(const upx_byte *p, const upx_byte *ibufstart, const upx_byte *ibufend);
~Resource();
void init(const upx_byte *);
@ -418,8 +419,7 @@ protected:
*/
};
class Export : private noncopyable
{
class Export : private noncopyable {
struct alignas(1) export_dir_t {
char _[12]; // flags, timedate, version
LE32 name;
@ -449,17 +449,15 @@ protected:
void build(char *base, unsigned newoffs);
unsigned getsize() const { return size; }
};
};
class PeFile32 : public PeFile
{
class PeFile32 : public PeFile {
typedef PeFile super;
protected:
PeFile32(InputFile *f);
virtual ~PeFile32();
void pack0(OutputFile *fo, unsigned subsystem_mask,
upx_uint64_t default_imagebase, bool last_section_rsrc_only);
void pack0(OutputFile *fo, unsigned subsystem_mask, upx_uint64_t default_imagebase,
bool last_section_rsrc_only);
virtual void unpack(OutputFile *fo) override;
virtual int canUnpack() override;
@ -512,15 +510,13 @@ protected:
pe_header_t ih, oh;
};
class PeFile64 : public PeFile
{
class PeFile64 : public PeFile {
typedef PeFile super;
protected:
PeFile64(InputFile *f);
virtual ~PeFile64();
void pack0(OutputFile *fo, unsigned subsystem_mask,
upx_uint64_t default_imagebase);
void pack0(OutputFile *fo, unsigned subsystem_mask, upx_uint64_t default_imagebase);
virtual void unpack(OutputFile *fo) override;
virtual int canUnpack() override;