Writeup Reto 6 – CyberOlympics

Cuando acabaron la previa del CTF de Cyberolympics mis antiguos compañeros del IES Fidiana, me pasaron los retos para que les echara un vistazo.

Uno de los retos era de reversing y realmente no me había enfrentado a ningún reto así, así que me puse a ello y de paso aprender algo de reversing.

Enunciado

Un conocido fabricante de ATM (cajeros automáticos) quiere implantar un sistema de seguridad con clave de manera que, aunque un técnico malicioso obtenga el software, no pueda obtener la clave original. Como están tan seguros de que es imposible, nos han dado una copia del programa que realiza el filtro para que la auditemos. Debemos averiguar cuál es la contraseña válida que acepta el programa.

Writeup

En este reto nos encontramos primero con un binario de linux. Lo primero lanzamos el comando file para ver a qué nos estamos enfrentando.

Como vemos es un elf de 64 bits linkeado dinámicamente. Ahora vamos a probar el programa en sí para ver la lógica de funcionamiento.

Como vemos cuando lo ejecutamos nos pide una contraseña pasandosela por un argumento y si es incorrecta nos dice que la contraseña no es válida.

Viendo los strings del binario podemos deducir que cuando introduzcamos una contraseña correcta nos devolverá congratulations! flag{%s}.

Visto esto procedemos a debuggearlo con gdb (En mi caso tengo instalado también peda).

Si hacemos un disass del main vemos esto:

Tras un rato viendo como funciona, llegamos a la conclusión que en main+202 se hace la comparación de memoria donde previsiblemente se comparen las contraseñas.

0x00000000000019f1 <+202>:   call 0x1070 <[email protected]>

Por lo que ponemos un breakpoint en esa dirección y ejecutamos el programa.

Y ejecutamos el programa pasándole por parámetro por ejemplo AAAAAAA.

Lo que podemos ver cuando hace el breakpoint es esto:

Lo que resulta bastante extraño es que podamos ver la cadena que hemos pasado por parámetro y no vemos con qué lo está comparando.

Tras unos días sin conseguir nada me dijeron una de las pistas: se usaba MD5. Entonces se me iluminó la bombilla.

En esta comparación de memoria se comparan los registros rsi y rdi y casi siempre lo que buscamos está en el rsi por lo que lo mostramos con x/16bx $rsi.

Esto significa:

  • x de examine
  • 16 (el número de bytes a mostrar)
  • b (de byte, el tipo de datos que manejamos)
  • x de (hexadecimal)

Que es diciéndole a gdb, examíname 16 bytes en hexadecimal.

Ahora si leemos esto nos daría el hash c047916474a472d9ce780dcf858ef7cb.

Lo primero que hacemos es buscarlo en google y vemos que en un foro ruso lo han crackeado.

Se ve que un usuario lo pidió y lo han crackeado.

Y ahora si introducimos eso en el programa, nos lo valida como la contraseña correcta por lo que tenemos la flag.

¡Un saludo!

local_offerevent_note febrero 18, 2019

account_box Rafael Sojo


local_offer

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *