| |||||||||
摘要: 嵌套 | 字段 | 构造方法 | 方法 | 详细信息: 字段 | 构造方法 | 方法 |
java.lang.instrument
接口 Instrumentation
public interface Instrumentation
此类提供检测 Java 编程语言代码所需的服务。检测是向方法中添加字节码,以搜集各种工具所使用的数据。由于更改完全是进行添加,所以这些工具不修改应用程序的状态或行为。这种无害工具的例子包括镜像代理、分析器、覆盖分析器和事件记录器。
获取 Instrumentation
接口的实例有两种方式:
当 JVM 以指示一个代理类的方式启动时,将传递给代理类的
premain
方法一个Instrumentation
实例。当 JVM 提供某种机制在 JVM 启动之后某一时刻启动代理时,将传递给代理代码的
agentmain
方法一个Instrumentation
实例。
这些机制在包规范中描述。
如果某个代理获得了 Instrumentation
实例,它便可以在任何时候调用该实例上的方法。
- 从以下版本开始:
- 1.5
方法摘要 | |
---|---|
void | addTransformer(ClassFileTransformer transformer) 注册提供的转换器。 |
void | addTransformer(ClassFileTransformer transformer, boolean canRetransform) 注册提供的转换器。 |
void | appendToBootstrapClassLoaderSearch(JarFile jarfile) 指定 JAR 文件,检测类由引导类加载器定义。 |
void | appendToSystemClassLoaderSearch(JarFile jarfile) 指定 JAR 文件,检测类由系统类加载器定义。 |
Class[] | getAllLoadedClasses() 返回 JVM 当前加载的所有类的数组。 |
Class[] | getInitiatedClasses(ClassLoader loader) 返回所有初始化加载器是 loader 的类的数组。 |
long | getObjectSize(Object objectToSize) 返回指定对象使用的特定于实现的近似存储量。 |
boolean | isModifiableClass(Class<?> theClass) 确定一个类是否可以被 retransformation 或 redefinition 修改。 |
boolean | isNativeMethodPrefixSupported() 返回当前 JVM 配置是否支持设置本机方法前缀。 |
boolean | isRedefineClassesSupported() 返回当前 JVM 配置是否支持类的重定义。 |
boolean | isRetransformClassesSupported() 返回当前 JVM 配置是否支持类的重转换。 |
void | redefineClasses(ClassDefinition... definitions) 使用提供的类文件重定义提供的类集。 |
boolean | removeTransformer(ClassFileTransformer transformer) 注销提供的转换器。 |
void | retransformClasses(Class<?>... classes) 重转换提供的类集。 |
void | setNativeMethodPrefix(ClassFileTransformer transformer, String prefix) 通过允许重试,将前缀应用到名称,此方法修改本机方法解析的失败处理。 |
方法详细信息 |
---|
addTransformer
void addTransformer(ClassFileTransformer transformer, boolean canRetransform)
- 注册提供的转换器。所有以后的类定义对于该转换器都是可见的,任何已注册转换器所依赖的类定义除外。 加载类、重定义类时将调用该转换器。如果
canRetransform
为 true,那么重转换类时也将调用该转换器。 有关转换调用的顺序,请参见ClassFileTransformer.transform
。 如果转换器在执行过程中抛出异常,JVM 将仍然按顺序调用其他已注册转换器。可以多次添加相同的转换器,但建议最好创建一个新的转换器类实例来避免这样做。此方法旨在用于检测,正如类规范所述。
- 参数:
transformer
- 要注册的转换器canRetransform
- 此转换器的转换是否可以重转换- 抛出:
NullPointerException
- 如果传递了null
转换器UnsupportedOperationException
- 如果canRetransform
为 true 但当前 JVM 的配置不允许重转换(isRetransformClassesSupported()
为 false)。- 从以下版本开始:
- 1.6
addTransformer
void addTransformer(ClassFileTransformer transformer)
- 注册提供的转换器。
与
addTransformer(transformer, false)
相同。 - 参数:
transformer
- 要注册的转换器- 抛出:
NullPointerException
- 如果传递了一个null
转换器- 另请参见:
addTransformer(ClassFileTransformer,boolean)
removeTransformer
boolean removeTransformer(ClassFileTransformer transformer)
- 注销提供的转换器。以后的类定义将不再向该转换器显示。移除最新添加的转换器的匹配实例。由于类加载的多线程特性,在调用被移除后,转换器还可能接收调用。所以编写转换器时应防止出现这种情况。
- 参数:
transformer
- 要注销的转换器- 返回:
- 如果找到并移除转换器,则返回 true;如果找不到转换器,则返回 false
- 抛出:
NullPointerException
- 如果传递了一个null
转换器
isRetransformClassesSupported
boolean isRetransformClassesSupported()
- 返回当前 JVM 配置是否支持类的重转换。 转换已加载类是 JVM 的一个可选性能。 仅当
Can-Retransform-Classes
清单属性在代理 JAR 文件中设置为true
(如包规范所述),且 JVM 支持此性能时,才支持重转换。 在单个 JVM 的单个实例化过程中,多次调用此方法将总是返回相同的答案。 - 返回:
- 如果当前 JVM 配置支持类的重转换,则返回 true;如果不支持,则返回 false。
- 从以下版本开始:
- 1.6
- 另请参见:
retransformClasses(java.lang.Class...)
retransformClasses
void retransformClasses(Class<?>... classes) throws UnmodifiableClassException
- 重转换提供的类集。
此函数为检测已加载类提供了方便。 当最初加载了类或重定义了类时,初始类文件字节可以使用
ClassFileTransformer
转换。 此函数返回转换进程(以前是否发生过转换)。 此转换按以下步骤进行:- 从初始类文件字节开始
- 对于每个添加时
canRetransform
设为 false 的转换器,上一次类加载或重定义期间transform
返回的字节将被重新用于转换的输出;注意,这等价于不做更改地重新应用前一个转换;没有调用transform
的情况除外。 - 对于每个添加时
canRetransform
设为 true 的转换器,在这些转换器中调用transform
方法 - 转换的类文件字节将作为类的新定义安装
转换的顺序在
transform
方法中描述。在自动重新应用不可重转换的转换时,也将使用这一顺序。最初的类文件字节表示(应用转换前)传递给
ClassLoader.defineClass
或redefineClasses
的字节,但有可能不完全匹配。常量池的布局或内容可能不同。常量池的条目可能多一些或少一些。常量池条目的顺序可能不同,但是,方法字节码中常量池的索引将是对应的。一些属性可能不存在。在顺序没有意义的地方(例如,方法的顺序),可能不保留顺序。此方法在一个集合上操作,以便允许同时对多个类进行相互依赖的更改(重转换类 A 要求重转换类 B)。
如果重转换的方法有活动的堆栈帧,那么这些活动的帧将继续运行原方法的字节码。重转换的方法将用于新的调用。
此方法不会引起任何初始化操作,JVM 惯例语义下发生的初始化除外。换句话说,重定义一个类不会引起其初始化方法的运行。静态变量的值将与调用之前的值一样。
重转换类的实例不受影响。
重转换可能会更改方法体、常量池和属性。重转换不得添加、移除、重命名字段或方法;不得更改方法签名、继承关系。在以后的版本中,可能会取消这些限制。在应用转换之前,类文件字节不会被检查、验证和安装。如果结果字节错误,此方法将抛出异常。
如果此方法抛出异常,则不会重转换任何类。
此方法旨在用于检测,正如类规范所述。
- 参数:
classes
- 要转换的类数组; 允许长度为 0 数组,在这种情况下,此方法不执行任何操作- 抛出:
UnmodifiableClassException
- 如果不能修改指定的类(isModifiableClass(java.lang.Class)
返回false
)UnsupportedOperationException
- 如果 JVM 的当前配置不允许重转换(isRetransformClassesSupported()
为 false),或者重转换试图做出不受支持的更改ClassFormatError
- 如果数据不包含有效的类NoClassDefFoundError
- 如果类文件中的名称不等于类的名称UnsupportedClassVersionError
- 如果类文件版本号不受支持ClassCircularityError
- 如果新类包含循环LinkageError
- 如果发生链接错误NullPointerException
- 如果提供的类数组或其任意组件为null
。- 从以下版本开始:
- 1.6
- 另请参见:
isRetransformClassesSupported()
,addTransformer(java.lang.instrument.ClassFileTransformer, boolean)
,ClassFileTransformer
isRedefineClassesSupported
boolean isRedefineClassesSupported()
- 返回当前 JVM 配置是否支持类的重定义。重定义已加载类是 JVM 的一个可选性能。 仅当
Can-Retransform-Classes
清单属性在代理 JAR 文件中设置为true
(如包规范所述),且 JVM 支持此性能时,才支持重转换。 在执行单个 JVM 的单实例化过程中,对此方法的多次调用将始终返回同一应答。 - 返回:
- 如果当前 JVM 配置支持类的重定义,则为 true,否则为 false。
- 另请参见:
redefineClasses(java.lang.instrument.ClassDefinition...)