(CVE-2020-1957)Apache Shiro \< 1.5.2 身份认证绕过漏洞¶
一、漏洞简介¶
Apache Shiro 1.5.2之前版本中存在安全漏洞。攻击者可借助特制的请求利用该漏洞绕过身份验证。
二、漏洞影响¶
Apache Shiro \< 1.5.2
三、复现过程¶
环境搭建¶
明白上文的内容,漏洞复现就很容易了,复现环境代码主要参考网上的开源demo。
-
下载demo代码 shiro-basic。
-
导入idea
-
Shiro版本1.4.2
<!-- -->
- 修改ShiroConfig配置文件,添加authc拦截器的拦截正则
<!-- -->
- 修改路由控制器方法
<!-- -->
- 启动应用
漏洞复现¶
访问/hello/1
接口,可以看到被authc拦截器拦截了,将会跳转到登录接口进行登录。
访问/hello/1/,成功绕过authc拦截器,获取到了资源。
≤1.5.1版本绕过¶
观察1.5.2版本中新添加的测试用例
切换测试版本到1.5.1中,然后从中上面的测试用例提取payload进行绕过。
在1.5.1版本中,添加/
还是会直接跳转到登录。
绕过payload,/fdsf;/../hello/1
,成功绕过。
问题同样可以定位到getChain函数中对于requestURI的获取中,如下图所示,this.getPathWithinApplication(request)
获取的requestURI为/fdsf
,而不是我们输入的/fdsf;/../hello/1
,从而导致后面的URI路径模式匹配返回False,从而再次绕过了shiro拦截器。
getPathWithinApplication函数中会调用WebUtils (org.apache.shiro.web.util)中的getRequestUri函数获取RequestUri。
public static String getRequestUri(HttpServletRequest request) {
String uri = (String)request.getAttribute("javax.servlet.include.request_uri");
if (uri == null) {
uri = request.getRequestURI();
}
return normalize(decodeAndCleanUriString(request, uri));
}
RequestUri函数中最终调用decodeAndCleanUriString函数对URI进行清洗。
private static String decodeAndCleanUriString(HttpServletRequest request, String uri) {
uri = decodeRequestString(request, uri);
int semicolonIndex = uri.indexOf(59);//获取;号的位置
return semicolonIndex != -1 ? uri.substring(0, semicolonIndex) : uri;
}
如果URI中存在;
号的话,则会删除其后面的所有字符。/fdsf;/../hello/1/
最终也就变成了/fdsf
。