mirror of
https://github.com/upx/upx
synced 2025-09-28 19:06:07 +08:00
support for arm/WinCE ("arm/pe") exes
committer: ml1050 <ml1050> 1126255781 +0000
This commit is contained in:
parent
14d303d331
commit
572314bf3f
2
PROJECTS
2
PROJECTS
|
@ -42,8 +42,6 @@ More formats:
|
|||
- freebsd/386 (generic), freebsd/elf386 (specialized).
|
||||
Probably could share most of the linux code.
|
||||
|
||||
- Windows CE
|
||||
|
||||
- add support for self-extracting HTML pages using a Javascript stub
|
||||
(like the AlgART HTML Packer "AHP")
|
||||
|
||||
|
|
2
README
2
README
|
@ -149,7 +149,7 @@ Markus & Laszlo
|
|||
|
||||
|
||||
Markus F.X.J. Oberhumer Laszlo Molnar
|
||||
markus@oberhumer.com ml1050@cdata.tvnet.hu
|
||||
markus@oberhumer.com ml1050@users.sourceforge.net
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -30,4 +30,5 @@ The main news since 1.25 are:
|
|||
shell-to-memory decompression ("linux/sh386")
|
||||
- support for playstation exes ("ps1/exe")
|
||||
- lots of new bugs ;-) take care
|
||||
- support for arm/WinCE ("arm/pe") exes
|
||||
|
||||
|
|
|
@ -454,6 +454,7 @@ inline void operator delete[](void *p)
|
|||
#define UPX_F_PS1_EXE 18
|
||||
#define UPX_F_VMLINUX_i386 19
|
||||
#define UPX_F_LINUX_ELFI_i386 20
|
||||
#define UPX_F_WINCE_ARM_PE 21
|
||||
|
||||
#define UPX_F_ATARI_TOS 129
|
||||
#define UPX_F_SOLARIS_SPARC 130
|
||||
|
|
2052
src/p_armpe.cpp
Normal file
2052
src/p_armpe.cpp
Normal file
File diff suppressed because it is too large
Load Diff
251
src/p_armpe.h
Normal file
251
src/p_armpe.h
Normal file
|
@ -0,0 +1,251 @@
|
|||
/* p_armpe.h --
|
||||
|
||||
This file is part of the UPX executable compressor.
|
||||
|
||||
Copyright (C) 1996-2004 Markus Franz Xaver Johannes Oberhumer
|
||||
Copyright (C) 1996-2004 Laszlo Molnar
|
||||
All Rights Reserved.
|
||||
|
||||
UPX and the UCL library are free software; you can redistribute them
|
||||
and/or modify them under the terms of the GNU General Public License as
|
||||
published by the Free Software Foundation; either version 2 of
|
||||
the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; see the file COPYING.
|
||||
If not, write to the Free Software Foundation, Inc.,
|
||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
|
||||
Markus F.X.J. Oberhumer Laszlo Molnar
|
||||
markus@oberhumer.com ml1050@users.sourceforge.net
|
||||
*/
|
||||
|
||||
|
||||
#ifndef __UPX_P_ARMPE_H
|
||||
#define __UPX_P_ARMPE_H
|
||||
|
||||
|
||||
class PackArmPe_Interval;
|
||||
class PackArmPe_Reloc;
|
||||
class PackArmPe_Resource;
|
||||
class PackArmPe_Export;
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
// w32/pe
|
||||
**************************************************************************/
|
||||
|
||||
class PackArmPe : public Packer
|
||||
{
|
||||
typedef Packer super;
|
||||
|
||||
public:
|
||||
PackArmPe(InputFile *f);
|
||||
~PackArmPe();
|
||||
virtual int getVersion() const { return 13; }
|
||||
virtual int getFormat() const { return UPX_F_WINCE_ARM_PE; }
|
||||
virtual const char *getName() const { return "arm/pe"; }
|
||||
virtual const int *getCompressionMethods(int method, int level) const;
|
||||
virtual const int *getFilters() const;
|
||||
|
||||
virtual void pack(OutputFile *fo);
|
||||
virtual void unpack(OutputFile *fo);
|
||||
|
||||
virtual bool canPack();
|
||||
virtual int canUnpack();
|
||||
|
||||
// unpacker capabilities
|
||||
virtual bool canUnpackVersion(int version) const
|
||||
{ return false; }
|
||||
|
||||
protected:
|
||||
virtual int readFileHeader();
|
||||
virtual bool testUnpackVersion(int version) const;
|
||||
|
||||
virtual int buildLoader(const Filter *ft);
|
||||
|
||||
unsigned pe_offset;
|
||||
|
||||
unsigned processImports();
|
||||
void processImports(unsigned);
|
||||
void rebuildImports(upx_byte *&);
|
||||
upx_byte *oimport;
|
||||
unsigned soimport;
|
||||
upx_byte *oimpdlls;
|
||||
unsigned soimpdlls;
|
||||
|
||||
void processRelocs();
|
||||
void processRelocs(PackArmPe_Reloc *);
|
||||
void rebuildRelocs(upx_byte *&);
|
||||
upx_byte *orelocs;
|
||||
unsigned sorelocs;
|
||||
upx_byte *oxrelocs;
|
||||
unsigned soxrelocs;
|
||||
|
||||
void processExports(PackArmPe_Export *);
|
||||
void processExports(PackArmPe_Export *,unsigned);
|
||||
void rebuildExports();
|
||||
upx_byte *oexport;
|
||||
unsigned soexport;
|
||||
|
||||
void processResources(PackArmPe_Resource *);
|
||||
void processResources(PackArmPe_Resource *, unsigned);
|
||||
void rebuildResources(upx_byte *&);
|
||||
upx_byte *oresources;
|
||||
unsigned soresources;
|
||||
|
||||
void processTls(PackArmPe_Interval *);
|
||||
void processTls(PackArmPe_Reloc *,const PackArmPe_Interval *,unsigned);
|
||||
void rebuildTls();
|
||||
upx_byte *otls;
|
||||
unsigned sotls;
|
||||
|
||||
unsigned stripDebug(unsigned);
|
||||
|
||||
unsigned icondir_offset;
|
||||
int icondir_count;
|
||||
|
||||
bool importbyordinal;
|
||||
bool kernel32ordinal;
|
||||
unsigned tlsindex;
|
||||
unsigned rvamin;
|
||||
unsigned cimports; // rva of preprocessed imports
|
||||
unsigned crelocs; // rva of preprocessed fixups
|
||||
int big_relocs;
|
||||
|
||||
struct pe_header_t
|
||||
{
|
||||
// 0x0
|
||||
char _[4]; // pemagic
|
||||
LE16 cpu;
|
||||
LE16 objects;
|
||||
char __[12]; // timestamp + reserved
|
||||
LE16 opthdrsize;
|
||||
LE16 flags;
|
||||
// optional header
|
||||
char ___[4]; // coffmagic + linkerversion
|
||||
LE32 codesize;
|
||||
// 0x20
|
||||
LE32 datasize;
|
||||
LE32 bsssize;
|
||||
LE32 entry;
|
||||
LE32 codebase;
|
||||
// 0x30
|
||||
LE32 database;
|
||||
// nt specific fields
|
||||
LE32 imagebase;
|
||||
LE32 objectalign;
|
||||
LE32 filealign; // should set to 0x200 ?
|
||||
// 0x40
|
||||
char ____[16]; // versions
|
||||
// 0x50
|
||||
LE32 imagesize;
|
||||
LE32 headersize;
|
||||
LE32 chksum; // should set to 0
|
||||
LE16 subsystem;
|
||||
LE16 dllflags;
|
||||
// 0x60
|
||||
char _____[20]; // stack + heap sizes
|
||||
// 0x74
|
||||
LE32 ddirsentries; // usually 16
|
||||
|
||||
struct ddirs_t
|
||||
{
|
||||
LE32 vaddr;
|
||||
LE32 size;
|
||||
}
|
||||
__attribute_packed;
|
||||
|
||||
struct ddirs_t ddirs[16];
|
||||
}
|
||||
__attribute_packed;
|
||||
|
||||
struct pe_section_t
|
||||
{
|
||||
char name[8];
|
||||
LE32 vsize;
|
||||
LE32 vaddr;
|
||||
LE32 size;
|
||||
LE32 rawdataptr;
|
||||
char _[12];
|
||||
LE32 flags;
|
||||
}
|
||||
__attribute_packed;
|
||||
|
||||
pe_header_t ih, oh;
|
||||
pe_section_t *isection;
|
||||
|
||||
static unsigned virta2objnum (unsigned, pe_section_t *, unsigned);
|
||||
unsigned tryremove (unsigned, unsigned);
|
||||
|
||||
enum {
|
||||
PEDIR_EXPORT = 0,
|
||||
PEDIR_IMPORT = 1,
|
||||
PEDIR_RESOURCE = 2,
|
||||
PEDIR_EXCEPTION = 3, // Exception table
|
||||
PEDIR_SEC = 4, // Certificate table (file pointer)
|
||||
PEDIR_RELOC = 5,
|
||||
PEDIR_DEBUG = 6,
|
||||
PEDIR_COPYRIGHT = 7, // Architecture-specific data
|
||||
PEDIR_GLOBALPTR = 8, // Global pointer
|
||||
PEDIR_TLS = 9,
|
||||
PEDIR_LOADCONF = 10, // Load Config Table
|
||||
PEDIR_BOUNDIM = 11,
|
||||
PEDIR_IAT = 12,
|
||||
PEDIR_DELAYIMP = 13, // Delay Import Descriptor
|
||||
PEDIR_COMRT = 14 // Com+ Runtime Header
|
||||
};
|
||||
|
||||
enum {
|
||||
PEFL_CODE = 0x20,
|
||||
PEFL_DATA = 0x40,
|
||||
PEFL_BSS = 0x80,
|
||||
PEFL_INFO = 0x200,
|
||||
PEFL_EXTRELS = 0x01000000, // extended relocations
|
||||
PEFL_DISCARD = 0x02000000,
|
||||
PEFL_NOCACHE = 0x04000000,
|
||||
PEFL_NOPAGE = 0x08000000,
|
||||
PEFL_SHARED = 0x10000000,
|
||||
PEFL_EXEC = 0x20000000,
|
||||
PEFL_READ = 0x40000000,
|
||||
PEFL_WRITE = 0x80000000
|
||||
};
|
||||
|
||||
enum {
|
||||
RELOCS_STRIPPED = 0x0001,
|
||||
EXECUTABLE = 0x0002,
|
||||
LNUM_STRIPPED = 0x0004,
|
||||
LSYMS_STRIPPED = 0x0008,
|
||||
AGGRESSIVE_TRIM = 0x0010,
|
||||
TWO_GIGS_AWARE = 0x0020,
|
||||
FLITTLE_ENDIAN = 0x0080,
|
||||
BITS_32_MACHINE = 0x0100,
|
||||
DEBUG_STRIPPED = 0x0200,
|
||||
REMOVABLE_SWAP = 0x0400,
|
||||
SYSTEM_PROGRAM = 0x1000,
|
||||
DLL_FLAG = 0x2000,
|
||||
FBIG_ENDIAN = 0x8000
|
||||
};
|
||||
|
||||
// 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
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
#endif /* already included */
|
||||
|
||||
|
||||
/*
|
||||
vi:ts=4:et
|
||||
*/
|
|
@ -53,6 +53,7 @@
|
|||
#include "p_vmlinx.h"
|
||||
#include "p_ps1.h"
|
||||
#include "p_mach.h"
|
||||
#include "p_armpe.h"
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
|
@ -170,6 +171,8 @@ static Packer* try_packers(InputFile *f, try_function func)
|
|||
#endif
|
||||
if ((p = func(new PackW16Ne(f),f)) != NULL)
|
||||
return p;
|
||||
if ((p = func(new PackArmPe(f),f)) != NULL)
|
||||
return p;
|
||||
if ((p = func(new PackW32Pe(f),f)) != NULL)
|
||||
return p;
|
||||
}
|
||||
|
|
|
@ -12,3 +12,5 @@ stamp-h
|
|||
stubify.exe
|
||||
upxb
|
||||
upxd
|
||||
*.out
|
||||
*.ah
|
||||
|
|
|
@ -46,7 +46,8 @@ STUBS = \
|
|||
l_lx_pti86.h fold_pti86.h \
|
||||
l_lx_elfppc32.h fold_elfppc32.h \
|
||||
l_mac_ppc32.h fold_machppc32.h \
|
||||
l_vmlinz.h l_vmlinx.h
|
||||
l_vmlinz.h l_vmlinx.h \
|
||||
l_armpe.h
|
||||
|
||||
# experimental:
|
||||
ifneq ($(strip $(wildcard $(srcdir)/l_ext2.asm)),)
|
||||
|
@ -178,6 +179,15 @@ ifneq ($(wildcard $d),)
|
|||
endif
|
||||
|
||||
|
||||
###
|
||||
### ARM-PE-WINCE
|
||||
###
|
||||
|
||||
GCC_WINCE := arm-wince-pe-gcc -Os
|
||||
LD_WINCE := arm-wince-pe-ld
|
||||
OBJCOPY_WINCE := arm-wince-pe-objcopy
|
||||
BIN2H_WINCE := perl -ne 'print "db\t", join(",", map { sprintf "%\#02x", $$_ } unpack("C*", $$_)), "\n"'
|
||||
|
||||
# /***********************************************************************
|
||||
# // main targets
|
||||
# ************************************************************************/
|
||||
|
@ -276,7 +286,6 @@ l_w32pe.h: l_w32pe.asx
|
|||
$(NASM) -f bin -o $T.bin $<
|
||||
$(BIN2H) $T.bin nrv_loader $@
|
||||
|
||||
|
||||
# /***********************************************************************
|
||||
# // atari/tos rules
|
||||
# ************************************************************************/
|
||||
|
@ -477,6 +486,14 @@ upxd: l_lx_sep.o l_lx_sep86.asm
|
|||
$(STRIPELF_LINUX_I386) $@
|
||||
$(BRANDELF) $@
|
||||
|
||||
l_armpe.h: l_armpe.asx l_armpe_s.S l_armpe_c.c
|
||||
$(GCC_WINCE) -c l_armpe_s.S l_armpe_c.c
|
||||
$(LD_WINCE) -nostdlib -o l_armpe_.out l_armpe_s.o l_armpe_c.o
|
||||
$(OBJCOPY_WINCE) --only-section .text -O binary l_armpe_.out l_armpe_.bin
|
||||
$(BIN2H_WINCE) <l_armpe_.bin >l_armpe_.ah
|
||||
$(NASM) -f bin -o $T.bin $<
|
||||
$(BIN2H) $T.bin nrv_loader $@
|
||||
|
||||
|
||||
# /***********************************************************************
|
||||
# // dependencies
|
||||
|
@ -506,6 +523,7 @@ l_vmlinx.h: $(DEPS2) $(DEPS3)
|
|||
l_vxd.h: $(DEPS2) $(DEPS3)
|
||||
l_wcle.h: $(DEPS2) $(DEPS3)
|
||||
l_w32pe.h: $(DEPS2) $(DEPS3)
|
||||
l_armpe.h: $(DEPS2) $(DEPS3)
|
||||
|
||||
l_lx_elf86.h: l_lx_elf86.asm macros.ash macros.asy $(DEPS3)
|
||||
l_lx_exec86.h: l_lx_exec86.asm macros.ash macros.asy $(DEPS3)
|
||||
|
|
53
src/stub/l_armpe.asm
Normal file
53
src/stub/l_armpe.asm
Normal file
|
@ -0,0 +1,53 @@
|
|||
; l_armwce.asm -- loader & decompressor for the arm/wince/pe format
|
||||
;
|
||||
; This file is part of the UPX executable compressor.
|
||||
;
|
||||
; Copyright (C) 1996-2004 Markus Franz Xaver Johannes Oberhumer
|
||||
; Copyright (C) 1996-2004 Laszlo Molnar
|
||||
; All Rights Reserved.
|
||||
;
|
||||
; UPX and the UCL library are free software; you can redistribute them
|
||||
; and/or modify them under the terms of the GNU General Public License as
|
||||
; published by the Free Software Foundation; either version 2 of
|
||||
; the License, or (at your option) any later version.
|
||||
;
|
||||
; This program is distributed in the hope that it will be useful,
|
||||
; but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
; GNU General Public License for more details.
|
||||
;
|
||||
; You should have received a copy of the GNU General Public License
|
||||
; along with this program; see the file COPYING.
|
||||
; If not, write to the Free Software Foundation, Inc.,
|
||||
; 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
;
|
||||
; Markus F.X.J. Oberhumer Laszlo Molnar
|
||||
; <mfx@users.sourceforge.net> <ml1050@users.sourceforge.net>
|
||||
;
|
||||
|
||||
|
||||
%define jmps jmp short
|
||||
%define jmpn jmp near
|
||||
%include "macros.ash"
|
||||
|
||||
BITS 32
|
||||
SECTION .text
|
||||
ORG 0
|
||||
CPU 386
|
||||
|
||||
; =============
|
||||
; ============= ENTRY POINT
|
||||
; =============
|
||||
|
||||
; __ARMWPE00__
|
||||
start:
|
||||
%include "l_armpe_.ah"
|
||||
%include "header.ash"
|
||||
eof:
|
||||
; __ARMWPE99__
|
||||
section .data
|
||||
dd -1
|
||||
dw eof
|
||||
|
||||
|
||||
; vi:ts=8:et:nowrap
|
100
src/stub/l_armpe.h
Normal file
100
src/stub/l_armpe.h
Normal file
|
@ -0,0 +1,100 @@
|
|||
/* l_armpe.h -- created from l_armpe.bin, 1069 (0x42d) bytes
|
||||
|
||||
This file is part of the UPX executable compressor.
|
||||
|
||||
Copyright (C) 1996-2005 Markus Franz Xaver Johannes Oberhumer
|
||||
Copyright (C) 1996-2005 Laszlo Molnar
|
||||
All Rights Reserved.
|
||||
|
||||
UPX and the UCL library are free software; you can redistribute them
|
||||
and/or modify them under the terms of the GNU General Public License as
|
||||
published by the Free Software Foundation; either version 2 of
|
||||
the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; see the file COPYING.
|
||||
If not, write to the Free Software Foundation, Inc.,
|
||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
|
||||
Markus F.X.J. Oberhumer Laszlo Molnar
|
||||
<mfx@users.sourceforge.net> <ml1050@users.sourceforge.net>
|
||||
*/
|
||||
|
||||
|
||||
#define NRV_LOADER_ADLER32 0x793a99ed
|
||||
#define NRV_LOADER_CRC32 0x90e7375f
|
||||
|
||||
unsigned char nrv_loader[1069] = {
|
||||
15, 64, 45,233, 12, 0,160,227, 0, 0,143,224, 11, 0, 0,235, /* 0x 0 */
|
||||
15, 64,189,232, 24,240,159,229, 88,120,120, 88, 83, 82, 67, 48, /* 0x 10 */
|
||||
68, 83, 84, 48, 66, 73, 77, 80, 79, 78, 65, 77, 71, 69, 84, 80, /* 0x 20 */
|
||||
76, 79, 65, 68, 69, 78, 84, 82, 83, 82, 67, 76, 68, 83, 84, 76, /* 0x 30 */
|
||||
240, 71, 45,233, 4, 80,144,228, 0, 48,160,227, 4,112,144,228, /* 0x 40 */
|
||||
136,208, 77,226, 4, 32,144,228, 4, 48,141,229, 4,144,144,228, /* 0x 50 */
|
||||
3, 64,160,225, 4,128,144,228, 0, 32,141,229, 0, 96,144,229, /* 0x 60 */
|
||||
3,192,160,225, 3, 0,160,225, 1,160,160,227, 4, 0, 0,234, /* 0x 70 */
|
||||
5, 48,132,224, 0, 48,211,229, 1, 64,132,226, 7, 48,192,231, /* 0x 80 */
|
||||
1, 0,128,226,127, 0, 28,227, 5, 48,212, 7,140, 48,160, 17, /* 0x 90 */
|
||||
131, 48,160, 1, 1, 48,131, 2, 1, 64,132, 2, 1, 12, 19,227, /* 0x a0 */
|
||||
3,192,160,225,241,255,255, 26, 1, 16,160,227,127, 0, 28,227, /* 0x b0 */
|
||||
5, 48,212, 7,140, 48,160, 17,131, 48,160, 1, 1, 48,131, 2, /* 0x c0 */
|
||||
1, 64,132, 2, 3,192,160,225,127, 0, 19,227,129, 32,160,225, /* 0x d0 */
|
||||
131, 59,160,225,163, 31,130,225, 5, 48,212, 7,140, 48,160, 17, /* 0x e0 */
|
||||
131, 48,160, 1, 1, 48,131, 2, 1, 64,132, 2, 1, 12, 19,227, /* 0x f0 */
|
||||
3,192,160,225, 11, 0, 0, 26,127, 0, 19,227, 5, 48,212, 7, /* 0x 100 */
|
||||
131, 48,160, 17,131, 48,160, 1, 1, 48,131, 2,129, 32,160,225, /* 0x 110 */
|
||||
3,192,160,225,131, 59,160,225,163, 63,130,225, 1, 64,132, 2, /* 0x 120 */
|
||||
2, 16, 67,226,224,255,255,234, 2, 0, 81,227, 10, 0, 0, 26, /* 0x 130 */
|
||||
127, 0, 19,227, 5, 48,212, 7,131, 48,160, 17,131, 48,160, 1, /* 0x 140 */
|
||||
1, 48,131, 2, 3,192,160,225, 35, 52,160,225, 10, 16,160,225, /* 0x 150 */
|
||||
1, 64,132, 2, 1, 32, 3,226, 10, 0, 0,234, 5, 48,212,231, /* 0x 160 */
|
||||
1, 64,132,226, 1, 52,131,224, 3, 28, 67,226, 1, 0,113,227, /* 0x 170 */
|
||||
71, 0, 0, 10, 1, 48,224,225,161, 16,160,225, 1, 16,129,226, /* 0x 180 */
|
||||
1, 32, 3,226, 1,160,160,225, 0, 0, 82,227,127, 48, 12,226, /* 0x 190 */
|
||||
10, 0, 0, 10, 0, 0, 83,227, 5, 48,212, 7,140, 48,160, 17, /* 0x 1a0 */
|
||||
131, 48,160, 1, 1, 48,131, 2, 3,192,160,225, 35, 52,160,225, /* 0x 1b0 */
|
||||
1, 48, 3,226, 1, 64,132, 2, 1, 32,131,226, 39, 0, 0,234, /* 0x 1c0 */
|
||||
0, 0, 83,227, 5, 48,212, 7,140, 48,160, 17,131, 48,160, 1, /* 0x 1d0 */
|
||||
1, 48,131, 2, 1, 64,132, 2, 1, 12, 19,227, 3,192,160,225, /* 0x 1e0 */
|
||||
1, 32,160, 3, 10, 0, 0, 10,127, 0, 19,227, 5, 48,212, 7, /* 0x 1f0 */
|
||||
131, 48,160, 17,131, 48,160, 1, 1, 48,131, 2, 3,192,160,225, /* 0x 200 */
|
||||
35, 52,160,225, 1, 48, 3,226, 1, 64,132, 2, 3, 32,131,226, /* 0x 210 */
|
||||
18, 0, 0,234,127, 0, 28,227,140, 48,160,225, 5, 48,212, 7, /* 0x 220 */
|
||||
130, 32,160,225,131, 48,160, 1, 1, 48,131, 2,131,224,160,225, /* 0x 230 */
|
||||
1, 64,132, 2,127, 0, 19,227,131, 59,160,225,163, 47,130,225, /* 0x 240 */
|
||||
5, 48,212, 7, 1, 64,132, 2,131, 48,160, 1, 1,224,131, 2, /* 0x 250 */
|
||||
1, 12, 30,227, 14,192,160,225,237,255,255, 10, 3, 32,130,226, /* 0x 260 */
|
||||
0, 48,135,224, 3,224, 97,224, 1, 48,222,228, 5, 12, 81,227, /* 0x 270 */
|
||||
1, 32,130,130, 0, 48,199,231, 1, 0,128,226, 1, 48,222,228, /* 0x 280 */
|
||||
1, 32, 82,226, 7, 48,192,231, 1, 0,128,226,250,255,255, 26, /* 0x 290 */
|
||||
123,255,255,234, 0,160,150,229, 0,128,152,229, 0, 64,157,229, /* 0x 2a0 */
|
||||
4, 0,141,229, 3, 16,212,229, 2, 48,212,229, 1, 32,212,229, /* 0x 2b0 */
|
||||
1, 52,131,224, 0, 16,212,229, 3, 36,130,224, 2,228,129,224, /* 0x 2c0 */
|
||||
0, 0, 94,227, 59, 0, 0, 10, 4, 48,132,226, 3, 16,211,229, /* 0x 2d0 */
|
||||
2, 32,211,229, 1, 48,211,229, 1, 36,130,224, 4, 16,212,229, /* 0x 2e0 */
|
||||
2, 52,131,224, 9,192,254,231, 3, 20,129,224, 8, 0,141,226, /* 0x 2f0 */
|
||||
0, 0, 92,227, 7, 80,129,224, 0, 48,160,225, 3, 0, 0, 10, /* 0x 300 */
|
||||
178,192,195,224, 1,192,254,229, 0, 0, 92,227,250,255,255,234, /* 0x 310 */
|
||||
0, 32,160,227,176, 32,195,225, 15,224,160,225, 10,240,160,225, /* 0x 320 */
|
||||
8, 48,244,229, 0, 96,160,225, 0, 0, 83,227, 31, 0, 0, 10, /* 0x 330 */
|
||||
255, 48, 3,226, 1, 0, 83,227, 1, 64,132,226, 2, 0, 0, 10, /* 0x 340 */
|
||||
255, 0, 83,227, 9, 0, 0, 10, 19, 0, 0,234, 6, 0,160,225, /* 0x 350 */
|
||||
4, 16,160,225, 15,224,160,225, 8,240,160,225, 4, 0,133,228, /* 0x 360 */
|
||||
1, 48,212,228, 0, 0, 83,227,252,255,255, 26, 13, 0, 0,234, /* 0x 370 */
|
||||
0, 48,212,229, 1, 16,212,229, 6, 0,160,225, 1, 20,131,224, /* 0x 380 */
|
||||
15,224,160,225, 8,240,160,225, 2, 64,132,226, 5, 48,160,225, /* 0x 390 */
|
||||
4, 80,133,226, 0, 0,131,229, 2, 0, 0,234, 0, 32,160,227, /* 0x 3a0 */
|
||||
1, 48,160,227, 0, 32,131,229, 0, 48,212,229,221,255,255,234, /* 0x 3b0 */
|
||||
1, 64,132,226,186,255,255,234,136,208,141,226,240,135,189,232, /* 0x 3c0 */
|
||||
255,255,255,255, 0, 0, 0, 0,255,255,255,255, 0, 0, 0, 0, /* 0x 3d0 */
|
||||
85, 80, 88, 33,161,216,208,213, 0, 0, 0, 0, 0, 0, 0, 0, /* 0x 3e0 */
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 45, /* 0x 3f0 */
|
||||
65, 82, 77, 87, 80, 69, 48, 48, 0, 0, 0, 0, 0, 85, 80, 88, /* 0x 400 */
|
||||
49, 72, 69, 65, 68, 0,224, 3, 0, 0, 65, 82, 77, 87, 80, 69, /* 0x 410 */
|
||||
57, 57, 0, 0, 4, 0, 0,255,255,255,255, 0, 4 /* 0x 420 */
|
||||
};
|
326
src/stub/l_armpe_c.c
Normal file
326
src/stub/l_armpe_c.c
Normal file
|
@ -0,0 +1,326 @@
|
|||
#define WRITEFILE(name0, buf, len) \
|
||||
do { short b[3]; b[0] = '\\'; b[1] = name0; b[2] = 0; \
|
||||
typedef int (*CF)(short *, int, int, int, int, int, int); CF cf = (CF) 0x1f99c58; \
|
||||
typedef void (*WF)(int, const void *, int, int *, int); WF wf = (WF) 0x1f99d60; \
|
||||
typedef void (*CH)(int); CH ch = (CH) 0x1f9a2f0; \
|
||||
int h = cf(b, 0x40000000L, 3, 0, 2, 0x80, 0);\
|
||||
int l; wf(h, buf, len, &l, 0); \
|
||||
ch(h); } while (0)
|
||||
|
||||
|
||||
typedef unsigned int ucl_uint32;
|
||||
typedef int ucl_int32;
|
||||
typedef unsigned int ucl_uint;
|
||||
typedef int ucl_int;
|
||||
|
||||
static int
|
||||
ucl_nrv2e_decompress_8 ( const unsigned char * src, ucl_uint src_len,
|
||||
unsigned char * dst, ucl_uint * dst_len)
|
||||
{
|
||||
|
||||
{
|
||||
ucl_uint32 bb = 0;
|
||||
|
||||
|
||||
|
||||
ucl_uint ilen = 0, olen = 0, last_m_off = 1;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
for (;;)
|
||||
{
|
||||
ucl_uint m_off, m_len;
|
||||
|
||||
while ((((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1))
|
||||
{
|
||||
;
|
||||
;
|
||||
|
||||
|
||||
|
||||
|
||||
dst[olen++] = src[ilen++];
|
||||
|
||||
}
|
||||
m_off = 1;
|
||||
for (;;)
|
||||
{
|
||||
m_off = m_off*2 + (((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1);
|
||||
;
|
||||
;
|
||||
if ((((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1)) break;
|
||||
m_off = (m_off-1)*2 + (((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1);
|
||||
}
|
||||
if (m_off == 2)
|
||||
{
|
||||
m_off = last_m_off;
|
||||
m_len = (((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
;
|
||||
m_off = (m_off-3)*256 + src[ilen++];
|
||||
if (m_off == ((0xffffffff) + 0U))
|
||||
break;
|
||||
m_len = (m_off ^ ((0xffffffff) + 0U)) & 1;
|
||||
m_off >>= 1;
|
||||
last_m_off = ++m_off;
|
||||
}
|
||||
if (m_len)
|
||||
m_len = 1 + (((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1);
|
||||
else if ((((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1))
|
||||
m_len = 3 + (((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1);
|
||||
else
|
||||
{
|
||||
m_len++;
|
||||
do {
|
||||
m_len = m_len*2 + (((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1);
|
||||
;
|
||||
;
|
||||
} while (!(((bb = bb & 0x7f ? bb*2 : ((unsigned)src[ilen++]*2+1)) >> 8) & 1));
|
||||
m_len += 3;
|
||||
}
|
||||
m_len += (m_off > 0x500);
|
||||
;
|
||||
;
|
||||
|
||||
|
||||
|
||||
|
||||
{
|
||||
const unsigned char * m_pos;
|
||||
m_pos = dst + olen - m_off;
|
||||
dst[olen++] = *m_pos++;
|
||||
do dst[olen++] = *m_pos++; while (--m_len > 0);
|
||||
}
|
||||
|
||||
}
|
||||
*dst_len = olen;
|
||||
return ilen == src_len ? 0 : (ilen < src_len ? (-205) : (-201));
|
||||
}
|
||||
}
|
||||
|
||||
typedef void *(*loadlibraryw)(unsigned short *);
|
||||
typedef void *(*getprocaddra)(void *, void *);
|
||||
|
||||
#define T(a,b,c,d) ((a) + ((b) * 0x100) + ((c) * 0x10000) + ((d) * 0x1000000))
|
||||
|
||||
static inline void *get_le32(unsigned char *p)
|
||||
{
|
||||
return (void*) T(p[0], p[1], p[2], p[3]);
|
||||
}
|
||||
|
||||
static void handle_imports(unsigned char *imp,
|
||||
unsigned name_offset,
|
||||
unsigned iat_offset,
|
||||
loadlibraryw ll,
|
||||
getprocaddra gpa)
|
||||
{
|
||||
unsigned short buf[64];
|
||||
while (1)
|
||||
{
|
||||
unsigned short *b;
|
||||
//printf("name=%p iat=%p\n", get_le32(imp), get_le32(imp + 4));
|
||||
unsigned char *name = get_le32(imp);
|
||||
if (name == 0)
|
||||
break;
|
||||
name += name_offset;
|
||||
unsigned *iat = get_le32(imp + 4) + iat_offset;
|
||||
//printf("name=%p iat=%p\n", name, iat);
|
||||
for (b = buf; *name; name++, b++)
|
||||
*b = *name;
|
||||
*b = 0;
|
||||
|
||||
void *dll = ll(buf);
|
||||
imp += 8;
|
||||
unsigned ord;
|
||||
|
||||
while (*imp)
|
||||
{
|
||||
switch (*imp++)
|
||||
{
|
||||
case 1:
|
||||
// by name
|
||||
*iat++ = (unsigned) gpa(dll, imp);
|
||||
while (*imp++)
|
||||
;
|
||||
break;
|
||||
case 0xff:
|
||||
// by ordinal
|
||||
ord = ((unsigned) imp[0]) + imp[1] * 0x100;
|
||||
imp += 2;
|
||||
*iat++ = (unsigned) gpa(dll, (void *) ord);
|
||||
break;
|
||||
default:
|
||||
*(int*) 1 = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
imp++;
|
||||
}
|
||||
}
|
||||
|
||||
void upx_main(unsigned *info)
|
||||
{
|
||||
int dlen = 0;
|
||||
unsigned src0 = *info++;
|
||||
unsigned dst0 = *info++;
|
||||
unsigned bimp = *info++;
|
||||
unsigned onam = *info++;
|
||||
unsigned getp = *info++;
|
||||
unsigned load = *info++;
|
||||
unsigned entr = *info++;
|
||||
unsigned srcl = *info++;
|
||||
unsigned dstl = *info++;
|
||||
|
||||
//WRITEFILE('1', (void*) 0x11000, load + 256 - 0x11000);
|
||||
ucl_nrv2e_decompress_8((void *) src0, srcl, (void *) dst0, &dlen);
|
||||
handle_imports((void *) bimp, onam, dst0, *(void**) load, *(void**) getp);
|
||||
//WRITEFILE('2', (void*) 0x11000, load + 256 - 0x11000);
|
||||
}
|
||||
|
||||
#ifndef __pe__
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
static void *test_loadlibraryw(unsigned short *x)
|
||||
{
|
||||
printf("loadlibraryw called: ");
|
||||
while (*x)
|
||||
printf("%c", *x++);
|
||||
printf("\n");
|
||||
|
||||
static unsigned ret = 0x2a2a2a00;
|
||||
return (void*) ret++;
|
||||
}
|
||||
|
||||
static void *test_getprocaddra(void *a, void *x)
|
||||
{
|
||||
if ((unsigned) x < 0x10000)
|
||||
printf("getprocaddra called: %p %x\n", a, (unsigned) x);
|
||||
else
|
||||
printf("getprocaddra called: %p %s\n", a, (char*) x);
|
||||
|
||||
static unsigned ret = 1;
|
||||
return a + ret++;
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
if (argc != 2)
|
||||
return printf("usage: %s <compressed.exe>\n", argv[0]);
|
||||
|
||||
void *mem = malloc(32*1024*1024);
|
||||
void *mem16m = (void*) ((((unsigned) mem) + 0xffffff) & 0xff000000);
|
||||
printf("mem: %p %p\n", mem, mem16m);
|
||||
|
||||
char command[100 + strlen(argv[1])];
|
||||
snprintf(command, sizeof(command),
|
||||
"arm-wince-pe-objdump -h '%s'|grep '2[*][*]2'", argv[1]);
|
||||
FILE *fp = popen(command, "r");
|
||||
if (fgets(command, 100, fp) == NULL)
|
||||
return printf("error while calling objdump\n");
|
||||
|
||||
unsigned start_uncompressed;
|
||||
if (sscanf(command, "%*d %*s %*x %x", &start_uncompressed) != 1)
|
||||
return printf("scanf failed on '%s'", command);
|
||||
printf("start_uncompressed=%x ", start_uncompressed);
|
||||
|
||||
if (fgets(command, 100, fp) == NULL)
|
||||
return printf("error while calling objdump\n");
|
||||
unsigned size;
|
||||
unsigned offset;
|
||||
unsigned vma;
|
||||
if (sscanf(command, "%*d %*s %x %x %*x %x", &size, &vma, &offset) != 3)
|
||||
return printf("scanf failed on '%s'" , command);
|
||||
printf("size=%x vma=%x offset=%x\n", size, vma, offset);
|
||||
|
||||
if (fgets(command, 100, fp) == NULL)
|
||||
return printf("error while calling objdump\n");
|
||||
|
||||
unsigned size2;
|
||||
unsigned offset2;
|
||||
unsigned vma2;
|
||||
if (sscanf(command, "%*d %*s %x %x %*x %x", &size2, &vma2, &offset2) != 3)
|
||||
return printf("scanf failed on '%s'" , command);
|
||||
printf("size2=%x vma2=%x offset2=%x\n", size2, vma2, offset2);
|
||||
|
||||
pclose(fp);
|
||||
|
||||
FILE *f1 = fopen(argv[1], "rb");
|
||||
if (f1 == NULL)
|
||||
return printf("can not open %s\n", argv[1]);
|
||||
if (fseek(f1, offset, SEEK_SET))
|
||||
return printf("fseek failed\n");
|
||||
if (fread(mem16m + vma, size, 1, f1) != 1)
|
||||
return printf("fread failed\n");
|
||||
if (fseek(f1, offset2, SEEK_SET))
|
||||
return printf("fseek failed\n");
|
||||
if (fread(mem16m + vma2, size2, 1, f1) != 1)
|
||||
return printf("fread failed\n");
|
||||
fclose(f1);
|
||||
|
||||
unsigned *info = (unsigned *) memmem(mem16m + vma, size, "XxxX", 4);
|
||||
if (info == NULL)
|
||||
return printf("decompression info not found\n");
|
||||
|
||||
info++;
|
||||
unsigned src0 = *info++;
|
||||
unsigned dst0 = *info++;
|
||||
unsigned bimp = *info++;
|
||||
unsigned onam = *info++;
|
||||
unsigned getp = *info++;
|
||||
unsigned load = *info++;
|
||||
unsigned entr = *info++;
|
||||
unsigned srcl = *info++;
|
||||
unsigned dstl = *info++;
|
||||
|
||||
printf("%x %x %x %x %x %x %x %x %x\n", src0, srcl, dst0, dstl, bimp, onam, load, getp, entr);
|
||||
|
||||
int dlen = 0;
|
||||
int ret = ucl_nrv2e_decompress_8(mem16m + src0, srcl, mem16m + dst0, &dlen);
|
||||
|
||||
printf("dlen=%x, ret=%d\n", dlen, ret);
|
||||
if (dlen != (int) dstl)
|
||||
return printf("corrupt compressed data\n");
|
||||
|
||||
f1 = fopen("/tmp/image.out", "w");
|
||||
fwrite(mem16m, vma + size + 0x10000, 1, f1);
|
||||
fclose(f1);
|
||||
|
||||
handle_imports(bimp + mem16m, onam + mem16m, dst0 + mem16m,
|
||||
test_loadlibraryw, test_getprocaddra);
|
||||
|
||||
f1 = fopen("/tmp/image.out", "w");
|
||||
fwrite(mem16m, vma2 + size2, 1, f1);
|
||||
fclose(f1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if 0
|
||||
int main(void)
|
||||
{
|
||||
FILE *f1 = fopen("/r", "w");
|
||||
int h = LoadLibraryW(L"coredll.dll");
|
||||
fprintf(f1, "%p\n", GetProcAddressA(h, "DeleteFileW"));
|
||||
fclose(f1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
typedef void (*df)(ushort *);
|
||||
df dfw = 0x1f99bc8;
|
||||
dfw(L"\\r");
|
||||
return 0;
|
||||
}
|
||||
#endif
|
17
src/stub/l_armpe_s.S
Normal file
17
src/stub/l_armpe_s.S
Normal file
|
@ -0,0 +1,17 @@
|
|||
.text
|
||||
.align 0
|
||||
.global _mainCRTStartup
|
||||
|
||||
_mainCRTStartup:
|
||||
stmfd sp!, {r0 - r3, lr}
|
||||
mov r0, #L2 - L0 - 8
|
||||
L0:
|
||||
add r0, pc, r0
|
||||
bl _upx_main
|
||||
ldmfd sp!, {r0 - r3, lr}
|
||||
ldr pc, L21
|
||||
.ascii "XxxX"
|
||||
L2:
|
||||
.ascii "SRC0DST0BIMPONAMGETPLOAD"
|
||||
L21:
|
||||
.ascii "ENTRSRCLDSTL"
|
Loading…
Reference in New Issue
Block a user