Loading

URLDNS反序列化漏洞

URLDNS外带反序列化:

写一个简单的demo:

package org.example.demo1;


import java.io.*;

import java.net.URL;
import java.util.HashMap;

public class UrlDns implements Serializable {
    public static void main(String[] args) throws IOException, ClassNotFoundException {
        HashMap<URL, Object> map = new HashMap<>();
        map.put(new URL("http://127.0.0.1:8080/"), new Object());//此处做测试,域名为什么不重要,关键是跟进观察
        FileOutputStream fos = new FileOutputStream("url.bin");
        ObjectOutputStream oos = new ObjectOutputStream(fos);
        oos.writeObject(map);
        oos.flush();
        oos.close();
        fos.close();
        FileInputStream fis = new FileInputStream("url.bin");
        ObjectInputStream ois = new ObjectInputStream(fis);
        Object obj = ois.readObject();
        ois.close();
        fis.close();


    }

}

debug调试:

向hashmap中添加一条键值对,包括了url和一个不重要的对象

然后跳转到了:

该方法用于将指定的键值对存入HashMap中。

首先调用hash(key)计算键的哈希值;

然后调用putVal方法完成实际的插入操作;

如果键已存在,则旧值被替换;

返回与键关联的旧值,若不存在则返回null。

关键点在于调用了hash(key),这个方法,先跟进继续看,进入hash()

这段的意思是:

若 key 为 null,返回 0;

否则,先获取 key 的 hashCode() 值 h;

然后将 h 与 h 无符号右移 16 位后的结果进行异或运算,以打散高位影响,提升哈希分布均匀性。

由于传进来的key就是我们要解析的域名,并且不为空,所以会走hashcode()这个函数

所以接着跟进hashcode()

该方法用于计算URL对象的哈希码。

如果已计算过哈希码(hashCode != -1),直接返回缓存的结果;

否则,通过URL的协议处理器(handler)计算哈希码,并缓存该结果以供后续使用。

由于我们之前并没有计算过,所以会通过URL的协议处理器(handler)计算哈希码,

也就是说会调用hashCode = handler.hashCode(this);

所以跟进hashCode():

如果URL对象已缓存了IP地址(hostAddress),则直接返回;

否则获取URL的主机名(host);

若主机名为空或null,返回null;

否则通过InetAddress.getByName()解析主机名为IP地址,并缓存;

解析失败(如DNS异常或权限不足)则返回null。

关键点来了解析了主机名为ip地址,也就是说可以触发dns解析,来造成dnslog外带!!!!

流程:

ObjectInputStream.readObject()
  → HashMap.readObject()
    → HashMap.putVal()
      → HashMap.hash()
        → URL.hashCode()
          → URLStreamHandler.hashCode()
            → URLStreamHandler.getHostAddress()
              → InetAddress.getByName()  // 触发DNS查询

有一个注意点,在自己写脚本测试的时候,可以使用反射修改hashCode的值,使其不等于-1

为什么要先修改 url 内的 hashCode 在将 url 存到 HashMap 内呢?答案就在上面,如果不设置 hashCode 不为 -1 的话,那么存入 hashMap 的时候就会触发一次 hash(key),也就是本地生成 poc 会执行一次 DNS请求,这会对我们的判断造成影响,所以要先设置其不为 -1 ,存入 hashMap 以后再将其变回来,这样只会执行一次 DNS 了

posted @ 2025-07-16 16:13  赟希  阅读(9)  评论(0)    收藏  举报