はじめに
こんにちは、診断員の秋本です!
最近、ダイワスカーレットのドヤ顔を見るためだけにウマ娘をプレイしてます。ゲームシステム全然わからん…。
皆さんは、RFC6749で定義されているOAuth2.0をご存じでしょうか。
OAuth2.0には実装不備によって生じてしまう脆弱性があり、その中の一つとしてCSRFがよく知られています。このCSRFは一般的なWebアプリケーションにおけるそれとは毛色が違うため、直感的な理解がしがたい部分があると思います。
今回のブログでは、仮定の攻撃シナリオを交えつつOAuth2.0におけるCSRFを紹介します。
CSRF(Cross-Site Request Forgeries)とは
一般的なWebアプリケーションにおけるCSRFとは、「ユーザの意図しない処理を強制される」脆弱性のことです。 Webアプリにログイン中の被害者が、攻撃者の用意したHTMLコンテンツにアクセスするなどした結果、
- 商品の購入
- 登録情報の変更
などを行うリクエストがユーザのブラウザから送信され、意図しない処理を強制される可能性があります。
以上を踏まえると、OAuth2.0でもユーザの意図しない何らかの処理を強制される脆弱性が想定されるということになります。
OAuth2.0におけるCSRFとは
OAuth2.0におけるCSRFとは、被害者のクライアントアカウントに攻撃者のリソースが意図せず紐づけされる脆弱性のことです。
注意しておきたいのが、攻撃者のクライアントアカウントに被害者のリソースを紐づけられる脆弱性ではないということです。
CSRFの攻撃シナリオ
OAuth2.0におけるCSRFを説明するために、以下の前提のもとでCSRFの攻撃シナリオを考えます。
前提
- クライアント:SNSアプリ
- リソースサーバ:クラウドストレージ
- クラウドストレージはリソースサーバと認可サーバを兼任
- 認可コードフローによる実装
- SNSアプリには別サイトのクラウドストレージアカウントと連携する機能があり、この機能を実行することでSNSアプリからクラウドストレージ上の画像を投稿することができる
- 攻撃者と被害者はそれぞれSNSアプリとクラウドストレージのアカウントを所有
攻撃シナリオ
- 攻撃者は自身のSNSアプリアカウントから連携機能を実行し、クラウドストレージ上の自身の画像へのアクセスを許可するための認可リクエストを送信します
- 攻撃者は自身のクラウドストレージアカウントへの要求に同意し、認可レスポンスを受信します
- 本来であれば、認可レスポンスは攻撃者のブラウザを経由してSNSアプリへ渡されますが、攻撃者はここでSNSアプリ宛の認可レスポンスを中断させます
(認可コードが未使用な状態) - 攻撃者は認可レスポンス中のLocationヘッダに設定されている以下のようなURLを取得し、クラウドストレージの担当者を装ったメールを送信するなどして被害者をそのURLへ誘導します
https://SNSアプリのドメイン/cb?code=SplxlOBeZQQYbYS6WxSbIA
- SNSアプリにログイン中の被害者がそのURLへアクセスするとSNSアプリへ認可レスポンスが渡され、被害者のセッションと認可コードが紐づきます
- SNSアプリは、受け取った認可コードを用いてアクセストークンを取得します
- アクセストークンを取得後、被害者のSNSアカウントと攻撃者のクラウドストレージアカウントの連携が完了します
上記の流れを図にすると以下のようになります。
被害例
情報漏えい
今回の攻撃シナリオの結果、被害者は攻撃者のクラウドストレージにアクセスできるようになりました。 一見攻撃者が自爆しているようですが、これにより被害者が自分のSNSアカウントから投稿した画像が、攻撃者のクラウドストレージへ意図せずアップロードされてしまう情報漏えいの被害が想定されます。下図参照。
なりすまし
仮にクラウドストレージアカウントを用いてSNSアプリへのログインが可能になる連携機能が実装されていた場合を考えます。
その場合、攻撃者は自身のクラウドストレージアカウントを用いて被害者のSNSアプリへログインすることが可能となり、なりすましの被害が想定されます。
CSRFが発生する原因
認可リクエストを送信(今回の攻撃シナリオだと連携機能を実行)したセッションと、認可コードを送信してきたセッションが同一であるかの検証に不備があるとCSRFの脆弱性が発生します。
対策
RFC6749ではCSRF対策として、認可リクエストにstate
パラメータというクライアントとユーザのセッションに紐づく推測困難な値を含めることが推奨されています。
state
パラメータを認可リクエストに含めると、以下のように認可レスポンスにもstate
パラメータが追加されます。
HTTP/1.1 302 Found Location: https://クライアントのドメイン/cb?code=SplxlOBeZQQYbYS6WxSbIA&state=85MMUC5nLdGpPJKYeHm8QbVj29pTWj9K
※state
パラメータによるCSRF対策は、認可サーバによって対応状況が異なる可能性があります。
参考情報
いくつかの著名サービスでの対応状況を調べてみました。
Google
パラメータ名はstate
、利用を推奨されています。 developers.google.comLINE
パラメータ名はstate
、利用は必須になっています。
developers.line.biz
おわりに
今回はOAuth2.0におけるCSRFに着目した内容でした。
意図しない処理を強制されるという点では、一般的なWebアプリにおけるCSRFと共通しています。しかしながら、意図しない処理を強制した結果一見攻撃者が自爆しているようだったり、登場人物が多かったりと初見で納得できる方は少ないのではと思います。本記事がOAuth2.0を勉強し始めたという方の理解の一助になれば幸いです。
なお、OAuth2.0を拡張したOpenID Connectという認証フレームワークにおいても同様にCSRFの脆弱性が想定されます。
参考情報
OAuth2.0のRFC
tools.ietf.orgOpenID FoundationによるRFC6749の日本語訳
openid-foundation-japan.github.ioOAuth2.0の脅威モデルのRFC
tools.ietf.orgOpenID FoundationによるRFC6819の日本語訳版
openid-foundation-japan.github.io