首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

当使用ASM访问一个类时,如何在不加载任何类的情况下知道该类的祖先类?

当使用ASM访问一个类时,可以通过ASM提供的ClassVisitor类来获取类的祖先类信息,而无需加载任何类。

具体步骤如下:

  1. 创建一个自定义的ClassVisitor类,继承自ASM的ClassVisitor类。
  2. 在自定义的ClassVisitor类中重写visit方法,该方法会在访问到类的头部时被调用。
  3. 在visit方法中,通过调用super.visit方法,将访问控制权交给父类的visit方法。
  4. 在自定义的ClassVisitor类中重写visitMethod方法,该方法会在访问到类的方法时被调用。
  5. 在visitMethod方法中,通过调用super.visitMethod方法,将访问控制权交给父类的visitMethod方法。
  6. 在自定义的ClassVisitor类中重写visitField方法,该方法会在访问到类的字段时被调用。
  7. 在visitField方法中,通过调用super.visitField方法,将访问控制权交给父类的visitField方法。
  8. 在自定义的ClassVisitor类中重写visitInnerClass方法,该方法会在访问到类的内部类时被调用。
  9. 在visitInnerClass方法中,通过调用super.visitInnerClass方法,将访问控制权交给父类的visitInnerClass方法。
  10. 在自定义的ClassVisitor类中重写visitOuterClass方法,该方法会在访问到类的外部类时被调用。
  11. 在visitOuterClass方法中,通过调用super.visitOuterClass方法,将访问控制权交给父类的visitOuterClass方法。
  12. 在自定义的ClassVisitor类中重写visitSource方法,该方法会在访问到类的源文件时被调用。
  13. 在visitSource方法中,通过调用super.visitSource方法,将访问控制权交给父类的visitSource方法。
  14. 在自定义的ClassVisitor类中重写visitAnnotation方法,该方法会在访问到类的注解时被调用。
  15. 在visitAnnotation方法中,通过调用super.visitAnnotation方法,将访问控制权交给父类的visitAnnotation方法。
  16. 在自定义的ClassVisitor类中重写visitTypeAnnotation方法,该方法会在访问到类的类型注解时被调用。
  17. 在visitTypeAnnotation方法中,通过调用super.visitTypeAnnotation方法,将访问控制权交给父类的visitTypeAnnotation方法。
  18. 在自定义的ClassVisitor类中重写visitAttribute方法,该方法会在访问到类的属性时被调用。
  19. 在visitAttribute方法中,通过调用super.visitAttribute方法,将访问控制权交给父类的visitAttribute方法。
  20. 在自定义的ClassVisitor类中重写visitEnd方法,该方法会在访问到类的结束时被调用。
  21. 在visitEnd方法中,通过调用super.visitEnd方法,将访问控制权交给父类的visitEnd方法。

通过以上步骤,我们可以在不加载任何类的情况下,使用ASM访问一个类,并获取其祖先类的信息。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

从Java加载机制谈起:聊聊Java中如何实现热部署(热加载

本文将探索如何在破坏 Java 虚拟机现有行为前提下,实现某个单一热部署,让系统无需重启就完成某个更新。...目前加载机制,称为双亲委派,系统在使用一个 classloader 来加载,会先询问当前 classloader 是否有能力加载,如果父无法实现加载操作,才会将任务下放到该 classloader...这里有一个小技巧,让每次加载都保存成一个带有版本信息 class,比如加载 Test.class ,保存在内存中是 Test_v1.class,发生改变,重新加载名是 Test_v2...这样的话,我们就可以使用JRuby所做相同转换来把所有的Java分割成持有者和方法体。不幸是,这样一种做法会遭受(至少是)如下问题: 性能。...例如,我们支持动态实时地在Spring中添加bean和依赖,以及支持在其他框架中所做各种各样改变。 结论 本文总结了在未使用动态加载情况下各种重载Java方法。

3.2K20
  • JVM系列(1) JVM内存模型,双亲委派机制和沙箱安全机制

    OOM了,那么要知道怎么引起,理解JVM内存模型,有助于我们在编码避免一些坑。...来实现,它负责加载用户路径(ClassPath)所指定,开发者可以直接使用该类加载器,如果应用程序中没有自定义过自己加载器,一般情况下这个就是程序中默认加载器。...,因此,所有的加载请求最终都应该被传递到顶层启动加载器(Bootstrap ClassLoader)中,只有当父加载器在它搜索范围中没有找到所需,即无法完成该加载,子加载器才会尝试自己去加载该类...具体流程 1.AppClassLoader加载一个class,它不会尝试加载这个,而是把加载请求委派给父加载器ExtClassLoader去完成。...3.BootstrapClassLoader加载到这个.class,它会查找该类是否存在,如果不存在,就往下传递,交给ExtClassLoader,如果ExtClassLoader在自己相应包中也没找到对应

    26620

    Java字节码增强探秘

    2.1.2 直接利用ASM实现AOP 利用ASMCoreAPI来增强。这里纠结于AOP专业名词切片、通知,只实现在方法调用前、后增加逻辑,通俗易懂且方便理解。...这期间并不涉及到JVM运行时对加载,而是在第一个Main方法中,通过ASM对已编译字节码进行替换,在第二个Main方法中,直接使用已替换好信息。...另外在Javassist实现中,我们也只加载了一次Base,也涉及到运行时重加载。 如果我们在一个JVM中,先加载一个,然后又对其进行字节码增强并重新加载会发生什么呢?...这样,Agent被Attach到一个JVM中,就会执行字节码替换并重载入JVM操作。...如果JVM启动开启了JPDA,那么是允许被重新加载。在这种情况下,已被加载旧版本类信息可以被卸载,然后重新加载新版本

    1.9K51

    Java字节码增强探秘

    2.1.2 直接利用ASM实现AOP 利用ASMCoreAPI来增强。这里纠结于AOP专业名词切片、通知,只实现在方法调用前、后增加逻辑,通俗易懂且方便理解。...这期间并不涉及到JVM运行时对加载,而是在第一个Main方法中,通过ASM对已编译字节码进行替换,在第二个Main方法中,直接使用已替换好信息。...另外在Javassist实现中,我们也只加载了一次Base,也涉及到运行时重加载。 如果我们在一个JVM中,先加载一个,然后又对其进行字节码增强并重新加载会发生什么呢?...这样,Agent被Attach到一个JVM中,就会执行字节码替换并重载入JVM操作。...如果JVM启动开启了JPDA,那么是允许被重新加载。在这种情况下,已被加载旧版本类信息可以被卸载,然后重新加载新版本

    1K20

    探索 Java 热部署奥妙

    本文将探索如何在破坏 Java 虚拟机现有行为前提下,实现某个单一热部署,让系统无需重启就完成某个更新。...目前加载机制,称为双亲委派,系统在使用一个 classloader 来加载,会先询问当前 classloader 是否有能力加载,如果父无法实现加载操作,才会将任务下放到该 classloader...不过我们可以换一个思路,虽然无法抢先加载该类,但是仍然可以用自定义 classloader 创建一个功能相同,让每次实例化对象都指向这个新。...改变创建对象行为,使他们在创建使用自定义 classloader 加载 class。 自定义加载实现 自定义加载器仍然需要执行加载功能。...这里有一个小技巧,让每次加载都保存成一个带有版本信息 class,比如加载 Test.class ,保存在内存中是 Test_v1.class,发生改变,重新加载名是 Test_v2

    83150

    JVM 看这一篇就够了

    ASM文件中读入信息后,能够改变行为,分析信息,甚至能根据要求生成新 目前许多框架 cglib、Hibernate、spring 都直接或间接地使用ASM操作字节码 ASM编程模型 Core...程序对使用方式分成:主动使用和被动使用,JVM 必须在每个或接口 ”首次主动使用才初始化它们;被动使用不会导致初始化,主动使用情况: 创建实例 访问某个或接口静态变量 调用静态方法...JVM 中该类所有实例都已经被回收 加载该类 ClassLoader 已经被回收 没有任何地方引用该类 Class 对象 无法在任何地方通过反射访问这个 垃圾回收算法 标记清除算法 标记清除算法...目前这两个方法性能已经差不多了,建议优先选用 synchronized,ReentrantLock 增加了如下特性: 等待可中断:持有锁线程长时间释放锁,正在等待线程可以选择放弃等待 公平锁:多个线程等待同一个...只要没有竞争,获得偏向锁线程,在将来进入同步块,也不需要做同步 有其他线程请求相同,偏向模式结束 如果程序中大多数锁总是被多个线程访问时候,也就是竞争比较激烈,偏向锁反而会降低性能 使用

    50420

    2.2 ASM--接口和组件

    在这个示例中是null,因为接口没有参数化类型变量。 第五个参数是父使用内部名格式(接口隐式继承Object)。 最后一个参数是一个数组表示该类实现接口,使用内部名格式。...最后一个参数指定了可能被该方法抛出exception数组,使用内部名格式。这里是null,因为该方法抛出任何异常。...使用生成 上面生成byte数组可以保存到Comparable.class文件中,以便后续使用。 另外,该数组也可以被ClassLoader动态加载。...这种情况下,ClassReader组件不解些方法内容,也生成相应event,仅仅把表示该方法byte数组拷贝到ClassWriter中。...使用转换后class 在上一个部分,我们介绍了转换后class b2 可以被存储在硬盘上,或者被一个ClassLoader加载

    1.3K10

    深入探索 Java 热部署

    本文将探索如何在破坏 Java 虚拟机现有行为前提下,实现某个单一热部署,让系统无需重启就完成某个更新。...目前加载机制,称为双亲委派,系统在使用一个 classloader 来加载,会先询问当前 classloader 是否有能力加载,如果父无法实现加载操作,才会将任务下放到该 classloader...不过我们可以换一个思路,虽然无法抢先加载该类,但是仍然可以用自定义 classloader 创建一个功能相同,让每次实例化对象都指向这个新。...改变创建对象行为,使他们在创建使用自定义 classloader 加载 class。 自定义加载实现 自定义加载器仍然需要执行加载功能。...这里有一个小技巧,让每次加载都保存成一个带有版本信息 class,比如加载 Test.class ,保存在内存中是 Test_v1.class,发生改变,重新加载名是 Test_v2

    1K10

    Java成神路 —— 加载

    1.1 加载 1. 加载描述 程序要使用某个,如果该类还未被加载到内存中,则系统会通过加载连接,初始化这三个步骤来对进行初始化。...加载 就是指将class文件读入内存,并为之创建一个 java.lang.Class 对象 任何使用时,系统都会为之建立一个 java.lang.Class 对象 3....初始化时机 创建实例 调用方法 访问或者接口变量,或者为该类变量赋值 使用反射方式来强制创建某个或接口对应java.lang.Class对象 初始化某个子类 直接使用java.exe...JVM加载机制 全盘负责:一个加载器负责加载某个Class,该Class所依赖和引用其他Class也将由该类加载器负责载入,除非显示使用另外一个加载器来载入 父委托:一个加载器负责加载某个...Class,先让父加载器试图加载该Class,只有在父加载器无法加载该类才尝试从自己路径中加载该类 缓存机制:保证所有加载Class都会被缓存,程序需要使用某个Class对象加载器先从缓存区中搜索该

    15410

    C++8种常见类型

    类型 描述 具体 独立;表示一个祖先-后代世系终止结束 抽象 为所有的子类提供布局和蓝图基准,不能声明此类对象;必须派生新,对抽象基本中声明任何虚函数提供定义 接口 用于修改或者增强另外一个得接口...,默认情况下,抽象至少需要一个后代,才可以发挥出作用。...2、受保护(protected) 3、公有(public) 其中: 1、数据成员和成员函数为私有的,它们仅仅只能被中间成员函数访问,无法被非该类成员函数所访问; 2、成员函数和数据成员为受保护...,它们可以被中间成员和该类所有后代所访问,但该类之外函数无法访问 3、可以将成员函数和数据成员声明为公有的,则不管是什么成员,都可以访问被定义为public接口和成员 例如以下,这可以保护敏感函数或者变量...节点是继承和多态基础,与抽象一样,节点设计用于继承,但是不同是,节点包含纯抽象函数,其可以直接使用

    80810

    Java学习知识笔记

    (防止实现多个接口时候实现知道调用是哪个接口静态方法),对于接口中有两个及以上方法包含相同代码段使用private方法实现代码复用java9特性。...,如果该类还未被加载到内存中,则系统会通过加载连接,初始化这三个走来对进行初始化,如果不出现意外情况,jvm会连续完成这三个走。...调用方法或者创建实例或者访问变量或者接口变量,或者为变量复制,初始化某个子类 JVM加载机制: 1 全盘负责:一个加载器来加载某个class,该class所以来和引用其他...class也将由该类加载器负责载入,除非显示使用另外一个加载器来载入 2 父委托:就是一个加载器负责加载某个class,先让父加载器驶入加载class,只有父加载器无法加载该类才尝试从自己路径来加载该类..., 3 缓存机制:保证所有加载class都会被缓存,程序需要使用某个class对象加载器先从缓存区搜索该class,只由缓存区不存在该class对象,系统才会读取该类对应二进制数据,

    8210

    web安全防御之RASP技术

    b.初始化字节码转换模块给load class 操作进行插桩操作,加载时候会先进入 agent 进行处理hook指定函数。 3.架构大致如图2所示,具体技术细节后续分析。...图4 a.因为启动时候进行了插桩操作,被 ClassLoader 加载时候,所以会把该类字节码先交给自定义 Transformer 处理 b....自定义 Transformer 会判断该类是否为需要 hook ,如果是会将该类交给ASM字节码处理框架进行处理。 c....ASM框架会将字节码依照事件驱动模型逐步解析每个方法,触发了我们需要hook方法,我们会在方法开头或者结尾插入进入检测函数字节码 d..../p/8633660.html 4.一个简单RASP实现与攻击测试 上面我们已经大致了解了整体框架流程,知道了要实现JavaRASP所要具备能力和技术,在Java中有Javassist、与ASM可以实现对

    5.7K31

    加载原理解析与实现

    系统在使用一个 classloader 来加载,会先询问当前 classloader 是否有能力加载,如果父无法实现加载操作,才会将任务下放到该 classloader 来加载。...虽然,无法抢先加载该类,但是仍然可以用自定义 classloader 创建一个功能相同,让每次实例化对象都指向这个新。...图片默认情况下(即使用关键字new或者Class.forName)都是通过AppClassLoader加载器来加载。...,然后通过反射生成对象使用ASM修改class文件;重定义原始,先将原来变成接口每次变更,需要重新new一个加载器,开销太大使用ASM修改class文件;让每次加载都保存成一个带有版本信息...(5) 替换 class虽然,无法抢先加载该类,可以利用 JavaAgent拦截默认加载器,使用自定义 classloader 创建一个功能相同,替换默认加载class文件,让每次实例化对象都指向这个新

    5.3K30

    快速理解 Java 静态代理 动态代理

    理解Java动态代理需要对Java反射机制有一定了解 什么是代理模式 在有些情况下一个客户不能或者不想直接访问一个对象,这时需要找一个中介帮忙完成某项任务,这个中介就是代理对象。...其他方案 使用ASM在被代理基础上生成新字节码形成代理 使用javassist在被代理基础上生成新字节码形成代理 javassist也是常用一种动态代理方案,ASM速度非常快,这里不在进行展开...spring等这样框架,要增强具体业务逻辑方法,不可能在框架里面去写一个静态代理,太蠢了,只能按照用户注解或者xml配置来动态生成代理。...业务代码内,需要增强业务逻辑非常通用(:添加log,重试,统一权限判断等)使用动态代理将会非常简单,如果每个方法增强逻辑不同,那么静态代理更加适合。...使用静态代理,如果代理和被代理类同时实现了一个接口,接口方法有变动,代理也必须同时修改,代码将变得臃肿且难以维护。

    33830

    C++复习笔记——C++ 关键字

    export 为了访问其他编译单元(另一代码文件)中变量或对象,对普通类型(包括基本数据、结构和),可以利用关键字 extern,来使用这些变量或对象;但是对模板类型,则必须在定义这些模板对象和模板函数...模板参数使编译器在指认一个类型产生了误解。 class class()是 C++ 面向对象设计基础。使用class关键字声明一个。 for for是 C++ 中循环结构之一。...在 C++ 成员变量被声明为static(称为静态成员变量),意味着它被该类所有实例所共享,也就是说某个实例修改了该静态成员变量,其修改值为该类其它所有实例所见;而静态成员函数也只能访问静态成员...静态成员变量必须在声明它文件范围内进行初始化才能使用,private类型例外。...void void(空),可以作为函数返回值,表明返回任何数据;可以作为参数,表明没有参数传入(C++中不是必须);可以作为指针使用

    1.3K30

    【问底】静行:FastJSON实现详解

    SerializeConfig主要功能是配置并记录每种Java类型对应序列化(ObjectSerializer接口实现),比如Boolean.class使用BooleanCodec(看命名就知道该类将序列化和反序列化实现写到一起了...,或者clazz就是Object.class JSONType注解指明不适用ASM createASMSerializer加载失败 结合前面的讨论,可以得出使用ASM条件:非Android系统、非基础...与SerializeConfig不同是,配置和对应反序列IdentityHashMap是该类私有成员,构造函数时候就将基础反序列化加载进入IdentityHashMap中。 2....使用asm条件如下: 非Android系统 该类及其除Object之外所有父为是public 泛型参数非空 非asmFactory加载器之外加载加载 非接口 setter函数不大于...走寻常路 对于JavaBean,可以通过发射实现序列化和反序列化(FastJSON已有实现),但默认使用ASM框架生成对应字节码。为了性能,无所不用其极。 5.

    1.5K70

    万字总结——反射(框架之魂)

    如果我们没有Orange,那该类在编译时候就会报错找不到该类。这是我们平常使用“正射”。这个名字是为了和反射相对应,不是官方术语。 ?...答 优势: 在编译根本无法知道该对象或可能属于哪些,程序只依靠运行时信息来发现该对象和真实信息。反射提高了Java程序灵活性和扩展性,降低耦合性,提高自适应能力。...它允许程序创建和控制任何对象,无需提前硬编码目标。 劣势: 使用反射基本上是一种解释操作,用于字段和方法接入时要远慢于直接代码。...综上,大部分我们使用反射是不考虑性能,平常使用次数较少,如果真的遇到性能问题,反射效率影响到程序逻辑,可以采用缓存或Java字节码增强技术,参照库有asm,也有第三方工具库reflectAsm(...为了权衡两个版本性能,SunJDK使用了“inflation”技巧:让Java方法在被反射调用时,开头若干次使用native版,等反射调用次数超过阈值则生成一个专用MethodAccessor

    80720

    JDK1.9-static关键字

    1.2 定义和使用格式 变量 static修饰成员变量,该变量称为变量。该类每个对象都共享同一个变量值。...任何对象都可以更改该类变量值,但也可以在创建该类对象情况下变量进行操作。 变量:使用 static关键字修饰成员变量。...静态方法 static修饰成员方法,该方法称为方法 。静态方法在声明中有,建议使用名来调用,而不需要创建对象。调用方式非常简单。...调用格式: 被static修饰成员可以并且建议通过名直接访问。虽然也可以通过对象名访问静态成员,原因即多个对象均属 于一个,共享使用一个静态成员,但是建议,会出现警告信息。 格式: ?...作用:给变量进行初始化赋值。用法演示,代码如下: ? 小贴士: static 关键字,可以修饰变量、方法和代码块。在使用过程中,其主要目的还是想在创建对象情况下,去调用方法。

    29330
    领券