最近帮用户扫出来一个"HTTP请求走私漏洞",用户前端用的是nginx,后端是apache。后端用的版本可能比较低,与前端配合使用正好会导致这个漏洞。虽然用户后端apache没有页面,但还是建议他后端升级打下补丁。 HTTP 1.1协议特性在讲解这个漏洞之前,先了解下HTTP 1.1协议的特性。这个协议有两个重要的特性:Keep-Alive 和 PipelineKeep-Alive,这个特性在HTTP1.1中是默认开启的。就是在HTTP请求中增加一个特殊的请求头Connection:Keep-Alive,告诉服务器,接收完这次HTTP请求后,不要关闭TCP链接,后面对相同目标服务器的HTTP请求,重用这一个TCP链接,这样只需要进行一次TCP握手的过程,可以减少服务器的开销,节约资源,还能加快访问速度。
Pipeline,让客户端可以像流水线一样发送自己的HTTP请求,而不需要等待服务器的响应,服务器那边接收到请求后,需要遵循先入先出机制,将请求和响应严格对应起来,再将响应发送给客户端。浏览器一般默认都不启用,但是服务器端都会支持。 什么是HTTP请求走私漏洞?这两个特性其实并不会直接导致这个漏洞,就其本身而言是无害的。然后,现代网站组成结构很复杂,在Web服务器前面会有负载均衡、nginx、CDN加速器等各种不同作用的反向代理前端。同一个前端可能要为很多不同的后端进行转发处理。在这种场景下,前端和后端系统就请求之间的边界达成一致至关重要。否则,攻击者可能会发送一个模糊的请求,前端和后端系统会以不同的方式解析。从而导致部分前端请求被后端服务器解释为下一个请求的开始,走私内容被有效地添加到下一个请求之前,因此可能会干扰应用程序处理该请求的方式。如图,走私的内容(“前缀”),以橙色突出显示。比如,当我们向代理服务器发送一个经过设计的HTTP请求时,由于两者服务器的实现方式不同,可能代理服务器认为这是一个HTTP请求,然后将其转发给了后端的源站服务器,但源站服务器经过解析处理后,被后端解析为两个不同的HTTP请求。而其实前面那个为正常请求,那么剩下的第二个,就算是走私的请求了。 这个漏洞是如何产生的?大部分HTTP请求走私漏洞出现是因为HTTP规范提供了两种不同的方式来指定请求结束的位置:①利用Content-Length字段来判定请求体的内容长度这种方式称之为“内容编码”,通常用于对实体内容进行压缩编码,目的是优化传输,其格式也很好理解,例如:正常POST请求,会带上请求体(body),请求体有多少,Content-Length的值就是多少。 ②利用Transfer-Encoding字段来判定请求体的结束位置在头部加入Transfer-Encoding: chunked之后,就代表这个报文采用了分块编码。报文中的实体会改用一系列分块来传输,每个分块包含十六进制的长度值和数据,长度值独占一行,长度不包括它结尾的CRLF(\r\n),也不包括分块数据结尾的CRLF。最后一个分块长度值必须为0,对应的分块数据没有内容,表示实体结束,例如:上面这个代表着这次HTTP请求有3个分段,第一段长度是3,内容是abc;第二段长度是2,内容是de,第三段靠0这个字符来代表分块结束,之后还要跟2次换行。注意下,每个分段的长度都是以十六进制表示。 虽然HTTP规范有声明,如果Content-Length和Transfer-Encoding标头都存在,应该忽略Content-Length标头防止发生相互冲突。但由于以上两种不同规范的存在,如果单个消息同时使用这两种方法,当通过两个或多个前后端服务器时,就有可能发生HTTP走私协议漏洞。这是因为某些服务器不支持请求的Transfer-Encoding标头,或者标头以某种方式故意被混淆从而诱导某些支持Transfer-Encoding标头的服务器不处理它。就会出现前端和后端服务器在传输编码标头方面表现不一致,从而导致漏洞的发生。 举个简单的例子:比如前端nginx代理服务器不准请求/admin目录,但是Web服务器可以请求/admin目录,而正常的访问肯定是先请求nginx,因此就被拦截了。但如果nginx和Web服务器对body检测机制不同,我们就可以利用HTTP请求走私协议的漏洞,将访问Web服务器/admin目录的请求隐藏在body中就不会被nginx拦截了。 后面章节会结合一些实验场景来说明如何利用这个漏洞。部分历史文章链接:HTTP Host头漏洞-密码重置投毒 / HTTP Host头漏洞-Web缓存投毒 / HTTP Host头漏洞-基于路由的SSRF攻击HTTP Host头漏洞攻击-概念梳理DoS攻击之慢速攻击渗透测试之目录探测(一)/ 渗透测试之目录探测(二)渗透测试之信息收集-Nmap系列(一)/ 渗透测试之信息收集-Nmap系列(二)/ 渗透测试之信息收集-Nmap系列(三)渗透测试之SQLmap用法渗透测试之DVWA-SQL注入(上篇)/ 渗透测试之DVWA-SQL注入(下篇)渗透测试之DVWA命令注入篇