HackIt! Nivel 10: solución detallada

Lo primero que haremos será abrir con objdump el ejecutable ./go, para conocer la dirección
de entrada (saber desde dónde, desde qué dirección de memoria, empieza el programa a ejecutarse):


sh-3.2$ objdump -x ./go
./go: file format elf32-i386
./go
architecture: i386, flags 0x00000102:
EXEC_P, D_PAGED
start address 0x08048f50

Apuntamos la dirección de inicio: 0x08048f50

Necesitamos preparar el terreno un poco más. Vamos a examinar el ejecutable con elfsh:


$ elfsh
> load go

A continuación, dentro de elfsh, pediremos la lista de direcciones de las funciones a
las que llama el juego:


> rel
(elfsh-0.81-a8-dev@local) rel
[RELOCATION TABLES]
[Object go]
{Section .rel.dyn}
[000] R_386_GLOB_DAT 0x0804D488 sym[004] : __gmon_start__ => Create GOT entry
[001] R_386_COPY 0x0804DA40 sym[051] : stderr => Copy symbol at runtime
{Section .rel.plt}
[000] R_386_JMP_SLOT 0x0804D498 sym[001] : XDrawString => Create PLT entry
[001] R_386_JMP_SLOT 0x0804D49C sym[002] : XLookupKeysym => Create PLT entry
[002] R_386_JMP_SLOT 0x0804D4A0 sym[003] : sprintf => Create PLT entry
[003] R_386_JMP_SLOT 0x0804D4A4 sym[004] : __gmon_start__ => Create PLT entry
[004] R_386_JMP_SLOT 0x0804D4A8 sym[006] : XAutoRepeatOff => Create PLT entry
[005] R_386_JMP_SLOT 0x0804D4AC sym[007] : _ZdlPv => Create PLT entry
[006] R_386_JMP_SLOT 0x0804D4B0 sym[008] : XSetTile => Create PLT entry
[007] R_386_JMP_SLOT 0x0804D4B4 sym[009] : XSetClipMask => Create PLT entry
[008] R_386_JMP_SLOT 0x0804D4B8 sym[010] : XSetFont => Create PLT entry
[009] R_386_JMP_SLOT 0x0804D4BC sym[011] : XpmCreatePixmapFromData => Create PLT entry
[010] R_386_JMP_SLOT 0x0804D4C0 sym[012] : XSetFillStyle => Create PLT entry
[011] R_386_JMP_SLOT 0x0804D4C4 sym[013] : __libc_start_main => Create PLT entry
[012] R_386_JMP_SLOT 0x0804D4C8 sym[014] : XCreateSimpleWindow => Create PLT entry
[013] R_386_JMP_SLOT 0x0804D4CC sym[015] : XAutoRepeatOn => Create PLT entry
[014] R_386_JMP_SLOT 0x0804D4D0 sym[016] : XOpenDisplay => Create PLT entry
[015] R_386_JMP_SLOT 0x0804D4D4 sym[017] : gettimeofday => Create PLT entry
[016] R_386_JMP_SLOT 0x0804D4D8 sym[018] : XDrawLine => Create PLT entry
[017] R_386_JMP_SLOT 0x0804D4DC sym[019] : XCloseDisplay => Create PLT entry
[018] R_386_JMP_SLOT 0x0804D4E0 sym[020] : XSetForeground => Create PLT entry
[019] R_386_JMP_SLOT 0x0804D4E4 sym[021] : XFillRectangle => Create PLT entry
[020] R_386_JMP_SLOT 0x0804D4E8 sym[022] : fclose => Create PLT entry
[021] R_386_JMP_SLOT 0x0804D4EC sym[023] : XFreeGC => Create PLT entry
[022] R_386_JMP_SLOT 0x0804D4F0 sym[024] : XDrawRectangle => Create PLT entry
[023] R_386_JMP_SLOT 0x0804D4F4 sym[025] : fopen => Create PLT entry
[024] R_386_JMP_SLOT 0x0804D4F8 sym[026] : XNextEvent => Create PLT entry
[025] R_386_JMP_SLOT 0x0804D4FC sym[027] : XMapWindow => Create PLT entry
[026] R_386_JMP_SLOT 0x0804D500 sym[028] : _Znwj => Create PLT entry
[027] R_386_JMP_SLOT 0x0804D504 sym[029] : select => Create PLT entry
[028] R_386_JMP_SLOT 0x0804D508 sym[030] : XCreateGC => Create PLT entry
[029] R_386_JMP_SLOT 0x0804D50C sym[031] : fwrite => Create PLT entry
[030] R_386_JMP_SLOT 0x0804D510 sym[032] : XSelectInput => Create PLT entry
[031] R_386_JMP_SLOT 0x0804D514 sym[033] : XFlush => Create PLT entry
[032] R_386_JMP_SLOT 0x0804D518 sym[034] : XTextWidth => Create PLT entry
[033] R_386_JMP_SLOT 0x0804D51C sym[035] : XChangeGC => Create PLT entry
[034] R_386_JMP_SLOT 0x0804D520 sym[036] : XCopyColormapAndFree => Create PLT entry
[035] R_386_JMP_SLOT 0x0804D524 sym[037] : XLoadQueryFont => Create PLT entry
[036] R_386_JMP_SLOT 0x0804D528 sym[038] : XParseColor => Create PLT entry
[037] R_386_JMP_SLOT 0x0804D52C sym[039] : XAllocColor => Create PLT entry
[038] R_386_JMP_SLOT 0x0804D530 sym[040] : puts => Create PLT entry
[039] R_386_JMP_SLOT 0x0804D534 sym[041] : XSetStandardProperties => Create PLT entry
[040] R_386_JMP_SLOT 0x0804D538 sym[042] : XFreePixmap => Create PLT entry
[041] R_386_JMP_SLOT 0x0804D53C sym[043] : fread => Create PLT entry
[042] R_386_JMP_SLOT 0x0804D540 sym[044] : XCreatePixmap => Create PLT entry
[043] R_386_JMP_SLOT 0x0804D544 sym[055] : __gxx_personality_v0 => Create PLT entry
[044] R_386_JMP_SLOT 0x0804D548 sym[045] : _Unwind_Resume => Create PLT entry
[045] R_386_JMP_SLOT 0x0804D54C sym[046] : XSetWindowColormap => Create PLT entry
[046] R_386_JMP_SLOT 0x0804D550 sym[047] : XPending => Create PLT entry

Conviene fijarse en algunas funciones como: sprintf, fopen, fread, fclose…
En un post anterior vimos que el ejecutable busca un fichero desde el que leer el serial number, así que
saber dónde se hace un fopen/fread/fclose es sumamente interesante 😉

Ahora que tenemos unas pequeñas ayudas con las direcciones de esas funciones, y sabemos dónde poner
el primer punto de ruptura, podemos empezar a depurar con GDB:
Sigue leyendo HackIt! Nivel 10: solución detallada

HackIt! Nivel 10: 0wn3d !

Me pongo a escribir el tutorial dentro de unos días. Ahora voy a tomarme un descanso, porque este nivel me ha hecho perder algunas horas de sueño 😉 Para el que esté liado con este nivel del demonio, algunas pistas: elfsh es tu amigo.

Comandos clave en GDB:

ignore breakpoint saltos

set {int}0xdireccion = valor

jump *0xdireccion

disable breakpoint

info breakpoints

x/15x 0xdireccion

Configuración GDB para ingeniería inversa

La potencia de GDB como debugger, así como sus funcionalidades, son enormes. Sin embargo, el interfaz de usuario de GDB es bastante espartano, austero (sobre todo si lo comparamos con otros debuggers para Windows, como OllyDBG, por ejemplo). Si quieres desentrañar código en ensamblador por técnicas de ingeniería inversa con la ayuda del interfaz por defecto de GDB, vas a notar en tus propias carnes esa austeridad. ¿No se podría tener algo más amigable y usable que el interfaz de GDB pero con la misma potencia del debugger de GNU? Pues sí, existe la posibilidad de hacer algo de «tuning». Se hace a través del fichero de configuración .gdbinit que guardaremos en nuestro directorio $HOME. Y en concreto, existe un ejemplo de configuración llamado Mamon’s GDBINIT especialmente orientado para los hackers (en sus dos acepciones) de la ingeniería inversa.

Podéis apreciar que ahora, cada vez que ejecutemos una instrucción en GDB, se nos mostrará el estado de los registros, de la pila, de la sección de datos y el contexto de código en ensamblador en el que nos movemos. Impresionante y, una vez que lo conoces, indispensable. Rizando el rizo, el blog «in the name of zero», publicó hace tiempo ya una versión del Mamon’s gdbinit , añadiéndole coloreado. Ahora sí podremos depurar código como $DEITY manda…

HackIt Nivel 10: reverse engineering

Tras seguir las pistas dadas en los anteriores posts sobre el HackIt Nivel 9 (léanse también los comentarios), llegamos al fatídico nivel 10. Aquí nos quedamos cuando sonó el ¡gong! del GAME OVER 😉 A primera vista la cosa no pinta muy bien, dado que tras descargar el zip y descomprimirlo, vemos que efectivamente se trata del juego Breakout, por lo que dice el «enunciado» de la pista y por las librerías gráficas que carga:


[juanan@localhost game]$ ldd go
linux-gate.so.1 => (0x00110000)
libXpm.so.4 => /usr/lib/libXpm.so.4 (0x02216000)
libX11.so.6 => /usr/lib/libX11.so.6 (0x00a6e000)
libstdc++.so.6 => /usr/lib/libstdc++.so.6 (0x061ea000)
libm.so.6 => /lib/libm.so.6 (0x004bb000)
libgcc_s.so.1 => /lib/libgcc_s.so.1 (0x002aa000)
libc.so.6 => /lib/libc.so.6 (0x00360000)
libxcb-xlib.so.0 => /usr/lib/libxcb-xlib.so.0 (0x00bcc000)
libxcb.so.1 => /usr/lib/libxcb.so.1 (0x00bae000)
libdl.so.2 => /lib/libdl.so.2 (0x004e6000)
/lib/ld-linux.so.2 (0x00341000)
libXau.so.6 => /usr/lib/libXau.so.6 (0x00639000)
libXdmcp.so.6 => /usr/lib/libXdmcp.so.6 (0x0063e000)

pero, si analizamos el tipo de fichero:

[juanan@localhost game]$ file go
go: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), for GNU/Linux 2.6.8, dynamically linked (uses shared libs), corrupted section header size

vemos que es un fichero ejecutable ELF para Linux, y ¡ojo al parche!, las cabeceras están manipuladas (corrupted section header size) :-O Me temo que a GDB no le gustará nada de nada…


[juanan@localhost game]$ gdb go
GNU gdb Red Hat Linux (6.6-45.fc8rh)
(no debugging symbols found)


Pues vaya… no hay tabla de símbolos, así que ¿cómo indicar los puntos de ruptura? ¿cómo depurar el programa? Os dejo con el reto, y os animo a proponer vías de solución en los comentarios. Yo voy a por un café y cumplimentar papeleos de la universidad…

Hackit! 2007: Nivel 9, espiando conversaciones VoIP

Lo primero que vemos al entrar en el nivel 9 es la posibilidad de descargarnos un fichero .zip que incluye un único fichero tampering.cap . El propio Linux nos indica de qué se trata:

sh-3.2$ file tampering.pcap
tampering.pcap: tcpdump capture file (little-endian) - version 2.4 (Ethernet, capture length 65535)

Una captura de tráfico hecha con tcpdump. Vamos a darle un poco de trabajo a Wireshark (ex-Ethereal), mediante el comando

$ wireshark tampering.cap

Vemos en la columna Protocol que aparte de ARP, aparece el acrónimo SIP (Session Initiation Protocol), o sea, «protocolo de iniciación, modificación y finalización de sesiones interactivas de usuario donde intervienen elementos multimedia como el video, voz…» (Wikipedia dixit) ¿Han capturado tramas de voz? Menos mal que me he traído los auriculares 🙂 También veo tramas RTP (Real-time Transport Protocol, que define un formato para el transporte de audio y video sobre Internet)… veamos qué tenemos en Wireshark al respecto…

Varias opciones del menú se relacionan con SIP, RTP y llamadas de voz. Por medio de la vieja táctica de «prueba y error» 😉 llegamos a la opción «VoIP Calls». Nos sale esta pantalla:

Pulsamos en Player y obtenemos:

Esto parece una matrioska 🙂 Veamos… si pulsamos en «Decode».

Esto tiene muy buena pinta. Pónte los cascos, pulsa «Play» y escucha la conversación… mañana seguiremos con la resolución del misterio (inténtalo por tu cuenta, ¡hombre!)