谁在 class-loading 过程中首先创建了 Class<?> 对象?
Who firstly creates Class<?> object during class-loading process?
在 documentation 我发现:
Class objects are constructed automatically by the Java Virtual
Machine as classes are loaded and by calls to the defineClass method
in the class loader.
我检查了 the source code,但没有找到要调用的地方 defineClass
例如从 loadClass 方法。
请告诉我谁以及何时根据此方案调用 defineClass
方法:
图片source
defineClass()
方法在调用ClassLoader#loadClass()
的过程中被调用。但是,这不是直接在 java.lang.ClassLoader
class 中完成的,而是在其子 class 之一中完成的,例如在 URLClassLoader#findClass()
.
对 ClassLoader#defineClass()
的调用以对 native 方法之一的调用结束 defineClass1()
or defineClass2()
. The C implementations of these methods can be found in OpenJDK in src/share/native/java/lang/ClassLoader.c
.
java.lang.ClassLoader
这么大class。使用您的 GrepCode link( 用于 java 6-b14 版本 ),您可以在第 267 行找到 public loadClass
方法.
此方法在第 308 行调用受保护的 loadClass
方法,此方法尝试使用以下方法加载先前加载的 class:
findLoadedClass
最终调用 Native 方法,
- 呼叫
parent.loadClass
,
findBootstrapClass0
(一个native方法也是)如果没有parent
,
- 最后
findClass
如果没有找到 class。
这一点很重要,因为 ClassLoader
会尝试重用已加载的类,请记住。
但是,defineClass
在哪里调用?这个摘要没有地方 class,但是如果你使用 GrepCode 的参考工具并搜索它被使用的地方 defineClass
(see here results) 你会发现很多具体的 classes最后调用 definClass
.
这并不简单,其中一些 class 会覆盖 defineClass
而其他人会调用自己的 loadClass
然后调用 ... 等等,但最终它会调用defineClass
.
不要忘记 ClassLoader
的 defineClass
以负责 JVM magic 的三个本机方法之一结束:defineClass0
, defineClass1
and/or defineClass2
编辑
本机函数 defineClass0
从 ClassLoader.c
调用 Java_java_lang_ClassLoader_defineClass0
,函数 1 和函数 2 也是如此。
此函数使用 jvm.h
中定义并在 openjdk\hotspot\src\share\vm\prims\jvm.cpp
中实现的 JVM_DefineClassWithSource
创建所需的 class。
最后一个文件定义了 jvm_define_class_common
函数,它最终是创建所需 class 的函数。最后,这个函数调用 JNIHandles::make_local
来分配 class。您可以在 openjdk\hotspot\src\share\vm\runtime\jniHandles.cpp
中查看最后一个函数的代码
希望它能回答您的问题。
class NetworkClassLoader extends ClassLoader {
String host;
int port;
public Class findClass(String name) {
byte[] b = loadClassData(name);
return defineClass(name, b, 0, b.length);
}
private byte[] loadClassData(String name) {
// load the class data from the connection
. . .
}
}
在 documentation 我发现:
Class objects are constructed automatically by the Java Virtual Machine as classes are loaded and by calls to the defineClass method in the class loader.
我检查了 the source code,但没有找到要调用的地方 defineClass
例如从 loadClass 方法。
请告诉我谁以及何时根据此方案调用 defineClass
方法:
图片source
defineClass()
方法在调用ClassLoader#loadClass()
的过程中被调用。但是,这不是直接在 java.lang.ClassLoader
class 中完成的,而是在其子 class 之一中完成的,例如在 URLClassLoader#findClass()
.
对 ClassLoader#defineClass()
的调用以对 native 方法之一的调用结束 defineClass1()
or defineClass2()
. The C implementations of these methods can be found in OpenJDK in src/share/native/java/lang/ClassLoader.c
.
java.lang.ClassLoader
这么大class。使用您的 GrepCode link( 用于 java 6-b14 版本 ),您可以在第 267 行找到 public loadClass
方法.
此方法在第 308 行调用受保护的 loadClass
方法,此方法尝试使用以下方法加载先前加载的 class:
findLoadedClass
最终调用 Native 方法,- 呼叫
parent.loadClass
, findBootstrapClass0
(一个native方法也是)如果没有parent
,- 最后
findClass
如果没有找到 class。
这一点很重要,因为 ClassLoader
会尝试重用已加载的类,请记住。
但是,defineClass
在哪里调用?这个摘要没有地方 class,但是如果你使用 GrepCode 的参考工具并搜索它被使用的地方 defineClass
(see here results) 你会发现很多具体的 classes最后调用 definClass
.
这并不简单,其中一些 class 会覆盖 defineClass
而其他人会调用自己的 loadClass
然后调用 ... 等等,但最终它会调用defineClass
.
不要忘记 ClassLoader
的 defineClass
以负责 JVM magic 的三个本机方法之一结束:defineClass0
, defineClass1
and/or defineClass2
编辑
本机函数 defineClass0
从 ClassLoader.c
调用 Java_java_lang_ClassLoader_defineClass0
,函数 1 和函数 2 也是如此。
此函数使用 jvm.h
中定义并在 openjdk\hotspot\src\share\vm\prims\jvm.cpp
中实现的 JVM_DefineClassWithSource
创建所需的 class。
最后一个文件定义了 jvm_define_class_common
函数,它最终是创建所需 class 的函数。最后,这个函数调用 JNIHandles::make_local
来分配 class。您可以在 openjdk\hotspot\src\share\vm\runtime\jniHandles.cpp
希望它能回答您的问题。
class NetworkClassLoader extends ClassLoader {
String host;
int port;
public Class findClass(String name) {
byte[] b = loadClassData(name);
return defineClass(name, b, 0, b.length);
}
private byte[] loadClassData(String name) {
// load the class data from the connection
. . .
}
}