hacktricks/network-services-pentesting/pentesting-web/artifactory-hacking-guide.md

196 lines
16 KiB
Markdown
Raw Normal View History

2023-06-05 18:33:24 +00:00
<details>
<summary><a href="https://cloud.hacktricks.xyz/pentesting-cloud/pentesting-cloud-methodology"><strong>☁️ HackTricks Cloud ☁️</strong></a> -<a href="https://twitter.com/hacktricks_live"><strong>🐦 Twitter 🐦</strong></a> - <a href="https://www.twitch.tv/hacktricks_live/schedule"><strong>🎙️ Twitch 🎙️</strong></a> - <a href="https://www.youtube.com/@hacktricks_LIVE"><strong>🎥 Youtube 🎥</strong></a></summary>
- ¿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 la [**oficial PEASS & HackTricks swag**](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 hacktricks](https://github.com/carlospolop/hacktricks) y al [repositorio hacktricks-cloud](https://github.com/carlospolop/hacktricks-cloud)**.
</details>
**Este contenido fue tomado de** [**https://www.errno.fr/artifactory/Attacking\_Artifactory**](https://www.errno.fr/artifactory/Attacking\_Artifactory)
# Conceptos básicos de Artifactory <a href="#artifactory-basics" id="artifactory-basics"></a>
## Usuarios y contraseñas predeterminados <a href="#default-users-and-passwords" id="default-users-and-passwords"></a>
Las cuentas predeterminadas de Artifactory son:
| Cuenta | Contraseña predeterminada | Notas |
| ------------ | ---------------------------------------------- | --------------------------------------------------------------------- |
| admin | password | cuenta de administración común |
| access-admin | password (<6.8.0) o un valor aleatorio (>= 6.8.0) | utilizado solo para operaciones de administración local |
| anonymous | '' | usuario anónimo para recuperar paquetes de forma remota, no habilitado por defecto |
Por defecto, no se aplica ninguna política de bloqueo de contraseñas, lo que convierte a Artifactory en un objetivo principal para ataques de relleno de credenciales y de rociado de contraseñas.
## Autorizaciones <a href="#authorizations" id="authorizations"></a>
Idealmente, esto es lo que debería ver al conectarse a Artifactory:
![Página de inicio de sesión](https://www.errno.fr/artifactory/artif\_login.png)
Por otro lado, si se le presenta algo más parecido a esto:
![Página predeterminada](https://www.errno.fr/artifactory/artif\_default.png)
Significa que se ha habilitado el "Acceso anónimo" en el panel de administración, que es una configuración común utilizada para permitir que las aplicaciones recuperen artefactos sin problemas, pero que le permite a usted, el atacante, ver más de lo que es preferible.
## Comprobación de los derechos de la cuenta <a href="#checking-account-rights" id="checking-account-rights"></a>
¡A veces, debido a una mala configuración, se permite que el usuario anónimo implemente archivos en algunos repositorios!
Para comprobar en qué repositorios puede implementar el usuario anónimo, utilice la siguiente solicitud:
```
curl http://localhost:8081/artifactory/ui/repodata?deploy=true
{"repoList":["artifactory-build-info","example-repo-local"]}
```
Si hay entradas `repoKey` en la solicitud, cualquier persona anónima puede desplegar en ellas, lo cual es realmente malo. Definitivamente, se debe estar autenticado para desplegar cualquier archivo.
Esto se puede generalizar a otras cuentas una vez que se obtiene una contraseña o token para ellas.
## Listado de usuarios <a href="#listing-users" id="listing-users"></a>
Por alguna razón, la lista de usuarios es un derecho reservado solo para los administradores. Encontré una forma alternativa de listar usuarios (aquellos que están desplegando activamente al menos) que se basa en el valor "Desplegado por" de los artefactos:
![Desplegado por](https://www.errno.fr/artifactory/artif\_deployed\_by.png)
[Este script](https://gist.github.com/gquere/347e8e042490be87e6e9e32e428cb47a) simplemente intenta encontrar recursivamente todos los usuarios que han desplegado artefactos. Tenga en cuenta que podría tardar un tiempo en completarse si hay muchos repositorios (>1000).
```
./artifactory_list_users.py http://127.0.0.1:8081/artifactory
There are 23 repositories to process
Found user admin
Found user test
Found user user
Found user test_deploy
```
## Permisos <a href="#permissions" id="permissions"></a>
Aquí están los permisos básicos y su utilidad:
* Manage: ?
* Delete/Overwrite: interesante para pentest
* Deploy/Cache: interesante para pentest
* Annotate: necesario para CVE-2020-7931
* Read: generalmente un permiso predeterminado
# Vulnerabilidades conocidas <a href="#known-vulnerabilities" id="known-vulnerabilities"></a>
Aquí hay una lista seleccionada de vulnerabilidades públicas de alto impacto:
## CVE-2016-10036: Carga de archivo arbitraria y RCE (<4.8.6) <a href="#cve-2016-10036-arbitrary-file-upload--rce-486" id="cve-2016-10036-arbitrary-file-upload--rce-486"></a>
[Detalles aquí.](https://www.exploit-db.com/exploits/44543)
Este es un poco antiguo y es poco probable que te encuentres con una versión tan desactualizada de Artifactory. Sin embargo, es bastante efectivo, ya que es una simple travesía de directorios que permite la ejecución de código arbitrario en el nivel de Tomcat.
## CVE-2019-9733: Bypass de autenticación (<6.8.6) <a href="#cve-2019-9733-authentication-bypass-686" id="cve-2019-9733-authentication-bypass-686"></a>
[Advertencia original aquí.](https://www.ciphertechs.com/jfrog-artifactory-advisory/)
En versiones anteriores de Artifactory (hasta 6.7.3), la cuenta `access-admin` usaba una contraseña predeterminada `password`.
Normalmente, esta cuenta local está prohibida para acceder a la interfaz de usuario o la API, pero hasta la versión 6.8.6, Artifactory podía ser engañado para creer que la solicitud emanaba localmente si se establecía el encabezado HTTP `X-Forwarded-For` en `127.0.0.1`.
## CVE-2020-7931: Inyección de plantillas en el lado del servidor (Artifactory Pro) <a href="#cve-2020-7931-server-side-template-injection-artifactory-pro" id="cve-2020-7931-server-side-template-injection-artifactory-pro"></a>
[Advertencia original aquí.](https://github.com/atredispartners/advisories/blob/master/ATREDIS-2019-0006.md)
Aquí hay una [herramienta que escribí](https://github.com/gquere/CVE-2020-7931) para automatizar la explotación de esta vulnerabilidad.
Estos son necesarios para la explotación:
* un usuario con derechos de implementación (crear archivos) y anotación (establecer filtrados)
* Artifactory Pro
La vulnerabilidad es bastante simple: si un recurso implementado se establece en filtrado, se interpreta como una plantilla de Freemarker, lo que le da al atacante una ventana de ataque SSTI. ![Recurso filtrado](https://www.errno.fr/artifactory/artif_filtered.png)
Aquí están los primitivos implementados:
* lecturas básicas del sistema de archivos
* escrituras limitadas del sistema de archivos
Estos deberían ser suficientes para darle ejecución de código remoto de varias maneras, desde la más fácil/silenciosa hasta la más difícil/ruidosa:
* leyendo un secreto en el sistema de archivos que le permite pivotar (/home/user/.bash\_history, /home/user/password.txt, /home/user/.ssh/id\_rsa …)
* agregando una clave SSH al usuario
* implementando un archivo .war para ejecutar un servlet
* implementando un script de usuario Groovy de Artifactory
### Historias .war: travesuras de Java renameTo() <a href="#war-stories-java-renameto-shenanigans" id="war-stories-java-renameto-shenanigans"></a>
Esta es una pequeña historia de cómo me golpeé la cabeza contra la pared durante horas, si no días, durante una prueba de penetración. Me encontré con una versión desactualizada de Artifactory que sabía que era vulnerable a CVE-2020-7931. Implementé la plantilla SSTI original de la advertencia y comencé a buscar en el sistema de archivos. Parecía que Artifactory se había instalado en una ubicación no estándar, lo que no es demasiado inusual ya que a los administradores les gusta mantener particiones separadas entre binarios de aplicaciones, datos, registros y configuración (¡esto es algo bueno!). No había claves SSH o contraseñas en el directorio principal del usuario que me hubieran proporcionado un pivote fácil, así que llegó el momento de ser menos discreto y escribir en el sistema de archivos. La carga útil inicial (una clave pública) en el directorio de carga de Artifactory fue bien, pero simplemente no pude moverla al directorio de claves SSH. Así que volví a mi sandbox de explotación, lo probé de nuevo y, ¡oh sorpresa!, funcionó bien. Así que tenía que haber una configuración diferente que me impidiera completar el método `renameTo()`. En este punto, siempre es una buena idea [consultar la documentación](https://docs.oracle.com/javase/8/docs/api/java/io/File.html#renameTo-java.io.File-) ... que claramente establece que no se pueden renombrar archivos en diferentes sistemas de archivos, lo que supongo que tiene sentido dependiendo de la implementación del método, es decir, si funciona a nivel de inodo. Arg.
¿Recuerdas lo que dije sobre los administradores que les gustan las particiones? Bueno, ¡este es un caso de un administrador que sin saberlo endureció su configuración contra mi explotación! Así que tuve que profundizar en lo que es esencialmente una cárcel de Java para encontrar otro método que me permitiera escribir un archivo en disco. Y eso no fue divertido en absoluto, ya que no estoy familiarizado con ninguna de las cosas involucradas: plantillas FTL, Java, Tomcat/Catalina. Rápidamente descubrí que las fugas de la cárcel de Java regulares simplemente no funcionarían, ya que instanciar nuevas clases estaba prohibido. Después de horas de leer la documentación de las clases de Java y Catalina, finalmente encontré un método write() en un objeto al que podía acceder. Pero estaba limitado a la ruta base de la aplicación web... Así que luego pensé en combinar la escritura en otro sistema de archivos y el `renameTo()` a través de este sistema de archivos recién alcanzable para, con suerte, poder escribir en cualquier lugar. Y funcionó un poco. Logré escribir fuera del directorio de carga temporal ... pero no tan lejos de él, ya que ahora estaba atrapado en otro sistema de archivos que era el punto de montaje de todas las cosas de Artifactory: configuración, aplicación y cosas. Así que todavía no hay clave SSH para mí.
De acuerdo, podría escribir en la carpeta raíz de Artifactory, ¿seguramente podría hacer algo aquí? Oye, ¿no hace Tomcat por defecto implementar archivos WAR escritos en su ruta de aplicación? Así que usé msfvenom para generar una shell web JSP empaquetada en un archivo WAR y lo probé en mi sandbox... bueno, se implementó correctamente, pero no me dio ejecución de comandos. Parece que el Tomcat predeterminado no maneja los JSP. Ugh. Cada vez más frustrado, busqué otra forma de ejecutar código en Tomcat y encontré otro método de ejecución usando servlets. No pude encontrar una carga útil adecuada, así que jódete, estoy todo adentro en este punto y [desarrollé mi propio método que puedes encontrar aquí](https://github.com/gquere/javaWebShell). Lo probé en el sandbox, funciona, bien. Lo puse en el objetivo, se implementa y... nada. Resulta que había un proxy delante de Artifactory que reescribía todas las URL a /artifactory. Así que aunque mi puerta trasera estaba implementada y funcionando, no había forma de acceder a ella... Si hubiera algún tipo de ejecución de código remoto para lograr en este punto, tendría que estar en el contexto de Artifactory, no de Tomcat.
Al día siguiente, estoy sollozando en mi escritorio mirando por última vez la documentación de Artifactory con la esperanza vana de una epifanía. Y luego aparecieron las palabras mágicas "scripts Groovy". Resulta que hay una forma complicada de ejecutar scripts Groovy, escribiéndolos en disco y luego recarg
```
cat artifactory.hashes
user:1f70548d73baca61aab8660733c7de81${CAFEBABEEBABEFAC}
john artifactory.hashes --format=dynamic_1
Loaded 1 password hash (dynamic_1 [md5($p.$s) (joomla) 256/256 AVX2 8x3])
password (user)
```
El otro tipo de contraseña bcrypt no requiere nada especial, es simplemente un hash bcrypt estándar:
```
cat artifactory_bcrypt.hashes
admin:$2a$08$EbfHSAjPLoJnG/yHS/zmi.VizaWSipUuKAo7laKt6b8LePPTfDVeW
john artifactory_bcrypt.hashes
Loaded 1 password hash (bcrypt [Blowfish 32/64 X2])
password (admin)
```
### Secretos remotos <a href="#remote-secrets" id="remote-secrets"></a>
Artifactory puede necesitar almacenar secretos para identificarse en servicios remotos. Estos secretos no están hashados, por supuesto, se almacenan cifrados en el disco, con la clave junto a ellos. Hay dos tipos de secretos mencionados en la [documentación oficial](https://jfrog.com/knowledge-base/what-are-the-artifactory-key-master-key-and-what-are-they-used-for/).
**Formato antiguo (<5.9): DES-EDE**
TODO. [Abra un problema si tiene datos cifrados de muestra](https://github.com/gquere/ArtifactoryDecryptor).
**Nuevo formato (>=5.9): cifrado AES128-CBC, almacenado como base58**
Los secretos externos (como las contraseñas de los servidores remotos) se encuentran en los [descriptores de configuración](https://www.jfrog.com/confluence/display/JFROG/Configuration+Files#ConfigurationFiles-GlobalConfigurationDescriptor), por ejemplo, `/var/opt/jfrog/artifactory/etc/artifactory.config.latest.xml` y se ven así:
```
<keyStorePassword>AM.25rLQ.AES128.vJMeKkaK6RBRQCUKJWvYEHUw6zs394X1CrRugvJsQGPanhMgQ5be8yjWDhJYC4BEz2KRE</keyStorePassword>
```
Donde:
* `AM` siempre denota un secreto cifrado de Artifactory
* `25rLQ` es el identificador del secreto que debe coincidir con el identificador de la clave
* `AES128` obviamente es el algoritmo utilizado
* `vJMeK...KRE` es la codificación base58 de `IV_SIZE|IV|secret|CRC`
Se pueden encontrar más secretos (tokens, copias de seguridad de configuración...) utilizando la siguiente expresión regular:
```
grep -r 'AM\..*\.AES128\.' /var/opt/jfrog/artifactory/
```
La clave se almacena en `/var/opt/jfrog/artifactory/etc/security/artifactory.key` y tiene este aspecto:
```
JS.25rLQ.AES128.7fcJFd3Y2ib3wi4EHnhbvZuxu
```
Donde:
* `JS` denota una clave
* `25rLQ` es un identificador de clave único que lleva un registro de qué clave puede descifrar qué secretos
* `AES128` es obviamente el algoritmo utilizado
* `7fcJFd3Y2ib3wi4EHnhbvZuxu` es la codificación base58 de la clave y 2 bytes de CRC
Esta herramienta que escribí se puede utilizar sin conexión para descifrar secretos de Artifactory: [ArtifactoryDecryptor](https://github.com/gquere/ArtifactoryDecryptor).
# Defendiendo Artifactory <a href="#defending-artifactory" id="defending-artifactory"></a>
Si eres el equipo azul o un administrador de Artifactory, a estas alturas deberías tener una buena idea de qué hacer:
* mantener Artifactory actualizado, especialmente cuando se emiten actualizaciones críticas
* implementar una política de contraseñas sólida (sin contraseñas predeterminadas, contraseñas fuertes obligatorias, bloqueos), preferiblemente diferido a un LDAP externo para una mejor supervisión
* restringir accesos (respetar el principio de menor privilegio), especialmente para el usuario anónimo