jvm15版本源码阅读之从universe_init到init_globals的剩余部分
- 1 从universe_init开始到init_globals结束
- 1.1 gc_barrier_stubs_init
- 1.2 interpreter_init_stub
- 1.3 accessFlags_init
- 1.4 InterfaceSupport_init
- 1.5 universe2_init
- 1.6 javaClasses_init
- 1.7 interpreter_init_code
- 1.8 invocationCounter_init
- 1.9 referenceProcessor_init
- 1.10 jni_handles_init
- 1.11 vmStructs_init
- 1.12 vtableStubs_init
- 1.13 InlineCacheBuffer_init
- 1.14 compilerOracle_init
- 1.15 dependencyContext_init
- 1.16 stubRoutines_init2
- 1.17 MethodHandles::generate_adapters
- 2 小结
由于universe_init比较大,所以单独分析.这之后就是从universe_init往后到init_globals的结束了.
1 从universe_init开始到init_globals结束
1.1 gc_barrier_stubs_init
GC中的屏障初始化,比如在zgc中就是用了读屏障.
1.2 interpreter_init_stub
解释器的引用初始化.
1.3 accessFlags_init
获取权限初始化,比如public,private等.
1.4 InterfaceSupport_init
接口的额外支持的初始化,主要针对ASSERT来说.
1.5 universe2_init
类似universe_init的初始化,只是这里涉及的内容比较少,进入该方法
进入Universe::genesis方法
主要两部分,第一部分是一个代码段,之后是_objectArrayKlassObj的赋值.
1 代码段
首先java_lang_Class::allocate_fixup_lists方法设定了固定的列表,主要是包括模块等在内的固定参数.其次compute_base_vtable_size方法计算了虚表的基础大小,然后MetadataFactory::new_array方法初始化了一些比如Klass和InstanceKlass的数组,初始大小都为0.之后vmSymbols::initialize方法初始化了vm符号系统,SystemDictionary::initialize方法初始化了系统的字典,主要内容就是设置类型和其偏移量,比如invoke_method_table代表的调用表,同时也解析和设置了常用类型,包括基本类型,软引用类型,弱饮用类型等,之后为各个组成设置偏移量,比如class字节码中类和引用的偏移量.最后调用initialize_basic_type_klass初始化基本类型.
2 _objectArrayKlassObj的赋值
同时使用了新的和老的赋值方式,新的方式如下
老的方式如下
1.6 javaClasses_init
有关java的class文件初始化,进入该方法
首先是对java计算得到class文件中各个类的偏移量,之后进行了校验,最后根据常量池的偏移量把class文件中的常量值放入池中,至此常量池生成.
1.7 interpreter_init_code
解释器的初始化代码,主要是和检查点等的结束和开始的位置有关.
1.8 invocationCounter_init
方法调用计数器初始化.
1.9 referenceProcessor_init
引用处理的初始化,主要是和软引用,弱引用的处理有关.
1.10 jni_handles_init
Jni的调用初始化.
1.11 vmStructs_init
VM结构的初始化,主要是校验一些基本设置和数据就够是否正确.
1.12 vtableStubs_init
虚表中有关调用的初始化
1.13 InlineCacheBuffer_init
内联缓存初始化
1.14 compilerOracle_init
编译器初始化,主要针对命令行和文件的编译.
1.15 dependencyContext_init
依赖的上下文初始化.
1.16 stubRoutines_init2
调用的第二次初始化,和第一次一样,只是由于之前有了解释器和编译器等需要调用的组件的加入,这里就再次生成一遍.
1.17 MethodHandles::generate_adapters
方法的处理代理生成,可以看成是方法主体逻辑的封装,供外部直接调用.
2 小结
至此,全局部分的初始化init_globals已经完成,主要初始化的内容有
1 堆的初始化
2 class文件中各个元素,包括类,引用及常量池的字典生成
3 方法引用或者调用的包装器的生成
至此主体的初始化部分已经完成,接下来就是init_globals之后的初始化方法了.