WebLogic 12.2.1.4.0 T3反序列化JNDI注入漏洞分析
漏洞概述
本漏洞是Oracle WebLogic Server 12.2.1.4.0版本中的一个JNDI注入漏洞,通过T3协议的反序列化机制实现远程代码执行。该漏洞利用了WebLogic Coherence组件中的com.tangosol.util.extractor.UniversalExtractor类,绕过了之前补丁对MvelExtractor和ReflectionExtractor类的黑名单限制。
影响范围
- Oracle WebLogic Server 12.2.1.4.0
漏洞原理
漏洞入口
漏洞利用的入口与CVE-2020-2883相同,通过java.util.PriorityQueue的反序列化过程间接调用com.tangosol.util.ValueExtractor接口任意实现类的extract方法。
绕过补丁分析
在CVE-2020-2883修复中,Oracle将extract方法存在危险操作的MvelExtractor和ReflectionExtractor两个类加入到了黑名单。本漏洞通过寻找另一个extract方法存在危险操作且实现了ValueExtractor接口的类来绕过补丁,即com.tangosol.util.extractor.UniversalExtractor。
UniversalExtractor分析
UniversalExtractor类的关键部分:
public class UniversalExtractor<T, E> extends AbstractExtractor<T, E>
implements ValueExtractor<T, E>, ExternalizableLite, PortableObject {
protected String m_sName; // 方法名
protected Object[] m_aoParam; // 参数
private transient boolean m_fMethod;
private transient TargetReflectionDescriptor m_cacheTarget;
// ...
}
关键点:
m_fMethod和m_cacheTarget使用transient修饰,无法通过序列化直接控制extract方法有两种执行路径,取决于m_cacheTarget是否为null
extract方法分析
extract方法的关键逻辑:
- 如果
m_cacheTarget不为null,则调用targetPrev.getMethod().invoke() - 否则调用
extractComplex方法
extractComplex方法的关键逻辑:
protected E extractComplex(T oTarget) throws InvocationTargetException, IllegalAccessException {
String sCName = this.getCanonicalName();
boolean fProperty = this.isPropertyExtractor();
if (fProperty) {
// 处理属性提取
String sBeanAttribute = Character.toUpperCase(sCName.charAt(0)) + sCName.substring(1);
for(int cchPrefix = 0; cchPrefix < BEAN_ACCESSOR_PREFIXES.length && method == null; ++cchPrefix) {
method = ClassHelper.findMethod(clzTarget,
BEAN_ACCESSOR_PREFIXES[cchPrefix] + sBeanAttribute, clzParam, false);
}
} else {
// 处理方法调用
// ...
}
// ...
}
关键限制:
- 只能调用
get和is开头的无参方法 - 方法名不能以
()结尾 - 参数数组必须为null或空
利用链构造
通过分析,构造利用链的关键步骤:
-
第一次调用
UniversalExtractor#extract:- 调用
getDatabaseMetaData()方法(get开头无参方法) - 使用
com.sun.rowset.JdbcRowSetImpl类
- 调用
-
JdbcRowSetImpl.getDatabaseMetaData()会调用this.connect() -
connect()方法中通过this.getDataSourceName()进行JNDI查找
利用条件:
- 控制
JdbcRowSetImpl的dataSource属性(可序列化) - 目标JDK版本需低于6u211、7u201或8u191(JNDI注入限制)
漏洞证明
由于Weblogic在JEP290机制下做的是全局反序列化过滤,而JNDI在JDK高版本依赖于本地Class的反序列化链,因此在Weblogic中JNDI注入只能影响以下JDK版本:
- JDK6u211之前
- JDK7u201之前
- JDK8u191之前
补丁分析
Oracle在补丁p31537019_122140_Generic.zip中:
- 将
com.tangosol.util.extractor.UniversalExtractor加入黑名单 - 过滤了
com.tangosol.util.extractor包下的其他几个类 - 将
com.tangosol.coherence.rest.util.extractor、com.tangosol.internal.util.invoke.lambda等包加入黑名单
防护建议
- 及时安装Oracle官方发布的安全补丁
- 升级JDK到安全版本(6u211+/7u201+/8u191+)
- 限制T3协议的外部访问
- 使用WebLogic的网络安全配置限制不必要的服务暴露
总结
该漏洞展示了即使在高版本WebLogic中,通过寻找新的可利用类仍然可以绕过已有的反序列化防护机制。安全研究人员需要持续关注反序列化利用链的新变种,而防御方则需要实施纵深防御策略,不仅依赖黑名单机制,还应考虑白名单控制、网络隔离等多层防护措施。