GCP - Network Docker Escape

Apoya a HackTricks

Estado Inicial

En ambos informes donde se especifica esta técnica, los atacantes lograron obtener acceso root dentro de un contenedor Docker gestionado por GCP con acceso a la red del host (y las capacidades CAP_NET_ADMIN y CAP_NET_RAW).

Explicación del Ataque

En una instancia de Google Compute Engine, la inspección regular del tráfico de red revela numerosas solicitudes HTTP en texto plano al metadata instance en 169.254.169.254. El Google Guest Agent, un servicio de código abierto, realiza frecuentemente tales solicitudes.

Este agente está diseñado para monitorear cambios en los metadatos. Notablemente, los metadatos incluyen un campo para claves públicas SSH. Cuando se agrega una nueva clave pública SSH a los metadatos, el agente la autoriza automáticamente en el archivo .authorized_key. También puede crear un nuevo usuario y agregarlo a sudoers si es necesario.

El agente monitorea cambios enviando una solicitud para recuperar todos los valores de metadatos de forma recursiva (GET /computeMetadata/v1/?recursive=true). Esta solicitud está diseñada para solicitar al servidor de metadatos que envíe una respuesta solo si hay algún cambio en los metadatos desde la última recuperación, identificado por un Etag (wait_for_change=true&last_etag=). Además, se incluye un parámetro de timeout (timeout_sec=). Si no ocurre ningún cambio dentro del tiempo de espera especificado, el servidor responde con los valores sin cambios.

Este proceso permite que el IMDS (Instance Metadata Service) responda después de 60 segundos si no ha ocurrido ningún cambio de configuración, creando una posible ventana para inyectar una respuesta de configuración falsa al agente invitado.

Un atacante podría explotar esto realizando un ataque Man-in-the-Middle (MitM), suplantando la respuesta del servidor IMDS e insertando una nueva clave pública. Esto podría permitir el acceso SSH no autorizado al host.

Técnica de Escape

Mientras que el spoofing ARP es ineficaz en las redes de Google Compute Engine, una versión modificada de rshijack desarrollada por Ezequiel puede ser utilizada para la inyección de paquetes en la comunicación para inyectar el usuario SSH.

Esta versión de rshijack permite ingresar los números ACK y SEQ como argumentos de línea de comandos, facilitando la suplantación de una respuesta antes de la respuesta real del servidor de Metadatos. Además, se utiliza un pequeño script Shell para devolver una carga útil especialmente diseñada. Esta carga útil activa al Google Guest Agent para crear un usuario wouter con una clave pública especificada en el archivo .authorized_keys.

El script utiliza el mismo ETag para evitar que el servidor de Metadatos notifique inmediatamente al Google Guest Agent sobre diferentes valores de metadatos, retrasando así la respuesta.

Para ejecutar la suplantación, son necesarios los siguientes pasos:

  1. Monitorear solicitudes al servidor de Metadatos usando tcpdump:

tcpdump -S -i eth0 'host 169.254.169.254 and port 80' &

Busca una línea similar a:

<TIME> IP <LOCAL_IP>.<PORT> > 169.254.169.254.80: Flags [P.], seq <NUM>:<TARGET_ACK>, ack <TARGET_SEQ>, win <NUM>, length <NUM>: HTTP: GET /computeMetadata/v1/?timeout_sec=<SECONDS>&last_etag=<ETAG>&alt=json&recursive=True&wait_for_change=True HTTP/1.1
  1. Envía los datos de metadatos falsos con el ETAG correcto a rshijack:

fakeData.sh <ETAG> | rshijack -q eth0 169.254.169.254:80 <LOCAL_IP>:<PORT> <TARGET_SEQ> <TARGET_ACK>; ssh -i id_rsa -o StrictHostKeyChecking=no wouter@localhost

Este paso autoriza la clave pública, habilitando la conexión SSH con la clave privada correspondiente.

Referencias

Support HackTricks

Last updated