source files for arm-darwin.macho-*.S

This commit is contained in:
John Reiser
2008-11-16 07:35:53 -08:00
parent 4c4768aaf3
commit b60caeb9dd
2 changed files with 427 additions and 0 deletions
+141
View File
@@ -0,0 +1,141 @@
/* arm-darwin.macho-entry.S -- iPhone program entry point & decompressor (Elf binary)
*
* This file is part of the UPX executable compressor.
*
* Copyright (C) 1996-2008 Markus Franz Xaver Johannes Oberhumer
* Copyright (C) 1996-2008 Laszlo Molnar
* Copyright (C) 2000-2008 John F. Reiser
* 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>
*
* John F. Reiser
* <jreiser@users.sourceforge.net>
*/
//#define SIMULATE_ON_DEBIAN_EABI4 1
#undef SIMULATE_ON_DEBIAN_EABI4
#ifdef SIMULATE_ON_DEBIAN_EABI4 /*{*/
#define LINUX_ARM_CACHEFLUSH 1 /* SIMULATE_ON_DEBIAN_EABI4 */
#define ARMEL_EABI4 1 /* SIMULATE_ON_DEBIAN_EABI4 */
#else /*}{ usual case */
#define DARWIN_ARM_CACHEFLUSH 1
#define ARMEL_DARWIN 1
#endif /*}*/
#include "arch/arm/v5a/macros.S"
#define bkpt .long 0xe1200070
sz_b_info= 12
sz_unc= 0
sz_cpr= 4
b_method= 8
sz_l_info= 12
sz_p_info= 12
PROT_READ= 1
PROT_WRITE= 2
PROT_EXEC= 4
MAP_PRIVATE= 2
MAP_FIXED= 0x10
MAP_ANONYMOUS= 0x20
PAGE_SHIFT= 12
PAGE_SIZE = -(~0<<PAGE_SHIFT)
__NR_exit = 1 + __NR_SYSCALL_BASE
__NR_write = 4 + __NR_SYSCALL_BASE
__NR_mmap = 197 + __NR_SYSCALL_BASE
// DEBUG ONLY:
__ARM_NR_BASE = 0xf0000 + __NR_SYSCALL_BASE
__ARM_NR_cacheflush = 2 + __ARM_NR_BASE
//.long sz_pack2 // placed there by ::pack3()
section MACHMAINX
_start: .globl _start
sub sp,sp,#4 // space for mhdrp
stmdb sp!,{r0-r12,r14,r15} // paranoia [omit sp===r13]
bl main
L20:
f_decompress:
section NRV_HEAD
// empty
section NRV2E
#include "arch/arm/v4a/nrv2e_d8.S"
section NRV2D
#include "arch/arm/v4a/nrv2d_d8.S"
section NRV2B
#include "arch/arm/v4a/nrv2b_d8.S"
section NRV_TAIL
// empty
#include "arch/arm/v4a/lzma_d.S"
section MACHMAINY
end_decompress: .globl end_decompress
/* IDENTSTR goes here */
section MACHMAINZ
unfold: // lr= &L100
ldr ldst,[lr,#sz_unc]
ldr lsrc,[lr,#sz_cpr]
add dst,lsrc,lr; add dst,dst,#sz_b_info
add src,ldst,lr; add src,src,#GAP+NO_LAP // defend against prefetch and overlap
mov r4,lsrc // loop count
movup: // descending copy folded_loader to higher address
ldrb ip,[dst,#-1]!
subs r4,r4,#1
strb ip,[src,#-1]!
bne movup
ldr r4, [lr,#b_method]
add lr,lr,#GAP
PUSH {ldst}; mov ldst,sp // LZMA needs for EOF
mov dst,lr // unfolded result
sub r11,r5,#4+ L20 - _start // &sz_pack2 param to unfolded loader
PUSH {r4} // 5th param to decompressor
mov r10,lr // DEBUG ONLY
blx r5 // bx r5
bx r10 // DEBUG ONLY
main:
mov r5,lr // &f_decompress
bl unfold
L100:
/* { b_info={sz_unc, sz_cpr, {4 char}}, folded_loader...} */
GAP= 128 // > farthest prefetch; must match ../../p_mach.cpp
NO_LAP= 64 // avoid overlap for folded loader; must match ../../p_mach.cpp
/*
vi:ts=8:et:nowrap
*/
+286
View File
@@ -0,0 +1,286 @@
// arm-darwin.macho-fold.S -- linkage to C code to process Mach-O binary
//
// This file is part of the UPX executable compressor.
//
// Copyright (C) 2000-2008 John F. Reiser
// 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>
//
// John F. Reiser
// <jreiser@users.sourceforge.net>
//
//#define SIMULATE_ON_DEBIAN_EABI4 1
#undef SIMULATE_ON_DEBIAN_EABI4
#ifdef SIMULATE_ON_DEBIAN_EABI4 /*{*/
#define LINUX_ARM_CACHEFLUSH 1 /* SIMULATE_ON_DEBIAN_EABI4 */
#define ARMEL_EABI4 1 /* SIMULATE_ON_DEBIAN_EABI4 */
#else /*}{ USUAL case */
#define DARWIN_ARM_CACHEFLUSH 1
#define ARMEL_DARWIN 1
#endif /*}*/
#include "arch/arm/v5a/macros.S"
sz_l_info = 12
sz_p_info = 12
sz_b_info = 12
sz_unc= 0
sz_cpr= 4
b_method= 8
// control just falls through, after this part and compiled C code
// are uncompressed.
fold_begin:
/* In:
r11= &sz_pack2; follows compressed program {l_info; p_info; b_info; data...}
r5= f_decompress
sp/ junk1,junk2,{15 original regs (omit sp)},junk3,original_stack...
*/
ldr r1,[r11] // sz_pack2
add r7,sp,#4*(2+(16-1)) // &junk3; will become &mhdrp
sub r0,r11,r1 // &{l_info; p_info; b_info}
ldr r3,[r0,#sz_unc + sz_l_info + sz_p_info] // sz_unc of Mach_header
cmp r3,#(1<<13)
movls r3,#(1<<13) // at least 8KiB
sub sp,sp,r3 // alloca
mov r2,sp // Mach_header *tmp
adr r6,f_unfilter
stmdb sp!,{r5,r6,r7}
bl upx_main // (r0=l_info *, r1=sz_compressed, r2=Mach_header *tmp,
// r3=sz_mhdr, f_decompress, f_unfilter, Mach_header **)
ldr r0,[r0,#15*4] // entry: ((Mach_ARM_thread_state const *)dyld)->pc
sub sp, r7,#4*(16-1) // unalloca; keep 15 original registers and mhdrp
str r0,[r7,#-4] // .r15= entry
ldmia sp!,{r0-r12,r14,r15} // restore original registers; goto dynamic linker
f_unfilter: // (char *ptr, uint len, uint cto, uint fid)
ptr .req r0
len .req r1
cto .req r2 // unused
fid .req r3
t1 .req r2
t2 .req r3
#ifndef FILTER_ID /*{*/
#define FILTER_ID 0x50 /* little-endian */
#endif /*}*/
and fid,fid,#0xff
cmp fid,#FILTER_ID // last use of fid
movne pc,lr // no-op if not filter 0x50
movs len,len,lsr #2 // word count
cmpne ptr,#0
moveq pc,lr // no-op if either len or ptr is 0
top_unf:
sub len,len,#1
ldr t1,[ptr,len,lsl #2]
and t2,t1,#0x0f<<24
cmp t2, #0x0b<<24; bne tst_unf // not 'bl' subroutine call
and t2,t1,#0xff<<24 // all the non-displacement bits
sub t1,t1,len // convert to word-relative displacement
bic t1,t1,#0xff<<24 // restrict to displacement field
orr t1,t1,t2 // re-combine
str t1,[ptr,len,lsl #2]
tst_unf:
cmp len,#0
bne top_unf
mov pc,lr
.unreq ptr
.unreq len
.unreq cto
.unreq fid
spin: .globl spin
ret
__NR_exit = 1 + __NR_SYSCALL_BASE
__NR_read = 3 + __NR_SYSCALL_BASE
__NR_write = 4 + __NR_SYSCALL_BASE
__NR_open = 5 + __NR_SYSCALL_BASE
__NR_close = 6 + __NR_SYSCALL_BASE
__NR_brk = 45 + __NR_SYSCALL_BASE
__NR_mmap = 197 + __NR_SYSCALL_BASE
__NR_munmap = 73 + __NR_SYSCALL_BASE
__NR_mprotect = 74 + __NR_SYSCALL_BASE
__NR_pread = 153 + __NR_SYSCALL_BASE
#ifdef SIMULATE_ON_DEBIAN_EABI4 /*{*/
__NR_mmap = 192 + __NR_SYSCALL_BASE // mmap2
__NR_munmap = 91 + __NR_SYSCALL_BASE
__NR_mprotect = 125 + __NR_SYSCALL_BASE
__NR_pread = 180 + __NR_SYSCALL_BASE
#endif /*}*/
.globl exit
exit:
do_sys __NR_exit
.globl read
read:
do_sys __NR_read; ret
.globl write
write:
do_sys __NR_write; ret
.globl open
open:
do_sys __NR_open; ret
.globl close
close:
do_sys __NR_close; ret
.globl brk
brk:
do_sys __NR_brk; ret
.globl munmap
munmap:
do_sys __NR_munmap; ret
.globl mprotect
mprotect:
do_sys __NR_mprotect; ret
.globl mmap
mmap:
#ifdef SIMULATE_ON_DEBIAN_EABI4 /*{*/
stmdb sp!,{r4,r5}
ldr r5,[sp,#3*4] // off_t
ldr r4,[sp,#2*4] // fd
movs r12,r5,lsl #(32-12); bne mmap_frag // lo 12 bits of offset
mov r5,r5,lsr #12 // convert to page number (avoid 64-bit argument)
do_sys __NR_mmap
mmap_ret:
ldmia sp!,{r4,r5}
ret
mmap_frag:
EINVAL=22
mov r0,#-EINVAL // offset not a multiple of page size
b mmap_ret
#else /*}{ USUAL case */
mov ip,sp
stmdb sp!,{r4,r5,r6}
ldmia ip ,{r4,r5 /*,r6*/}
mov r6,#0 // XXX: convert 32-bit unsigned off_t to 64-bits
do_sys __NR_mmap
ldmia sp!,{r4,r5,r6}
ret
#endif /*}*/
.globl pread
pread:
#ifdef SIMULATE_ON_DEBIAN_EABI4 /*{*/
stmdb sp!,{r4,r5} // EABI4 wants 64-bit off_t in even,odd register pair
mov r4,r3 // 32-bit off_t
mov r5,#0 // hi bits of 64-bit off_t
do_sys __NR_pread
ldmia sp!,{r4,r5}
ret
#else /*}{ USUAL case */
str r4,[sp,#-4]! // PUSH r4
mov r4,#0 // convert 32-bit unsigned off_t in r3 to 64 bits in (r3,r4)
do_sys __NR_pread
ldr r4,[sp],#4 // POP r4
ret
#endif /*}*/
.globl bswap
bswap:
mov ip, #0xff
orr ip,ip,#0xff<<16 // ip= 0x00ff00ff
b bswap9
bswap0:
ldr r2,[r0] // r2= A B C D
and r3,ip,r2 // r3= 0 B 0 D
and r2,ip,r2,ror #24 // r2= 0 C 0 A
orr r2,r2,r3,ror # 8 // r2= D C B A
str r2,[r0],#4
bswap9:
subs r1,r1,#4
bge bswap0
ret
#if 0 /*{ "gcc-3.4 -fPIC" botches string constants when code moves! */
.globl STR_0x
STR_0x:
mov r0,pc; mov pc,lr
.asciz "0x"
.balign 4
.globl STR_hex
STR_hex:
mov r0,pc; mov pc,lr
.asciz "0123456789abcdef"
.balign 4
.globl STR_xread
STR_xread:
mov r0,pc; mov pc,lr
.asciz "xread %p(%x %p) %p %x\n"
.balign 4
.globl STR_unpackExtent
STR_unpackExtent:
mov r0,pc; mov pc,lr
.asciz "unpackExtent in=%p(%x %p) out=%p(%x %p) %p %p\n"
.balign 4
.globl STR_make_hatch_arm
STR_make_hatch_arm:
mov r0,pc; mov pc,lr
.asciz "make_hatch_arm %p %x\n"
.balign 4
.globl STR_auxv_up
STR_auxv_up:
mov r0,pc; mov pc,lr
.asciz "auxv_up %p %x %x\n"
.balign 4
.globl STR_xfind_pages
STR_xfind_pages:
mov r0,pc; mov pc,lr
.asciz "xfind_pages %x %p %d %p\n"
.balign 4
.globl STR_do_xmap
STR_do_xmap:
mov r0,pc; mov pc,lr
.asciz "do_xmap fdi=%x ehdr=%p xi=%p(%x %p) av=%p p_reloc=%p f_unf=%p\n"
.balign 4
.globl STR_upx_main
STR_upx_main:
mov r0,pc; mov pc,lr
.asciz "upx_main av=%p szc=%x f_dec=%p f_unf=%p xo=%p(%x %p) xi=%p(%x %p) dynbase=%x\n",
.balign 4
#endif /*}*/
// vi:ts=8:et:nowrap