基础知识

MQ(Message Queue):消息队列/消息中间件。消息服务将消息放在队列/主题中,在合适时候发给接收者。发送和接收是异步的(发送者和接收者的生命周期没有必然关系)。

  • 队列:消息存在队列中,发送和接收都是异步的
  • 主题:在发布pub/订阅sub模式下,发送消息给固定接收者(订阅过主题的),一对多的通信方式

MQ解决的问题:

  • 解耦:新模块接入时,代码改动最小
  • 消峰:设置流量缓冲池,让后端系统按照自身吞吐能力消费,不被冲垮
  • 异步:强弱依赖梳理能将非关键调用链路的操作异步化,并提升整体系统的吞吐能力

产品种类:Kafka, RabbitMQ, RocketMQ, ActiveMQ

ActiveMQ是美国阿帕奇(Apache)软件基金会所研发的一套开源的消息中间件,它支持Java消息服务、集群、Spring Framework等。

 

漏洞原理

该漏洞源于程序没有限制可在代理中序列化的类。远程攻击者可借助特制的序列化的Java Message Service(JMS)ObjectMessage对象利用该漏洞执行任意代码。

 

影响版本 

5.13.0之前5.x版本

 

复现环境

将ActiveMQ部署在MAC上,使用版本为apache-activemq-5.11.1,MAC上有JDK1.7和JDK1.8两个版本(应使用JDK1.7)。

漏洞利用库jmet-0.1.0-all.jarhttps://github.com/matthiaskaiser/jmet

 

复现过程

参考教程:https://github.com/vulhub/vulhub/blob/master/activemq/CVE-2015-5254/README.zh-cn.md

1. 安装和启动ActiveMQ

  • 解压:tar -zxvf apache-activemq-5.11.0-bin.tar.gz,新建文件夹myactiveMQ,把解压的压缩包pache-activemq-5.11.0拷过去
  • 终端进入myactiveMQ/pache-activemq-5.11.0/bin
  • 启动命令:./activemq start (默认端口61616

    漏洞复现 - ActiveMQ反序列化漏洞(CVE-2015-5254)

     漏洞复现 - ActiveMQ反序列化漏洞(CVE-2015-5254)

2. 写code给ActiveMQ发送和接收消息(为了加深理解,不是必须步骤)

消息发送方:

漏洞复现 - ActiveMQ反序列化漏洞(CVE-2015-5254)
import org.apache.activemq.ActiveMQConnectionFactory;

import javax.jms.*;

public class JmsProduce {

    public static final String ACTIVEMQ_URL="tcp://localhost:61616";
    public static final String QUEUE_NAME="queue01";

    public static void main(String[] args) throws JMSException {

        //采用默认用户名和密码
        ActiveMQConnectionFactory activeMQConnectionFactory = new ActiveMQConnectionFactory(ACTIVEMQ_URL);
        Connection connection = activeMQConnectionFactory.createConnection();
        connection.start();

        Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
        Queue queue = session.createQueue(QUEUE_NAME);

        MessageProducer messageProducer = session.createProducer(queue);
        //使用messageProducer生产3条消息发送到MQ队列
        for (int i=0;i<3;i++){
            TextMessage textMessage=session.createTextMessage("msg----"+i);
            messageProducer.send(textMessage);
        }

        messageProducer.close();
        session.close();
        connection.close();

        System.out.println("******消息发布到MQ完成******");
    }
}
View Code

相关文章: