AWS CDKのセキュリティ脆弱性：ブートストラップ設定とS3バケットのリスク

# はじめに
末っ子の三男も高校サッカー選手権で敗退し、引退を迎えて週末の予定が無くなった [@\_\_\_nix___](https://twitter.com/___nix___)  です。
休日にMLBワールドシリーズ開幕戦を観ながら何故か技術記事を書いてます。

# 背景
AWS Cloud Development Kit (CDK)は、クラウドインフラストラクチャをコードとして定義し、デプロイするための強力なツールです。CDKを使用するには、各環境（アカウントとリージョンの組み合わせ）で「ブートストラップ」と呼ばれる初期設定プロセスを実行する必要があります。このプロセスでは、CDKが正常に機能するために必要な各種リソース（S3バケット、IAMロールなど）が作成されます。

# 概要
AWSはこのCDKにおいて、ブートストラップ設定に関する潜在的なセキュリティ問題を通知しました。この問題は、CDKのデフォルトアセットバケットが削除されているにもかかわらず、他のブートストラップリソースが残っている場合に発生する可能性があります。

※AWS Health では「AWS_CLOUDFORMATION_SECURITY_NOTIFICATION」で通知されています。

# 問題点
デフォルトのアセットバケット（`cdk-hnb659fds-assets-<アカウントID>-<リージョン>`）が存在しないが、デプロイロール（`cdk-hnb659fds-deploy-role-<アカウントID>-<リージョン>`）が残っている状態の場合が該当します。

この状況下で、悪意のある第三者が削除されたバケットと同じ名前でS3バケットを作成した場合、将来のCDKデプロイメント時に予期せぬ変更がアカウントに加えられる可能性があります。

`hnb659fds` という識別子が全アカウントで共通であるため、アカウントIDさえ分かれば、潜在的な攻撃者がCDKリソースを特定することが出来ます。

[こちらの記事](https://cybersecuritynews.com/aws-cdk-vulnerabilities/) で紹介されていた AWS CDK Attack Chain の図説
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/22939/a31267ad-846a-a6ae-45fa-13832cacf713.png)
*AWS CDK Attack Chain | Source: Aquasec*
https://cybersecuritynews.com/aws-cdk-vulnerabilities/

:::note info
以下の記事のように修飾子の変更をしている場合は対象外なので安心してください。
:::
https://dev.classmethod.jp/articles/changing-the-aws-cdk-bootstrap-environment-from-the-default-qualifier-hnb659fds/

# 確認方法
確認方法は以下の3つの方法があります。

## (1) CloudFormation コンソール
CloudFormationコンソールで、「CDKToolkit」という名前のスタックが存在するか確認します。

S3コンソールで、「`cdk-hnb659fds-assets-<アカウントID>-<リージョン>`」という名前のバケットが存在するか確認します。

:::note alert
スタックは存在するがバケットが存在しない場合、潜在的なリスクがあります！
:::

## (2) AWS Health Dashboard
AWS Health Dashboard で、「アカウントの状態」＞「イベントログ」で「CloudFormation security notification」を確認します。

「詳細」では問題に対する通知内容が確認でき、「影響を受けるアカウント」では具体的にどのリージョンに該当するスタックが存在しているかの確認ができます。

:::note alert
イベントログに「CloudFormation security notification」がある場合、潜在的なリスクがあります！
:::

## (3) AWS CLI
AWS CLI を実行し、結果が返ってきた場合はこの脆弱性のリスクがあります。
個別に確認する方法と、管理するアカウント全体を一括で確認する方法があります。
結果が無い場合は安心してください。

<details><summary>結果の例</summary>

```
{
    "events": [
        {
            "arn": "arn:aws:health:<REGION>::event/CLOUDFORMATION/AWS_CLOUDFORMATION_SECURITY_NOTIFICATION/AWS_CLOUDFORMATION_SECURITY_NOTIFICATION_0ec99ca6d6a2b5d5c59feea909c463458f85bded390ec4f51f701d6e25a068b4",
            "service": "CLOUDFORMATION",
            "eventTypeCode": "AWS_CLOUDFORMATION_SECURITY_NOTIFICATION",
            "eventTypeCategory": "accountNotification",
            "region": "<REGION>",
            "startTime": "2024-10-16T04:55:00+00:00",
            "lastUpdatedTime": "2024-10-16T07:50:14.319000+00:00",
            "statusCode": "open",
            "eventScopeCode": "ACCOUNT_SPECIFIC"
        }
    ]
}
```
</details>

### 個別AWSアカウント

```
aws health describe-events \
  --filter "eventTypeCodes=AWS_CLOUDFORMATION_SECURITY_NOTIFICATION" \
  --region us-east-1
```

### 組織ビューの有効化アカウント

組織全体のAWSアカウントの確認をする場合はこちらを実行してください。
但し、エラーが出る場合は諸々の条件が不足していますのでこの確認方法は諦めてください。

```
aws health describe-events-for-organization \
  --filter "eventTypeCodes=AWS_CLOUDFORMATION_SECURITY_NOTIFICATION" \
  --region us-east-1
```

:::note alert
結果例のような表示があった場合は潜在的なリスクがあります！
:::

# 対応方法
状況に応じて、以下のいずれかの対応を取ってください。

## CDKを使用しない場合
影響を受けるリージョンのCloudFormationコンソールで「CDKToolkit」スタックを削除します。

## CDKを引き続き使用する場合
1. 削除されたS3バケットを手動で再作成します。
2. バケットのバージョニングを有効にし、適切なKMSキーを選択します。
3. 提供されたバケットポリシーを設定します。
    ```json
    {
    	"Version": "2012-10-17",
    	"Id": "AccessControl",
    	"Statement": [
    		{
    			"Sid": "AllowSSLRequestsOnly",
    			"Effect": "Deny",
    			"Principal": "*",
    			"Action": "s3:*",
    			"Resource": [
    				"arn:aws:s3:::cdk-hnb659fds-assets-<ACCOUNT ID>-<REGION>",
    				"arn:aws:s3:::cdk-hnb659fds-assets-<ACCOUNT ID>-<REGION>/*"
    			],
    			"Condition": {
    				"Bool": {
    					"aws:SecureTransport": "false"
    				}
    			}
    		}
    	]
    }
    ```
4. ライフサイクルルールを作成して古いバージョンのオブジェクトを管理します。
5. 最新バージョンのCDK CLI（2.149.0以降）をダウンロードし、環境を再ブートストラップします。

# 終わりに
AWS CDKは非常に便利なツールですが、適切に管理されていないと潜在的なセキュリティリスクを生む可能性があります。
もちろんこれは全てのツールに言えることですので定期的なバージョンアップや今回のような通知を見逃さないようにしましょう。

# 一言
この記事良かったと少しでも思って頂けたら是非 [@\_\_\_nix___](https://twitter.com/___nix___) をフォローしてあげてください。或いは記事に対してリアクションをお願い致します。