HTTP请求走私攻击的变异形式:CL.TE与TE.CL详解
1. 题目描述
HTTP请求走私(HTTP Request Smuggling)是一种利用HTTP协议解析差异的安全漏洞,攻击者通过精心构造模糊的HTTP请求,干扰前端服务器(如反向代理、负载均衡器)与后端服务器对请求边界的不同解析,从而实现对其他用户请求的劫持、缓存投毒或身份绕过。CL.TE与TE.CL是两种基于Content-Length(CL)和Transfer-Encoding(TE)头部冲突的核心攻击形式,分别代表前端与后端服务器对请求体终止位置的解析差异。
2. 漏洞原理:解析差异的来源
- HTTP/1.1的请求体传输机制:
服务器需要通过特定机制判断请求体的结束位置。标准方式包括:Content-Length(CL):明确指定请求体的字节数。Transfer-Encoding: chunked(TE):使用分块编码,每块以十六进制长度开头,以0\r\n标记结束。
- 关键问题:如果请求中同时存在CL和TE头部,不同服务器可能优先处理其中一个(如RFC 7230规定TE优先级更高,但实际实现可能不一致)。这种解析差异是走私攻击的基础。
3. CL.TE攻击详解(前端使用CL,后端使用TE)
- 攻击场景:
前端服务器(如CDN)根据CL头部确定请求体结束位置,而后端服务器(如应用服务器)优先处理TE头部。 - 攻击步骤:
-
构造模糊请求:
攻击者发送一个同时包含CL和TE头部的POST请求,例如:POST / HTTP/1.1 Host: example.com Content-Length: 6 Transfer-Encoding: chunked 0 \r\n GET /admin HTTP/1.1 Foo: bar- CL值为6,表示请求体长度为6字节(即
0\r\n\r\n)。 - TE分块编码中,
0表示第一块长度为0,应结束请求。 - 后续的
GET /admin是攻击者意图走私的请求。
- CL值为6,表示请求体长度为6字节(即
-
前端服务器解析:
前端根据CL=6,将整个请求体视为0\r\n\r\n(恰好6字节),并将剩余数据(GET /admin...)误认为下一个请求的开头,转发给后端。 -
后端服务器解析:
后端优先处理TE头部,解析分块数据:遇到0后认为当前请求已结束,而将后续的GET /admin作为独立请求处理。此时,该请求可能被误认为是其他用户的请求,导致权限绕过或缓存污染。 -
危害示例:
若后端服务器信任前端IP,走私的GET /admin可能直接访问管理界面,而无需用户认证。
-
4. TE.CL攻击详解(前端使用TE,后端使用CL)
- 攻击场景:
前端服务器优先处理TE头部,后端服务器根据CL判断请求体结束。 - 攻击步骤:
-
构造特殊分块请求:
POST / HTTP/1.1 Host: example.com Content-Length: 3 Transfer-Encoding: chunked 5 GET /admin HTTP/1.1 Foo: bar 0 \r\n- TE分块中,第一块长度为5(十六进制),内容为
GET(注意空格凑满5字节)。 - CL=3表示请求体总长3字节,但实际分块数据更长。
- TE分块中,第一块长度为5(十六进制),内容为
-
前端服务器解析:
前端根据TE处理分块数据,读取5对应的5字节内容(GET),然后继续解析后续分块(/admin...),直到遇到0结束。整个请求被完整转发。 -
后端服务器解析:
后端忽略TE,仅根据CL=3截取前3字节作为请求体(即GET),剩余数据(/admin...)被留置缓冲区,拼接到下一个用户请求前,形成完整的恶意请求。 -
危害示例:
下一个用户的请求可能被篡改为GET /admin HTTP/1.1 ...,导致其权限被滥用或响应数据泄露。
-
5. 防御措施
- 服务器端配置:
- 禁用模糊头部:确保同一请求中不同时使用CL和TE。
- 强制协议一致性:前端与后端使用相同HTTP版本(如均用HTTP/2,其规范禁止分块编码)。
- 严格验证请求:后端服务器拒绝包含非法字符(如
\r\n)的请求路径或头部。
- 中间件防护:
- 使用标准化代理(如Nginx)并更新至最新版本,修复已知解析差异。
- 配置中间件丢弃 ambiguous 请求,或归一化后再转发。
- 应用层检测:
- 在业务代码中检查请求格式,如发现走私特征则记录并拦截。
6. 总结
CL.TE与TE.CL攻击本质是利用了服务器链对HTTP协议理解的“分歧”。防御需从协议规范统一、服务器配置加固、主动检测三方面入手,确保请求解析的一致性。