漏洞描述

因为Web应用没有对用户输入做严格验证,导致攻击者可以输入一些恶意字符。

攻击者一旦向请求行或首部中的字段注入恶意的CRLF,就能注入一些首部字段报文主体
并在响应中输出,所以又称为 HTTP响应拆分漏洞(HTTP Response Splitting)

CRLF是“回车+换行”(\r\n)的简称, 概念源自打字机,表明行的结束,计算机出现后沿用了这个概念。
其十六进制编码分别为0x0d和0x0a。
回车符(CR Carriage Return,ASCII 13,转义字符 \r,%0d) :光标移到行首,
换行符(LF  Linefeed,ASCII  10,转义字符 \n,%0a) :光标垂直移到下行


键盘上的回车键(Enter)就可以执行该操作。

但是不同的操作系统,行的结束符是不一样的。

Windows:使用CRLF表示行的结束

Linux/Unix:使用LF表示行的结束

MacOS:早期使用CR表示,现在好像也用LF表示行的结束

所以同一文件在不同操作系统中打开,内容格式可能会出现差异,这是行结束符不一致导致的。

 
 

 
在HTTP协议  报文的结构中,
-状态行和首部中的每行以CRLF结束

-首部与主体之间由一空行分隔。 
HTTP header首部与HTTP Body主体是用两个CRLF分隔的,理解为首部最后一个字段有两个CRLF
浏览器根据这两个CRLF来获取HTTP内容并显示。


浏览器就是根据这两个CRLF来取出HTTP内容并显示出来。
所以,一旦我们能够控制HTTP消息头中的字符,注入一些恶意的换行,
这样我们就能注入一些会话Cookie或者HTML代码。

CRLF漏洞常出现在Location与Set-cookie消息头中。 

漏洞检测

CRLF注入漏洞的本质和XSS有点相似,
攻击者将恶意数据发送给易受攻击的Web应用程序,
Web应用程序将恶意数据输出在HTTP响应头中。(XSS一般输出在主体中)

所以CRLF注入漏洞的检测也和XSS漏洞的检测差不多。
通过修改HTTP参数或URL,注入恶意的CRLF,查看构造的恶意数据是否在响应头中输出

找到输入点,构造恶意的CRLF字符

正常请求

抓包,在请求行的url参数中加入特殊构造的CRLF字符

 查看恶意数据是否在响应头中输出

将修改后的请求包提交给服务器端,查看服务器端的响应。
发现响应首部中多了个Set-Cookie字段。
这就证实了该系统存在CRLF注入漏洞,因为我们输入的恶意数据,作为响应首部字段返回给了客户端。

 请求包写入的恶意数据,怎么就被当成响应首部字段输出


当条件满足时,将请求包中的url参数值拼接到Location字符串中,并设置成响应头发送给客户端。

此时服务器端接收到的url参数值是我们修改后的

 http://itsecgames.blogspot%0d%0aSet-Cookie:crlf=true

在url参数值拼接到Location字符串中,设置成响应头后,响应包

%0d和%0a分别是CR和LF的URL编码。
HTTP规范中,行以CRLF结束。
所以当检测到%0d%0a后,
就认为Location首部字段这行结束了,Set-Cookie就会被认为是下一行

而我们构造的Set-Cookie字符在HTTP中是一个设置Cookie的首部字段,
这个时候就会将crlf=true设置成Cookie


重新请求,抓包,发现Cookie中多了crlf=true。

测试的用例大家可能会觉得这漏洞没什么危害性,
但试想一下:利用漏洞,
注入一个CRLF控制用户的Cookie,或者注入两个CRLF,控制返回给客户端的主体,
该漏洞的危害不亚于XSS

漏洞修复

过滤 \r 、\n 之类的行结束符,避免输入的数据污染其他 HTTP 首部字段。

更多推荐

渗透测试-CRLF注入/HTTP响应拆分漏洞(HTTP Response Splitting)