in the name of zero

December 25, 2006

season’s greetings

Maligayang pasko! Froehliche Weihnachten! kurisumasu omedeto! Sung Tan Chuk Ha! Kung His Hsin Nien bing Chu Shen Tan!

happy birthday jesus.

December 22, 2006

elf magic : elf auxiliary vectors

i’ve always wondered what the last line is for… note the [vdso] line in the maps file below:

misha@heaven ~/git/null/asm/vsyscall $ cat /proc/`pidof old`/maps
08048000-08049000 r-xp 00000000 03:01 21633      /home/misha/git/null/asm/vsyscall/old
08049000-0804a000 rwxp 00000000 03:01 21633      /home/misha/git/null/asm/vsyscall/old
bf7f5000-bf80a000 rwxp bf7f5000 00:00 0          [stack]
ffffe000-fffff000 —p 00000000 00:00 0          [vdso]

tonight, i finally stumbled upon something that sheds some light on the subject matter at hand. vdso is short for “virtual dynamic shared object“, and this page is being set up by the kernel as system call entry/exit points for user processes. a sysenter based system call mechanism.

; /usr/include/elf.h
%define AT_NULL         0               ;  /* End of vector */
%define AT_SYSINFO      32
	
        global _start
section .text
_start
        lea edi, [esp+4]        ; argv[0]
        mov eax, [esp]          ; int argc
        lea eax, [eax*4+4]
        add edi, eax            ; envp[0]
	
stage1
        mov eax, [edi]
        test eax, eax
        jz stage2
        add edi, 4
        jmp stage1
	
stage2
	add edi, 4
	mov eax, [edi]		; Elf32_auxv_t -> a_type
	cmp eax, AT_SYSINFO
	je SYSINFO_FOUND
	add edi, 4
	test eax, eax
	jnz stage2
	
	mov eax, 1
	xor ebx, ebx
	int 0x80  
	
SYSINFO_FOUND
        mov eax, [edi+4]                ; Elf32_auxv_t -> a_un
        push eax
	
        xor eax, eax
        inc al
        inc bl
        shl eax, 2
        mov ecx, banner
        mov edx, (ebanner-banner)
	
        call [esp]
	
        xor eax, eax
        xor ebx, ebx
        inc eax
        call [esp]
	
section .data
        banner  db "Merry Christmas!", 0xa, 0x0
        ebanner

or you can just cut all that overhead of searching past the stack for the aux vectors and look at System.map

misha@heaven ~ $ grep -i kernel_vsyscall /boot/System.map
ffffe400 A __kernel_vsyscall

references:

[1] http://manugarg.googlepages.com/systemcallinlinux2_6.html
[2] http://manugarg.googlepages.com/aboutelfauxiliaryvectors
[3] http://www.win.tue.nl/%7Eaeb/linux/lk/lk-4.html

colorizing mamon’s gdbinit

i doubt anyone will find this enhancement particularly useful. i simply just colorized the “context” output to increase readability and added a user-defined instruction “bhb” which is just a wrapper around the “hb” instruction.

some screenshots:
this is the original gdbinit[1] and here’s the colorized[2] one im using.

update:
patched[3] by zhang le

[1] http://www.eccentrix.com/members/mammon/gdb_init.txt
[2] get [3] instead
[3] http://www.esnips.com/doc/34523412-65b8-433e-ae75-cc0a46d65818

December 21, 2006

DVL

Damn Vulnerable Linux R1 on the stalls people. also get your playthings at crackmes.de. ciao.

December 12, 2006

finding ctors

so i encountered a crackme that does a PTRACE_TRACEME and checks to see if LD_PRELOAD is set.

if we try putting a breakpoint in main, we notice that the crackme quits sometime before actually hitting main(), thus the breakpoint doesn’t get to resolve. same results when we try ptrace hijacking. we can conclude that before the crackme’s main() function, a routine (or some routines) are being executed. these routines happen to be called “constructors” and they are found at section .ctors

they are made by using the gcc “constructor” function attribute[1]. for destructors, the function attribute “destructors” is used. the problem is, the crackme author modified the elf header in such a way that it’s impossible for some tools (objdump in particular) to view the program’s internals like the disassembly and section informations (like ctors)

misha@heaven ~/rccrackme $ objdump -s -j .ctors rccracker
	
rccracker:     file format elf32-i386

so we basically need to find the program’s ctors and see if there are other stuffs it does besides just detecting “tracing” and “ptrace wrappers”. there are some ways of approaching this and the first and most obvious would be to reconstruct the relevant elf sections of the crakme needed for “bsd based” tools like objdump to work. but this requires tedious analysis and binary patching. the second way is if we can find the location of ctors just by following the standard libc start up.

so we’re basically familiar with how libc gives control to main()… in _start[2], a few arguments are being pushed including the main() functions address, then finally, a call to _libc_start_main()[3]. libc_start_main() basically calls the “constructors”, main(), then “destructors” in that order.

so how do we reach the constructors that are get executed? i tried making another program that calls a simple constructor then followed the disassembly listing to _do_global_ctors_aux(). the flow goes…

(note: i followed this on a dynamic linked hello world program)

_start[2] --> __libc_start_main[3] --> __libc_csu_init[4] --> _init[5] --> _libc_global_ctors[6]

so what i did was to trace the crackme disassembly till i reach the address of libc_global_ctors[6] which is at 0x080487C8. it initilizes a pointer to a register and enters a loop calling each ((contructor)) function, so the first addresss it calls must be the first “constructor” function.. i followed the default “call eax” to the address 0x08048654. and there, i found the crackme calling “something” thru the dynamic linker, possibly, getenv(), i can only guess since the return value is a char* to the value assigned to LD_PRELOAD.

then a few instructions further, a call to the check_ptrace(int x) i want to get over.

LOAD:080486A6                mov	[esp], 68h	; succeeding function accepts an argument
LOAD:080486AD                call	sub_8048630	; our ptrace_check() function

— following the call —

LOAD:08048630 arg_0           = dword ptr  4
LOAD:08048630
LOAD:08048630                 mov	eax, [esp+arg_0]	; eax = 0x68
LOAD:08048634                 push	ebx			; save ebx
LOAD:08048635                 xor	ecx, ecx		; ecx = 0
LOAD:08048637                 push	ecx			; save ecx
LOAD:08048638                 shr	eax, 2			; eax = 0x1a = sys_ptrace
LOAD:0804863B                 pop	edx			; edx = 0
LOAD:0804863C                 mov	ebx, ecx		; ebx = 0
LOAD:0804863E                 push	ebx			; zero on stack
LOAD:0804863F                 pop	esi			; esi = 0
LOAD:08048640                 mov	edi, esi		; edi = 0
LOAD:08048642                 inc	esi			; esi = 1
LOAD:08048643                 int	80h			; call kernel
LOAD:08048645                 test	eax, eax		; did ptrace fail?
LOAD:08048647                 jge	short loc_8048650	; NO! great!
LOAD:08048649                 add	eax, 2			; (-1) + 2 = 1
LOAD:0804864E                 int	80h			; call sys_exit
LOAD:08048650
LOAD:08048650 loc_8048650:
LOAD:08048650                 pop     ebx			; restore former ebx value
LOAD:08048651                 retn				; return

from this point on, it’s just a matter of changing the return value of sys_ptrace(). put a breakpoint in 0x08048645. and change eax to from 0xffffffff to 0 to defeat the ptrace_check().

misha@heaven ~/rccrackme $ gdb rccracker
(no debugging symbols found)
Using host libthread_db library \"/lib/libthread_db.so.1\".
	
niel@gdb $ hb *0x08048645
Hardware assisted breakpoint 1 at 0x8048645
	
niel@gdb $ r
warning: shared library handler failed to enable breakpoint
(no debugging symbols found)
Error while running hook_stop:
Invalid type combination in ordering comparison.
	
Breakpoint 1, 0x08048645 in ?? ()
niel@gdb $ set $eax = 0
	
niel@gdb $ continue
--===[> Macabre's rc CrackMe <]===--
	
Program exited normally.

assuming this is the only anti-debugging trick employed in the crackme, we can now “gdb step” our way through completion.

[1] http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html
[2] sysdeps/i386/elf/start.S
[3] sysdeps/generic/libc-start.c :: STATIC int LIBC_START_MAIN ()
[4] csu/elf-init.c :: void __libc_csu_init ()
[5] sysdeps/i386/init-first.c :: void _init()
[6] elf/soinit.c :: __libc_global_ctors ()

December 5, 2006

gtk thru a lens

here’s the scenario.

i encountered a linux crackme today that employs a gui. my first time. the most obvious difference, (of course,) between a console and a GUI program would be the fact that one of them has a GUI and one doesn’t. a gui program has the added workload of “constructing” a gui along with the processing of data. in the same manner, if we look at a GUI program’s disassembly, we must isolate the “data processing” specific parts from the parts that take care of guifications.

running the crackme, it displayed a window, with a text “Kill this window (patch file)…”. there was no other button than the standard title bar buttons minimize, restore and quit, so i pressed quit. a new window appeared this time, with text entries and some button. i filled the text entries with some letters then pressed the “CrackMe” button, only to be greeted by “BAD KEY :p BAD cracker BAD :p”

now, although i _could_ deduce the toolset used for the gui based on the look n feel alone, i had to make sure on things…

misha@heaven ~/veneta $ file cm2
cm2: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), for GNU/Linux 2.2.5,
dynamically linked (uses shared libs), stripped

dyn-linked, but stripped. i wonder what libs it was using….

misha@heaven ~/veneta $ readelf -d cm2 | grep -i .so
 0x00000001 (NEEDED)                     Shared library: [libgtk-1.2.so.0]
 0x00000001 (NEEDED)                     Shared library: [libgdk-1.2.so.0]
 0x00000001 (NEEDED)                     Shared library: [libglib-1.2.so.0]
 0x00000001 (NEEDED)                     Shared library: [libc.so.6]

libgtk, libgdk, libglib gave things away. so i’m definitely looking at a gtk-1.2 crackme. at address 0x0404898D, things started becoming interesting. it copied the address of a string to esi, then called a function, which i later discovered was the nagscreen. following the call to the function in question, i saw the typical frame setup, then this:

 8048dfc:       68 01 00 00 00          push   0x1				; GTK_WINDOW_DIALOG
 8048e01:       e8 ba f9 ff ff          call   80487c0 <gtk_window_new@plt>	; gtk_window_new()
 8048e06:       a3 a0 a3 04 08          mov    ds:0x804a3a0,eax			; nag_screen_window GtkWidget *
	
gtk-1.2/gtk/gtkwindow.h :: GtkWidget* gtk_window_new(GtkWindowType type);
gtk-1.2/gtk/gtkwindow.h :: typedef enum { } GtkWindowType;

then it sets the window title like so:

 8048e0b:       68 2c a0 04 08          push   0x804a02c			; address of title string
 8048e10:       ff 35 a0 a3 04 08       push   ds:0x804a3a0			; nag screen window GtkWidget *
 8048e16:       e8 c5 f9 ff ff          call   80487e0 <gtk_window_set_title@plt>	; gtk_window_set_title()
	
gtk-1.2/gtk/gtkwindow.h :: void gtk_window_set_title(GtkWindow *window, const gchar *title);

then it creates a label widget using the string passed to esi before….

 8048e1b:       56                      push   esi				; "Kill this window (patch file)..."
 8048e1c:       e8 8f f9 ff ff          call   80487b0 <gtk_label_new@plt>
	
gtk-1.2/gtk/gtklabel.h :: GtkWidget* gtk_label_new (const gchar *str); 

and adds the newly created label widget to the nag screen window.

 8048e21:       50                      push   eax				; label GtkWdiget *
 8048e22:       ff 35 a0 a3 04 08       push   ds:0x804a3a0			; nag screen window GtkWidget *
 8048e28:       e8 63 f9 ff ff          call   8048790 <gtk_container_add@plt>	; gtk_container_add();
	
gtk-1.2/gtk/gtkcontainer.h :: void gtk_container_add(GtkContainer *container, GtkWidget *widget);

the nagscreen window is being typecasted to a GtkContainer structure. (consult the GTK widget Hierarchy) which is how GTK implements classes and and inheritance using C. it roughly goes…

GtkObject <- GtkWidget <- GtkContainer <- GtkBin <- GtkWindow

finally, the nag screen window is given a default size, gtk_window_set_default_size() and then is being displayed via call to gtk_widget_show_all().

the function returns and then a signal is being setup for the destroy signal. with the callback to a function that draws the new “main window”. this is why when i pressed the “x” button on the nagscreen, a new window pops up that holds the user input entries and buttons.

 8048997:       68 00 00 00 00          push   0x0			; NULL
 804899c:       68 bd 89 04 08          push   0x80489bd		; crackme_main_screen()
 80489a1:       68 28 a2 04 08          push   0x804a228		; "destroy"
 80489a6:       ff 35 a0 a3 04 08       push   ds:0x804a3a0		; crackme_nagscreen
 80489ac:       e8 cf fe ff ff          call   8048880 <gtk_signal_connect@plt>
	
gtk-1.2/gtk/gtksignal.h :: guint gtk_signal_connect(GtkObject *object,
						const gchar *name,
						GtkSignalFunc func,
						gpointer func_data);

well, that’s it. my first few fun-filled moments studying the gtk crackme.

December 4, 2006

macabre’s frogger crackme lvl 2

macabre’s frogger crackme lvl 2
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-

Restrictions: NO patching. No Hijacking

Goal: Find User/Key pair to make it print ‘Cracked!!’

Notes: No anti-debugging code.

Jump Jump ..oo ribbet oo…

Difficulty: 2 - Needs a little brain (or luck)
Platform: Unix/linux etc.
Language: Assembler

get it here
(more…)

December 3, 2006

cyrex’s Easy Math Keygenme

crackme is packed , symbol table is missing , no anti debug
- make a keygen (mhh)
- find a valid name/serial pair (easy)
- No Patching.

have fun

Difficulty: 2 - Needs a little brain (or luck)
Platform: Unix/linux etc.
Language: C/C++

get it here
(more…)

December 1, 2006

library fingerprinting

stripped static-linked crackmes have always been a pain for me (i suppose for other reversers as well). there have been attempts to address the problem of a) restoring the stripped symbols in binaries b) identification of function during disassembly.

[ fenris ]

a well known example is the dress utility found in michal zalewski’s project fenris. (new homepage) portage has it but i still haven’t been able to succesfully compile it. see fenris gentoo bugzilla entry.

the idea is simple. create a fingerprint database of a particular (unstripped) ‘library’ and run a comparison of the binary in question against this database, identifying what belongs to whom. (standard library or user supplied crap)

[ flair ]

or fast library acquisition for identification and recognition (4.90 at this time of writing), which is offered as a separate “freebie” for ida pro. for the record, i’m using sys-libs/glibc-2.3.4.20041102-r1 and upon generation of the signature file (for libc), it encountered some a collisions… but other than that, the signature seems ok in the end. you can get the signature file here.

[ others ]

this honeynet reverse challenge entry also employed some symbol generation..

Get free blog up and running in minutes with Blogsome | Theme designs available here