设为首页 - 加入收藏 - 网站地图 SecYe安全 Www.SecYe.Com - 国内网络信息安全IT技术门户网
当前位置:SecYe > 网络安全 > Web安全 > 正文

反序列化漏洞检测JMS

时间:2016-11-28 16:32 来源:未知 作者:SecYe安全 阅读:

Java反序列化漏洞大家应该都非常熟悉了,想必大家手里都有各种各样的利用这类漏洞的工具。其被称为是2015年被低估的“破坏之王”可见其影响之大。Java反序列化漏洞的成因和PHP反序列化漏洞的成因差不多,都是由于程序接收不可信的序列化数据后直接将其反序列化导致的。这又印证了那句老话:一切的输入都是有害的。

Java序列化与反序列化

Java中可以将对象序列化为字节流来方便对象的传输。在Java中很多地方都会用到对象序列化这种技术,我想这大概是Java反序列漏洞危害那么大的一个原因之一吧。在Java中有很多的看似与序列化没关系的东西都使用了序列化。比如一下的一些流行的协议,他们都是基于Java序列化的。

 

\

 

这样也就暴露很多潜在的攻击面。Java中只有实现了java.io.Serializable 或者 java.io.Externalizable接口的类才能被序列化和反序列化.能够被反序列的类通过使用 java.io.ObjectOutputStream 将对象转换为字节流,在通过使用 java.io.ObjectInputStream 将字节流反序列化为对象。而漏洞就发生在将输入的字节流反序列化为对象这一步。和 PHP 的反序列漏洞利用基本一致。我们能控制的有对象的属性,在Java反序列对象的过程中有一些 魔术方法会被调用比如 readObject() readResolve()等。如果某个可被反序列化的类实现了上述的某个方法,我们就有可能可以做到一些有趣的事情。下面来一个简单的Demo加深下理解。假设存在下面这样一个可被反序列化的类,同时该类在程序当前类路径中。

public class Gadget0 {

public String command;

protected void readObject(java.io.ObjectInputStream stream) throws IOException, ClassNotFoundException {

stream.defaultReadObject();

Runtime.getRuntime().exec(command);

}

}

可以看到该类实现了 readObject 方法,在该方法中又调用了Runtime.getRuntime().exec(command) 来执行一条系统命令,其参数为类的一个属性值,而属性值是我们可控的所以我们就能实现一个代码执行了。当然现实中并没有这么直接,而是需要许多条件的,需要利用一些gadgets构造POP链实现一些有趣的事.如果目标应用使用了一些具有漏洞的库那就很简单了,直接上神奇Ysoserial生成payload发送给应用反序列化可以干掉它喽。就像这样

 

\

 

Java消息服务(Java Message Service)

Java 消息服务(Java Message Service,JMS)应用程序接口是一个Java 平台中关于面向消息中间件(MOM)的API,用于在两个应用程序之间,或分布式系统中发送消息,进行异步通信。下面来看看支持JMS的产品。

 

\

 

可以看到JMS这个东西还是很受欢迎的。下面看看JMS的一个基础的运行流程是怎么样的。

 

\

 

其中主要的组成部分有一些几点。

1. JMS Broker :一般作为一个独立的服务运行,用来接受JMS的连接,并存储和分发消息.可以使用任何语言来实现。

2. JMS Client: 与Broker交互,生产者/消费者模型,即一个客户端提交消息,一个客户端获取消息

3. Connect : 使用一些特定的协议通信。

4. Session: 仅仅在需要管理时使用。
 

 

下面看看怎样使用API来发送和接收JMS消息

发送消息:

 

\

 

接收消息

 

\

 

前面提到过,在Java中有很多东西都是基于序列化的,JMS也是如此.我们先来看看JMS 消息的结构.

 

\

 

Message主要由三部分组成,分别是Header,Properties和Body, 解释如下:

Header: 消息头,所有类型的这部分格式都是一样的

Properties: 属性,按类型可以分为应用设置的属性,标准属性和消息中间件定义的属性

Body: 消息正文,指我们具体需要消息传输的内容。

JMS 消息的类型有很多,具体为

 

\

 

在这么多的类型中,有一种类型的消息,促成了攻击。他就是: javax.jms.ObjectMessage ,我们来看看官网是怎么介绍它的。

 

\

 

可以看到这个消息内部有一个可以序列化的对象,这就有趣了。下面接着看看ObjectMessage消息是怎样定义的

 

\

 

它有一个 getObject 方法,这个方法会将输入的消息反序列化。现在可反序列化的点已经找到,下面就是找找怎么样实现利用了。

漏洞挖掘

针对这种漏洞的挖掘思路很简单:找到接收不可信 ObjectMessage 的地方 之后分析程序所使用的一些库,看看能不能找到一些gadgets来构造一个 POP链,实现一个漏洞利用。实际上基本所有实现了ObjectMessage的组件中,都不会对输入的消息进行身份验证,直接拿去反序列化了。下面看看最近在这方面出现的漏洞。

 

\

 

下面是其中一个漏洞概要的截图。

 

 

可见这类漏洞发送的罪魁祸首就是 getObject 函数接收了不可信的输入。
 

 

漏洞利用

漏洞原理搞清楚了,进行利用就非常简单了。漏洞的本质就是接收不可信数据进行反序列化。那么我们就把发送包含payload对象序列化之后的数据的ObjectMessage发送到有漏洞的程序那就ok了。

 

\

 

整个一个漏洞利用的流程可以用下图来形象的解释。

 

\

 

攻击者假装为JMS 生产者向Broker提交一个带有恶意payload的ObjectMessage之后 Broker把消息分发给 JMS消费者,其拿个这样一个消息后对其中的序列化对象部分进行反序列化,触发漏洞,然后实现代码执行。而往往JMS消费者不会只有一个,所以现实中的情况会是这样。

 

\

 

有趣...

在实际构造exploit时并没有上面讲的那么轻松,一个成功的exploit 所要考虑的东西还是挺多的,比如:

1.jre的版本

2.应用程序所使用的库.

3.哪些库会在程序运行时的类路径中

4.是否开启 Java Security Manager

........

单纯的手工白盒分析是非常麻烦的,于是有了下面这个黑盒自动化工具来帮助我们.

JMET(Java Message Exploitation Tool)

下载地址:https://github.com/matthiaskaiser/jmet

工具支持的应用:

 

\

 

实战

目标:

 

\

 

看看目前了解到的的信息

1.一个网络管理软件

2.运行在 Jboss 5上.

3.使用了HornetQ的 JMS实现方式

4.审计方式为 本地或者 LDAP

5.十分依赖 JMS
 

 

下面来看看JMS的攻击面:

 

\

 

可以看到实现了很多MessageLister 来监听消息,其中使用了TextMessage 和 ObjectMessage.下面看一个有漏洞的实现

 

\

 

这里调用了ObjectMessage.getObject(),那么上JMET,由于JBOSS’ HornetQ需要登录,这里提供了账号和密码.

 

\

 

然后服务器上就弹了一堆的计算器.

 

\

 

说明该程序存在漏洞

总结

1.和其他的依赖于Java序列化机制的东西一样,JMS也会受到反序列化漏洞的影响.

2.所有发现的有漏洞的JMS应用都缺少对数据输入的验证.

本文来源:SecYe安全网[http://www.secye.com] (责任编辑:SecYe安全)

点击复制链接 与好友分享!

顶一下
(0)
0%
踩一下
(0)
0%