在最近运行findbugs(fb)之后,它抱怨一个:security-http响应拆分漏洞,以下代码触发它:
String referrer = req.getParameter("referrer");
if (referrer != null) {
launchURL += "&referrer="+(referrer);
}
resp.sendRedirect(launchURL);
基本上,“referer”http参数包含一个url,当单击应用程序中的后退按钮时,浏览器将返回到该url。它作为参数附加到url。经过一番研究,我知道我需要清理推荐人的网址。经过更多的研究,我发现esapi项目似乎提供了这种功能:
//1st canonicalize
import org.owasp.esapi.Encoder;
import org.owasp.esapi.Validator;
import org.owasp.esapi.reference.DefaultEncoder;
import org.owasp.esapi.reference.DefaultValidator;
[...]
Encoder encoder = new DefaultEncoder(new ArrayList<String>());
String cReferrer = encoder.canonicalize(referrer);
但是我不知道如何检测例如jscript代码或其他不属于referer url的东西。那我怎么能用伊萨皮做到这一点呢?
我试过:
Validator validator = new DefaultValidator(encoder);
validator.isValidInput("Redirect URL",referrer,"HTTPParameterValue",512,false);
但是这不起作用。我需要的是一个函数,其结果是:
http://www.google.com(好)
http://www.google.com/login?dest=http://google.com/%0D%0ALocation:javascript代码:%0d%0a%0d%0aalert(document.cookie)(不正常)
或者仅仅调用下面的语句就足够了?
encoder.encodeForHTMLAttribute(referrer);
感谢任何帮助。
最佳答案:
如果有人感兴趣,这是我的最终解决方案。首先规范化字符串,然后url解码字符串。如果存在一个CR或LF(\n\r),我只会剪切以\n或\r开头的潜在“攻击”字符串的其余部分。
String sanitize(String url) throws EncodingException{
Encoder encoder = new DefaultEncoder(new ArrayList<String>());
//first canonicalize
String clean = encoder.canonicalize(url).trim();
//then url decode
clean = encoder.decodeFromURL(clean);
//detect and remove any existent \r\n == %0D%0A == CRLF to prevent HTTP Response Splitting
int idxR = clean.indexOf('\r');
int idxN = clean.indexOf('\n');
if(idxN >= 0 || idxR>=0){
if(idxN>idxR){
//just cut off the part after the LF
clean = clean.substring(0,idxN-1);
}
else{
//just cut off the part after the CR
clean = clean.substring(0,idxR-1);
}
}
//re-encode again
return encoder.encodeForURL(clean);
}
理论上,我可以稍后根据esapi.properties中定义的“httpparametervalue”regex验证该值,但是它不喜欢http://中的冒号,我没有进一步研究。
测试之后还有一句话要说:现在大多数现代浏览器(Firefox>3.6、Chrome、IE10等)都会检测到这种漏洞,不会执行代码……