【web安全】Spring Data Commons 1.13.10 SpEL漏洞分析

1,331 阅读3分钟

一、简介

Spring Data是一个用于简化数据库访问,并支持云服务的开源框架,Spring Data Commons是Spring Data下所有子项目共享的基础框架。Spring Data Commons 在2.0.5及以前版本中,存在一处SpEL表达式注入漏洞,攻击者可注入恶意SpEL表达式以执行任意命令,漏洞编号为CVE-2018-1273。

​ 该漏洞发生在属性自动绑定阶段,当用户在项目中利用了Spring Data的相关Web特性对用户的输入参数进行自动匹配的时候,会将用户提交的Form表单的key值作为SpEL的执行内容,利用该特性,发送Payload将可能导致远程代码执行。

二、影响版本

  • Spring Data Commons 1.13 to 1.13.10 (Ingalls SR10)
  • Spring Data REST 2.6 to 2.6.10 (Ingalls SR10)
  • Spring Data Commons 2.0 to 2.0.5 (Kay SR5)
  • Spring Data REST 3.0 to 3.0.5 (Kay SR5)
  • Older unsupported versions are also affected

三、环境搭建

所使用Spring Data Commons 测试版本为1.13.10

搭建效果如下图:

四、漏洞复现

【→所有资源关注我,私信回复“资料”获取←】
1、网络安全学习路线
2、电子书籍(白帽子)
3、安全大厂内部视频
4、100份src文档
5、常见安全面试题
6、ctf大赛经典题目解析
7、全套工具包
8、应急响应笔记

  1. 以Post 请求发送form表单(含key-value)
  2. 在key的名称中包含Payload
  3. 提交的key名字已在Controller中实现有getName()
  4. 在key后面补上一段SPEL代码片段。

example:name[T(java.lang.Runtime).getRuntime().exec("calc")]

漏洞复现效果,如下图所示:

五、漏洞原理

​ 寻找漏洞代码段,定位到spring-data-commons-1.13.10.RELEASE.jar!org.springframework.data.web.ProxyingHandlerMethodArgumentResolver.class#createAttribute(),程序错误将用户输入传递至MapDataBinder.bind方法。

恶意数据带入,效果如下图所示:

当用户使用[]嵌套属性语法,程序将[]中SPEL表达式解析并得到属性(特性),于是攻击者可注入恶意SpEL表达式以执行任意命令。

​ 特性:通过一定的规则对及格进行筛选,构造出另一个集合 语法:“(list|map).? [选择表达式]” 选择表达式结果必须是boolean类型,如果true则选择的元素将添加到新集合中,false将不添加到新集合中。

解析SPEL表达式,效果如下图所示:

六、POC构造

​ 在实战中需要Fuzz字段,找寻自动属性字段。实验中Controller代码Account.name 已使用Spring默认构造器属性String getName()。故选取name为注入参数。

使用[]嵌套属性语法,程序将[]中SPEL表达式解析并得到属性,故POC 尝试 name[T(java.util.Arrays).toString(T(java.nio.file.Files).list(T(java.nio.file.Paths).get('d:\i4Tools7')).toArray())]

​ 但Response页面报错并无回显点,故此类文件读取POC无法验证漏洞存在,无法验证代码执行成功。

​ 尝试使用DNSLOG 验证执行成功,故POC 调整为,如burp图中所示。

验证DNSLOG出网,效果如下图所示:

七、修复方法

​ 将pom.xml中的org.springframework.boot设置为1.13.11版本或更新版本。

补丁将StandardEvaluationContext替代为SimpleEvaluationContext。

因SimpleEvaluationContext不包括 Java 类型引用,构造函数和 bean 引用,所以安全性较高。

补丁修复,效果如下图所示:

八、小结

​ 在审计中,可使用关键字加快进展,如org.springframework.expression.spel.standard、 expression.getValue()、expression.setValue() 、StandardEvaluationContext。

​ SPEL表达式较为灵活,其可以很好地适配业务中“经常变化”的部分,这可以是“业务规则”,也可以是“不同的数据处理逻辑”,SpEL的T{}表达式灵活具备反射的特点,在Spring环境下无需额外导包较为便捷。常见的SPEL实现资源的注入有如:调用各种资源的情况,包含普通文件、网址、配置文件、系统环境变量、使用预先定义模板的方式获取或者设置某对象中指定属性名的属性值。

​ 在项目中运用Spel技术的开发人员编程水平通常较高,也正是这种巧妙运用,使得漏洞较为隐蔽,较难实现一致性修复,需要安全人员付出足够耐心去寻找查核修复完成情况。