学习笔记 | Spring Security RegexRequestMatcher 认证绕过及转发流程

阅读量174272

发布时间 : 2022-10-11 14:30:24

 

在搜文章的过程中看到先知上的《CVE-2022-22978 Spring Security RegexRequestMatcher 认证绕过及转发流程分析》,刚好自己对spring了解不多。就跟着学习一下文中作者对spring的高低版本对业务转发的分析,记录一下笔记。

 
 
>>>环境搭建
环境搭建非常简单,可以直接参考上面提到的文章内容或者白帽汇的《Spring Security RegexRequestMatcher 认证绕过漏洞分析(CVE-2022-22978)》。也可以直接使用零号靶场:http://galaxy.pingan.com.cn/pingan/range/detail/3789
 
 
>>>漏洞分析
 
正则中,通常用点号.来匹配任意字符,但是默认情况下,它不会匹配换行符的(linux下\n)。而在RegexRequestMatcher中,就采用了默认匹配,导致可以向url中插入%0a(\n)或%0d(\d)就绕过正则匹配,从而绕过Spring Security的认证,成功请求后端资源。

可以看到在有漏洞的5.6.3版本中,DEFAULT = 0,而在5.6.4版本中设置了DEFAULT = Pattern.DOTALL。
 
通过使用Pattern.DOTALL,就改变了正则中.的默认匹配行为,使得.会匹配包括\n、\r在内的任意字符。
 

Spring 2.5.3的测试结果

 

将依赖改为spring 2.5.3,使用同样的payload进行测试,这时可以绕过Spring Security的认证,但是请求无法找到后端资源进行处理。

这时候要想搞明白为什么在不同版本下程序会由不同的表现,就需要去看一看spring处理路由的代码了。
调试跟踪

 

以2.7.2版本的代码来进行调试跟踪。
 
在Dispatcher中找到获取Handler的位置下断

一路跟踪下来,最终会来到pathPatternsCondition分支,而在2.5.3版本中,会进入patternsCondition分支。
 
它们分别调用PathPatternsCondition#getMatchingConditionPatternsCondition#getMatchingCondition
 

version2.7.2 – PathPatternsCondition

 

一路往下跟踪,最终由于路由配置中使用了*,对应WildcardPathElement,在其中不会利用正则匹配,而是匹配到所在位置有内容,则返回true。

version2.5.3 – PatternsCondition

 

而在PatternsCondition#getMatchingCondition中,一路跟踪,Spring会取出对应位置,然后进行字符串的正则匹配。

而this.pattern为java.util.regex.Pattern对象,在默认情况下它同样只会匹配换行符之外的字符。所以对于此处传入的路径无法正确匹配,返回false,最终导致无法找到handler。

>>>区别

 

综上所述,其实2.7.2和2.5.3两个版本的不同在于,在RequestMappingInfo#getMatchingCondition中,由于前期创建的RequestMappingInfo有差异,导致进入了不同的分支。

 

RequestMappingInfo取自RequestMappingHandlerMapping.mappingRegistry,关于MappingRegistry的注册过程直接参考:https://blog.csdn.net/weixin_42859458/article/details/118332596

 

直接在registerHandlerMethod中下断,回溯调用栈可以发现RequestInfo通过getMappingForMethod创建。

最终调用到RequestMappingInfo.Builder#build
 
在这里面2.7.2和2.5.3的实现就有所不不同了
 
2.7.2中this.options.patternPatser!=null,进入if块,创建了PathPatternsReuqestCondition,而patternsCondition为null。

在2.5.3则情况相反,this.options.patternParser == null,进入else块,创建PatternsCondition,而pathPatternsCondition为null。

正则表达式单行模式

 
单行模式(single line mode): 使得 通配符点”.” 匹配所有字符,包括换行符(默认情况下,点是不会匹配换行符的)。不过这个模式不被Javascript和Ruby支持。
所以其实就算Spring Security没有做升级修复,也可以通使用单行模式,增加对换行符的匹配,从而避免被绕过。
 

参考

1. Spring Security RegexRequestMatcher 认证绕过漏洞分析(CVE-2022-22978)

https://nosec.org/home/detail/5006.html

2. CVE-2022-22978 Spring Security RegexRequestMatcher 认证绕过及转发流程分析

https://xz.aliyun.com/t/11473

本文转载自: 平安集团安全应急响应中心

如若转载,请注明出处: https://mp.weixin.qq.com/s/D6delsnnsJJIypfCPdOPjg

安全客 - 有思想的安全新媒体

分享到:微信
+10赞
收藏
安全客
分享到:微信

发表评论

内容需知
合作单位
  • 安全客
  • 安全客
Copyright © 北京奇虎科技有限公司 三六零数字安全科技集团有限公司 安全客 All Rights Reserved 京ICP备08010314号-66