ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析

ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
作者:Ricter Z
vSphere vCenter Server 的 vsphere-ui 基于 OSGi 框架,包含上百个 bundle。前几日爆出的任意文件写入漏洞即为 vrops 相关的 bundle 出现的问题。在针对其他 bundle 审计的过程中,发现 h5-vsan 相关的 bundle 提供了一些 API 端点,并且未经过授权即可访问。通过进一步的利用,发现其中某个端点存在安全问题,可以执行任意 Spring Bean 的方法,从而导致命令执行。
漏洞时间线:

  • 2021/04/13 – 发现漏洞并实现 RCE;
  • 2021/04/16 – 提交漏洞至 VMware 官方并获得回复;
  • 2021/05/26 – VMware 发布漏洞 Advisory(VMSA-2021-0010);
  • 2021/06/02 – Exploit 公开(from 随风’s blog);
  • 2021/06/05 – 本文公开。
0x01. 漏洞分析存在漏洞的 API 端点如下:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 1. 存在漏洞的 Controller
首先在请求路径中获取 Bean 名称或者类名和方法名称,接着从 POST 数据中获取 methodInput 列表作为方法参数,接着进入 invokeService 方法:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 2. invokeService 方法
invokeServer 先获取了 Bean 实例,接着获取该实例的方法列表,比对方法名和方法参数长度后,将用户传入的参数进行了一个简单的反序列化后利用进行了调用。Bean 非常多(根据版本不同数量有微量变化),如图所示:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 3. Bean 列表
其中不乏存在危险方法、可以利用的 Bean,需要跟进其方法实现进行排查。本文中的 PoC 所使用的 Bean 是 vmodlContext,对应的类是 com.vmware.vim.vmomi.core.types.impl.VmodContextImpl,其中的 loadVmodlPackage 方法代码如下:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 4. loadVmodlPackage 方法
注意到 loadVmodlPackage 会调用 SpringContextLoader 进行加载,vmodPackage 可控。
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 5. 调用 SpringContextLoader
最终会调用到 ClassPathXmlApplicationContext 的构造方法。ClassPathXmlApplicationContext可以指定一个 XML 文件路径,Spring 会解析 XML 的内容,造成 SpEL 注入,从而实现执行任意代码。
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 6. ClassPathXmlApplicationContext
需要注意的是,在 SpringContextLoader 的 getContextFileNameForPackage 会将路径中的 .替换为 /,所以无法指定一个正常的 IPv4 地址,但是可以利用数字型 IP 绕过:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 7. 调用 loadVmodlPackages 方法并传入 URL
XML 文件内容及攻击效果如下:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 8. XML 文件内容及攻击效果
0x02. 不出网利用(6.7 / 7.0)若要利用此漏洞本质上需要获取一个 XML 文件的内容,而 Java 的 URL 并不支持 data 协议,那么需要返回内容可控的 SSRF 或者文件上传漏洞。这里利用的是返回内容可控的 SSRF 漏洞。漏洞位于 vSAN Health 组件中的 VsanHttpProvider.py:
ssr|VCSA 6.5-7.0 远程代码执行 CVE-2021-21985 漏洞分析
文章插图
图 9. VsanHttpProvider.py 文件内容
这里存在一个 SSRF 漏洞,使用的是 Python 的 urlopen 函数进行请求,接着将返回内容在内存中进行解压,并且匹配文件名为 .*offline_bundle.* 的内容并进行返回。Python 的 urlopen 支持 data 协议,所以可以构造一个压缩包并 Base64 编码,构造 data 协议的 URL: