This post is also available in: English (英語)
概要
2020年春、Unit 42のクラウド脅威インテリジェンスチームは、あるお客様から自社のAmazon Web Services (AWS)インフラストラクチャの防御機能をテストするように依頼されました。このお客様は、4つのAWSアカウントで、数千個のワークロードと数百個のAmazon Simple Storage Service (S3)バケットを実行し、500人を超えるアクティブな開発ユーザーと約1,000個のロールを含むクラウド ネイティブ データベースを管理していました。このレッドチーム演習において、Unit 42のリサーチャーには、内部アーキテクチャについての限られた情報のみが与えられ、環境自体にも限られたアクセスのみが許可されました。しかしリサーチャーは、Identity and Access Management (IAM)の2つの不適切な設定を利用して、2つのAWSアカウントに対する特権アクセスを得ることができました。これらの不適切な設定により、リサーチャーは匿名ユーザーとしてクラウドにアクセスでき、そこからクラウド外でホストされているソース コード リポジトリにアクセスできました。
最初に特定された不適切な設定(「ポリシーの危険な組み合わせ」を参照)では、ポリシーの危険な組み合わせを悪用して、IAMロールを持つユーザーをAdministratorAccessに昇格させてしまうことができました。何百人ものユーザーにこのロールが割り当てられると、さまざまな手段を用いてこの脆弱性を悪用し、AdministratorAccess権限を得て、クラウド全体を侵害できるようになります。特定された2つ目の不適切な設定(「制限が緩すぎるIAM信頼ポリシー」を参照)では、制限が緩すぎるIAM信頼ポリシーを悪用して、認証されていないユーザーが匿名で内部リソースにアクセスすることができました。リサーチャーはクラウド内で横方向に移動することに成功し、最終的には証明書に対する秘密鍵、データベースの認証情報、そしてリポジトリのソースコードを入手することができました。
制限が緩すぎるIAM信頼ポリシーの重大度の分析後、Unit 42のリサーチャーはGitHub上で偵察調査を実行し、IAM信頼ポリシーの設定が不適切であるAWSアカウントを探しました。この調査では、十億ドル規模の企業である米国の製薬会社とブラジルに拠点を置く金融会社で、設定が不適切なアカウントが見つかりました。
これらの不適切な設定はすべて、仮想マシン(VM)のスナップショット、データベーステーブル、S3バケットなど、クラウドワークロード上の何千もの機密情報を漏洩させる深刻なデータ侵害につながる可能性がありました。
レッドチーム演習およびGitHubの偵察調査の詳細については『Unit 42クラウド脅威レポート』2020年秋版を参照してください。このブログでは、クラウド内で攻撃パスを特定するために使用した技術とプロセスを紹介します。また、危険なIAMポリシーの組み合わせの根本的な原因について分析します。さらに、特定された不適切な設定に対する防御と修復の方法についても解説します。
Unit 42のリサーチャーは、演習中に見つかったすべての不適切な設定はお客様によるものであり、AWSプラットフォームセキュリティの設定ではなかったと指摘しています。AWSでは、IAM信頼ポリシーの不適切な設定を検出してユーザーに警告できるよう最善を尽くしています。しかし、IAM信頼ポリシーはデフォルトでは安全であっても、ユーザーがポリシーをオーバーライドして危険な設定にしてしまうことができます。AWSでは、外部エンティティと共有されているリソースやデータへの意図しないアクセスを特定する、IAM Access Analyzerも無料で提供しています。
AWS IAM
AWS IAMは、あらゆるクラウド環境の中でも最も複雑なサービスの1つです。すべてのユーザー、サービス、リソース間のやり取りを管理します。クラウドIAMサービスはAWSをはじめとするクラウド サービス プロバイダ(CSP)により安全に設計されていますが、お客様が適切に設定または使用していないと、複数のサービスやリソースに被害が及ぶ可能性があります。たとえば、2019年のCapital One社のデータ侵害では、IAM設定の制限が緩すぎたために、攻撃者がAWSウェブ アプリケーション ファイアウォール(WAF)からAmazon Elastic Compute Cloud (EC2)およびS3バケットに横方向に移動することができ、同社に8000万ドルの損害をもたらしました。
Unit 42のリサーチャーは、お客様から要望のあったレッドチーム演習にどう取り組むかを検討した結果、IAMサービスとその設定の重要性を考慮し、IAMから取り掛かることにしました。IAMのさまざまな機能を使用して、お客様のクラウド環境をテストしました。その結果、2つの異なるAWSアカウントで、リサーチャーがお客様のクラウド環境に侵入できてしまう、2つの異なるIAMロール関連の不適切な設定が見つかりました。次のセクションでは、AWS IAMロールについて簡単に紹介します。
AWS IAMロール
AWS IAMロールは、クラウドユーザーやサービスに一時的なアクセス権を提供するIAMアイデンティティです。IAMロールの概念は、ロールベースのアクセス制御に基づいています。同じアクセス権限を必要とするユーザーには同じロールが割り当てられ、複数のロールを1人のユーザーに割り当てることが可能です。AWSでは、ロールが割り当てられたプリンシパル(つまりユーザーまたはサービス)は、そのロールを「引き受ける」ことにより短期間のアクセストークンを取得することができます。このトークンにより、プリンシパルは許可されたリソースにアクセスできるようになります。各トークンは、付与された時点から15分~12時間後に期限が切れるように設定できます。トークンの期限が切れてからアクセスを続行するには、新しいトークンを要求する必要があります。IAMロールの一般的な使用例は以下のとおりです。
- 特定のクラウドリソースに一時的にアクセスする必要のあるユーザーを、特定の権限を付与するIAMロールに関連付けることができます。
- 特定のクラウドリソースとやり取りする必要があるEC2やAWS Lambdaなどのクラウドサービスに、IAMロールをアタッチすることができます。
- Azure Active Directory (AD)やOpenIDなどの既存のアイデンティティプロバイダ(IdP)を使用する組織では、IAMロールを使用して、IdPにより管理されているユーザーにクラウドへのアクセスを許可することができます。AD内の既存のユーザーは、クラウドにユーザーアカウントがなくても、ロールを引き受けるだけでクラウドにアクセスできるようになります。
- ユーザーやサービスに、1つのクラウドアカウントから別のクラウドへのクロスアカウントアクセスを許可することができるのです。たとえば、クラウドAの開発者のグループがAWS CodeBuildを使用してクラウドBの開発者と共同で作業する必要があるとします。この場合、クラウドAの開発者にアクセスを許可するIAMロールをクラウドBに作成することができます。
ポリシーの危険な組み合わせ
Unit 42のリサーチャーには、内部関係者による攻撃や認証情報の漏洩による攻撃をエミュレートするために、お客様の開発環境内の開発者のロールが付与されました。この環境では品質保証(QA)を目的とした本番インフラストラクチャの複数のレプリカがホストされており、数百人の開発者が実際に使用していました。
Unit 42のリサーチャーは、開発者ロールのユーザーが権限のセットをチェーン化することによりAdministratorAccess権限を得られることを発見しました。AWSのAdministratorAccessは、機密情報の窃盗やインフラストラクチャ全体の削除など、攻撃者が組織に対するあらゆる攻撃を実行できるようにする「王国への鍵」です。この開発環境には本番のワークロードは含まれていませんでしたが、攻撃者は開発環境で得た情報を使用して、本番環境にアクセスできる可能性がありました。リサーチャーは、認証情報、コードリポジトリ、そして不適切な設定までもが両方の環境で共有されていることを確認しました。また、本番環境には開発アカウントのユーザーが引き受けることが可能なIAMロールもありました。つまり、開発アカウントの攻撃者がAssumeRoleを使用して本番アカウントのアクセストークンを取得することができました。AssumeRoleは、クロスアカウントアクセスを可能にするAWS独自のロールです。
この脆弱性につながったIAM権限の1つが、IAM:PassRoleです。PassRoleは、プリンシパルがIAMロールを別のサービスにアタッチすることのできる機能です。たとえば、PassRole権限を持つユーザーは、EC2インスタンスを作成してロールをVMにアタッチすることができます。このVMはロールに関連付けられた権限を使用して、AWSリソースにアクセスできます。IAMのPassRole権限は、プリンシパルが他のAWSリソースを管理するためにAWSサービスを使用する必要がある場合に使用します。EC2、Lambda、Glue、ECSなどのAWSサービスにはすべて、特定の操作を実行するためのIAMロールをアタッチすることができます。
PassRole機能によりプリンシパルがクラウドサービスに権限を付与できるため、そのプリンシパルの権限ポリシーが制限されていなければ悪用される可能性があります。悪意のあるプリンシパルは、自分が持っていない権限をあるサービスに渡し、そのサービスを悪用して、悪意のある活動を代わりに実行させることができます。
プリンシパルが渡せるIAMロールは、そのプリンシパルの権限ポリシーとIAMロールの信頼ポリシーにより決まります。権限ポリシーは、プリンシパルが渡すことのできるIAMロールと、そのロールを渡すことができるサービスを制限します。信頼ポリシーは、ロールをアタッチできるサービスを制限します。
以下の図1で、左側のコードは、プリンシパルが特定の名前を持つロール(role/DevOpsEC2-*およびrole/DevOpsECS-*)をサービスのリスト(ec2.amazonaws.comおよびecs.amazonaws.com)に渡すことを許可する権限ポリシーを示しています。右側はIAMロールの信頼ポリシーです。この場合、EC2サービスにのみロールの引き受けを許可しています。プリンシパルは、以下の条件がすべて満たされている場合にのみ、ターゲットサービスにロールを渡すことができます。
- プリンシパルの権限ポリシーにIAM:PassRole権限が指定されている。
- ロールの名前が、権限ポリシーのResourceフィールドに定義されているパターンと一致している。
- ターゲットサービスが、権限ポリシーのConditionフィールドに指定されている。Conditionフィールドがない場合は、プリンシパルはどのサービスにでもロールを渡すことができます。
- ロールの信頼ポリシーにより、ターゲットサービスがそのロールを引き受けることが許可されている。
プリンシパルよりもロールの方が高特権(より多くの権限が許可されている)の場合、プリンシパルはロールがアタッチされているサービスにアクセスでき、特権の昇格が発生する可能性があります。
図2は、お客様のAWSクラウド環境で、Unit 42のリサーチャーがどのように脆弱性を発見し、悪用して、最終的にAdministratorAccessを得たかを示しています。リサーチャーは、環境を侵害するために攻撃者が順を追って実行することのできるアクションを特定し、確認しました。
1.攻撃者がフィッシングにより従業員から認証情報(開発者ロールのセッショントークンなど)を盗み出します。攻撃者はAWS IAM APIを使用するかサービスを列挙して、トークンの権限を調べます。
2.攻撃者はトークンにはIAM:PassRole権限があり、渡せるロールに制限がないことを発見します。つまり、攻撃者はどのロールでも渡せます。
3.攻撃者は既存のロールとその信頼ポリシーを確認します。通常は、各ロールを1つのサービスのみが引き受けることができます。攻撃者は、アクセスするサービスで引き受けることのできるロールを見つける必要があります。条件に合うロールのサブセットを見つけると、攻撃者は次に進むことができます。
4.攻撃者は、悪用可能なロールの権限ポリシーを確認します。いずれかのロールが攻撃者の現在のアイデンティティよりも高特権である(多くの権限が与えられている)場合、攻撃者はこのロールをサービスに渡して、そのサービスから昇格された特権を得ることができます。攻撃者は、EC2が引き受けることのできる、AdministratorAccessを持った複数のロールを発見します。
5.攻撃者は新しいEC2インスタンスを作成し、EC2ManagerRoleをVMにアタッチします。その後、攻撃者はVMにログインし、http://169.254.169[.]254/latest/meta-dataでメタデータサービスAPIを呼び出し、セッショントークンを取得します。このセッショントークンは、クラウド全体に対するAdministratorAccessを攻撃者に付与します。
上記の手順は、設定が不適切なIAM:PassRoleを使用して実行することのできる攻撃パスの1つを示しているにすぎません。Unit 42のリサーチャーは、お客様の環境で、同様に悪用可能な複数のIAMロールとサービスを特定しました。
この攻撃パスの「クラス」は、開発者ロールの権限ポリシーに、PassRoleアクションに対する制限が何もなかったために悪用することができました(図3)。さらに、悪用可能な複数のIAMロールにAdministratorAccess権限が付与されていました。数百人の開発者がこのIdPロールを毎日使用していることを考えると、いずれかの開発者のラップトップが実際にハッキングされた場合、大きな損害が発生した可能性が高かったでしょう。AdministratorAccess権限があれば、攻撃者はランサムウェアにより機密データを盗み出し、事業活動を中断させたりインフラストラクチャ全体をロックダウンさせたりすることができます。
問題を特定したUnit 42のリサーチャーは、ただちにお客様とともに不適切な設定を修正し、ログを確認しました。幸い、フォレンジック調査により、この不適切な設定の悪用に成功した攻撃者はいないことが確認されています。
制限が緩すぎるIAM信頼ポリシー
Unit 42のリサーチャーは、お客様のGitHubページで、お客様の本番AWSアカウントのIDを見つけました。GitHubページでは、お客様の製品との統合に使用される命令やスクリプトをホストしています。このアカウントIDを使用し、リサーチャーはロール名のリストの引き受けを試みて、設定が不適切なIAMロールを列挙することができました。匿名で引き受けることのできる、設定が不適切なロールを見つけるのにそれほど時間はかかりませんでした。図7は、攻撃者が環境を侵害するために順を追って実行することのできるアクションを、リサーチャーがどのようにして特定し、確認したかを示しています。
- 攻撃者は偵察と列挙により、ロール名のリスト(例: prodApp-nat、prodApp-app2-nat)を取得します。ロール名は長くなく、ある程度予測可能であるため、設定が不適切なロールを列挙により見つけることができます。
2. 攻撃者は設定が不適切なロールを引き受けることにより、一時的なアクセストークンを取得します。このアクセストークンを使用して、攻撃者は権限を列挙し、アクセス可能なリソースを見つけることができます。
3.攻撃者はすべてのEC2インスタンスを見ることができ、それらのメタデータを読み取ることができます。攻撃者はメタデータの起動スクリプトから、VMがデプロイするDockerイメージ、VMがクエリを実行するデータベース、VMがデータを抽出するS3バケットなどの情報を取得できます。
4.攻撃者はEC2メタデータ内で見つけたS3バケットにアクセスし、すべてのデータをダウンロードします。証明書鍵、アプリケーションのデプロイに使用される複数のシェルスクリプト、および認証情報を含むいくつかの暗号化ファイルといったデータです。
5.攻撃者はロールで利用可能なAWS KMS復号機能を使用して暗号化テキストを復号し、平文のアクセス認証情報を取得します。
6.平文の認証情報を取得した攻撃者は、横方向に移動し、Docker Hubリポジトリ、Splunkサーバー、およびデータベースにアクセスすることができます。
この設定が不適切なIAMロールは、認証されていない攻撃者によりリモートから悪用される可能性があったため、重大な脆弱性となっていました。攻撃者は、証明書に対する秘密鍵さえあれば、中間者攻撃を実行したり、会社の公式サイトを偽装したりすることができました。また、ソース コード リポジトリにアクセスして、会社の知的財産を漏洩させたり、脆弱性を見つけたりするだけでなく、ソースコードにマルウェアを注入することもできました。幸い、フォレンジック調査により、この不適切な設定の悪用に成功した攻撃者はいないことが確認されています。
実際に存在する設定が不適切なIAM信頼ポリシーの例
IAM信頼ポリシーの設定はリモートから匿名で確認できるため、Unit 42のリサーチャーは一般的に見て不適切な設定はどの程度存在するものなのかを調べました。リサーチャーの手法は、GitHub内の一般公開されているデータを使用して、偵察調査を実施するというものでした。
設定が不適切なIAMロールを検索するのは、パスワードなしでのログインが可能な公開されたデータベースを検索するのと似ています。Unit 42のリサーチャーは、IPアドレスやポートを探す代わりに、AWSアカウントIDを探しました。また、パスワードなしで認証されるデータベースユーザーを検索する代わりに、匿名で引き受けることができるIAMロールを検索しました。設定が不適切なロールの名前を正しく推測できれば、リサーチャー(すなわち、攻撃者)はロールを引き受けて、アクセストークンを取得することができます。
最終的にUnit 42のリサーチャーは145,623個のリポジトリで283,751個のファイルを分析し、32,987個の確認済みのAWSアカウントIDと68,361個のロール名を特定しました。図13は調査方法を示しています。
- Unit 42のリサーチャーはGitHub APIを使用して、Amazonリソースネーム(ARN)またはAWS IAMロール名が含まれる可能性のあるファイルを検索しました。リサーチャーは、IAMドキュメントに記載されている、考えられるすべてのリソース名をキーワードとして使用して、GitHub APIでのクエリを実行しました。たとえば、キーワードarn:aws:amplifyはAWS Amplify ARNと一致し、キーワードarn:aws:cloud9はAWS Cloud9 ARNと一致します。arn:aws:iam:123456789012:role/MyTestRoleのように、IAMロール名がIAM ARNに含まれる場合もあります。AWSは3つの異なるパーティションで動作しているため、各パーティション名(aws、aws-cn、aws-us-gov)も検索キーワードで使用しました。
- すべてのファイルがダウンロードされた後、Unit 42のリサーチャーはまず正規表現を使用して、考えられるアカウントIDとロール名を抽出しました。ファイルがAWS CloudFormation形式またはTerraform形式の場合は、ファイルはさらにJSONオブジェクトに解析され、すべてのプロパティ名が分析されました。IaCテンプレートは一般に広く使用されているため、ダウンロードされたファイルの70%余りがIaCであり、より簡単かつ正確に分析を行えました。
- 抽出されたすべてのアカウントIDが有効なわけではないため、リサーチャーはAWS管理コンソールページを使用して各アカウントを検証しました。AWSでは、アクティブな各アカウントに対して、https://account_alias_or_id.signin.aws.amazon.com/console/にコンソールページが作成されます。アカウントIDが存在していてアクティブであれば、このURLにHTTP要求を送信すると、HTTP 200応答を受け取ります。aws-cnパーティションおよびaws-us-govパーティション内のAWSアカウントも、それぞれURL https://account_alias_or_id.signin.amazonaws.cn/console/および https://account_alias_or_id.signin.amazonaws-us-gov.com/console/を使用して同様にテストできます。
4.AWSアカウントで既存のロール名を見つけるのは、データベース内でパスワードなしのユーザー名を見つけるブルートフォース攻撃と似ています。Rhino Security Labsにより公開されている手法を用いれば、ターゲットアカウントに痕跡を残さずに、AWSアカウントにロール名が存在するかどうかをチェックできます。この手法ではAWS IAM信頼ポリシー検証ツールを悪用して、Principalフィールドに指定されているIAMロールが存在するかどうかをチェックします。Unit 42のリサーチャーは、検証された各アカウントIDを、ステップ2で特定したロール名のサブセットとともに列挙しました。アカウントIDと同じGitHubリポジトリ内で見つかったロール名をテストしてから、GitHubで見つかった最も一般的なIAMロール名の上位500個をテストしました。
5.Unit 42のリサーチャーは、既存のIAMロールを匿名で引き受けることが可能かどうかを確認するために、assume-roleコマンドを使用して各ロールの引き受けを試みました。ロールを匿名で引き受けることができれば、秘密鍵とセッショントークンのセットが返されます。このステップでは、ロールの引き受けに成功したかどうかにかかわらず、ターゲットアカウントにログが残されます。
設定が不適切なアカウント内には、数十万個のEC2スナップショット、数千個のEC2ボリューム、そして数百個のS3バケットが見つかりました。設定が不適切なIAMロールから漏洩するリソースは、ロール自体の権限ポリシーによって異なります。Unit 42のリサーチャーは、システム管理者にほぼ近い権限が割り当てられていた、設定が不適切なDevOpsロールを発見しました。また、Amazon DynamoDBやAmazon Redshiftなどのデータベースサービスにアクセスできた、設定が不適切なDBAccessロールも見つかりました。さらに、Lambda関数での基本的なGetアクションとInvokeアクションのみを許可するLambdaExecutionロールもありました。
特に注目すべきは、この調査により、十億ドル規模の企業である米国の製薬会社とブラジルに拠点を置く金融会社で、設定が不適切なアカウントが見つかったことです。
これらの設定が不適切なロールは、アクセスできたリソースの種類にかかわらず、いずれも攻撃者が悪用できる情報を漏洩させていました。クラウドアカウントは数百または数千個のクラウドリソースにアクセスできる可能性があるため、クラウドアカウントが侵害された場合の被害は、クライアントホストが侵害された場合よりも大きくなる可能性があります。クラウド内には無限とも言える数のリソースが存在していることから、そうしたインフラストラクチャは魅力的な標的となっています。LambdaExecution権限のみを持つアカウントも、多数の関数呼び出しを実行することで、大きな経済的影響を及ぼす可能性があります。
結論
人間には得意なこともたくさんありますが、数百件ものアイデンティティ内で危険な権限を特定する作業は自動化すべきです。調査では、ほぼすべてのクラウド環境に、制限が緩すぎるアカウントや古いアカウントが存在することが明らかになっています。クラウドプロバイダは最小限の権限アプローチを実施するための適切なベースラインを提供していますが、クラウドで複数のプロバイダを採用するようになると、このアプローチは機能しなくなります。IAMは複雑かつ動的であるため、常に安全な状態を保つことは容易ではありません。今日は安全なIAMも、新たなロールが追加されたり、既存のポリシーが編集されたりして、明日には安全でなくなるかもしれません。しかし、IAMの「衛生管理」(ハイジーン)を適切に行うことで、リスクを大幅に軽減することができます。
Unit 42のリサーチャーは、以下のベストプラクティスを推奨しています。
AWSユーザー
- 機密データおよびワークロードに対するきめ細かなアクセス制御(最小限の権限): 絶対に必要な権限のみをユーザーやサービスに付与します。以下に例を示します。
- あるサービスがS3バケット内の数個のファイルにのみアクセスする必要がある場合、そのサービスにバケット全体に対するアクセスは許可しないようにします。
- あるサービスがKMS内の特定の鍵を使用してデータの復号/暗号化のみを実行する必要がある場合、そのサービスにKMS全体に対するアクセスは許可しないようにします。
- S3バケット内の機密ファイルまたはKMS内の鍵が特定のサービスによってのみアクセスされる場合、そのサービス以外のソースからのすべてのトラフィックをブロックします。
- IAMロールの信頼ポリシーの強化: どのIAMロールにも、匿名アクセス(“Principal” : { “AWS” : “*” })は付与しません。ランダムな文字列を追加して、ロール名を簡単に推測できないようにします。ロールが複数のAWSアカウントで共有されている場合は、追加の防御層として、推測できない外部IDを使用します。ロールが特定のIPアドレスからのユーザーやサービスによってのみ引き受けられる場合は、プリンシパルのソースIPに条件を適用します。
- IAM:PassRole権限の強化: ポリシー内でIAM:PassRole権限を付与する場合には、常に以下を制限します。
すべてのCSPユーザー
- MFAの有効化: 多要素認証(MFA)は、プライマリパスワードが侵害された場合の追加のセキュリティ層を提供します。MFAはユーザーとIAMロールの両方に対して有効にできます。
- 認証情報のローテーションの自動化: クラウド環境で使用される認証情報をローテーションする自動化されたプロセスを実装します。認証情報を定期的にローテーションすることにより、認証情報の漏洩リスクを軽減することができます。
- IAM:PassRole権限の強化: ポリシーでIAM:PassRole権限を付与する場合には、常に以下を制限します。
- 権限をきめ細かく設定したグループやロールの作成: 同じプロジェクト内のユーザーは同様の権限を必要とすることが多いため、同じグループまたはロールに配置することで権限の管理を簡素化できます。ただし、小さなチームがプロジェクトの別々の部分について作業を行っている場合は、各チームに対してより狭い範囲の権限が付与されたロールまたはグループを作成するべきです。
- IAM APIの監視: すべての大手クラウド サービス プロバイダは、IAMの使用状況を監視するためのサービスを提供しています。これらのサービスを利用すると、ブルートフォース攻撃や、認識されていないデバイスや場所からのログインなどの、異常な活動を特定することができます。
- クラウドのネイティブ セキュリティ プラットフォームの活用: 機密リソースの数は増加の一途をたどっており、そうしたリソースへのアクセス権を持つ多数の特権ユーザーを管理することは容易ではありません。その上、クラウドリソース自体の権限セットを管理する必要もあります。Prisma Cloudなどのクラウドのネイティブ セキュリティ プラットフォーム(CNSP)を使用することにより、クラウドリソースのアイデンティティを利用してセキュリティポリシーを適用し、複数のクラウド環境での安全なユーザー活動を保証することができます。
より詳しい調査内容および組織で実施できるベストプラクティスについては、Unit 42 クラウド脅威レポート2020年秋版 をダウンロードしてください。