JVM(一)

来源:互联网 发布:山西省建筑业企业网络 编辑:程序博客网 时间:2024/06/16 11:19

JVM(一)

JVM JAVA的虚拟机,包含PC寄存器、本地方法栈、JAVA栈,JAVA堆、方法区,常量池,JAV之所以能跨平台、跨系统无障碍运行,是因为JAVA虚拟机将JAVA的字节码翻译成机器识别的机器码。

  • 包含PC寄存器
  • 本地方法栈
  • JAVA栈
  • *JAVA堆
  • 方法区
  • 常量池

PC寄存器

PC寄存器保存正在执行的方法对应的字节码地址,每个线程都有一个PC寄存器

JAVA虚拟机支持多个线程同时运行,每个虚拟机线程当前时间只能执行一个方法,每个线程都包含PC寄存器,寄存器保存正在执行的方法的字节码地址。如果当前方法是本地方法(NATIVE),那么PC寄存器值就是Undefined。

JAVA虚拟栈

栈存储了局部变量和未完成计算的结果,JAVA虚拟机栈也叫堆栈,相对于虚拟机来说,虚拟机是一个应用程序,所以JAVA的栈其实是虚拟机的堆中分配的。

  • 栈桢

JAVA虚拟机是由其它语文编写,所以JAVA的栈也就是相对虚拟机的堆 ,JAVA虚拟栈是在每人线程创建的时候创建了对应的栈,用于存储局部变量和没有计算好的结果。虚拟机的栈的可以配置成固定大小或动态扩展和收缩。
配置成固定大小时,当申请的栈超过允许最大容量时有可能抛出异常:StackOverFlorError.
配置成动态时,当JVM的栈无法满足申请栈需要的容易时会抛出OutOfMemoryError.

-Xss 参数可以废置每个栈的固定大小,需谨慎申请栈最大容量执行出来StackOverFlorError.

栈存储的是栈桢,栈桢在方法创建的时候创建,栈桢包含了本地方法变量表、操作数栈、动态链,栈桢的操作数栈、本地方法变量表是在编译时就已经分配好的。

在同一个线程只有一个栈桢是活动的,也就是当前栈桢,当调用新的方法时新的栈桢产生,新的栈桢则为当前栈桢。每个栈桢是私有的,不可和其它线程的栈桢互通访问

  • 本地方法变量
  • 操作数栈
  • 动态链

本地方法变量
存储了方法的调用参数,本地方法的是用的索引位存储传递参数,索引位0 表示this,对象的本身实例,对于Long 、Double使用了两个索引位来存储,比如索n存储了Long 值,那么n、n+1都存储了Long的值

操作数栈

操作数栈存储了方法内的局部变量,使用的是后入先出的存储结构,将每一个变量和结果压入操作数栈。操作数栈的深度是在编译期间就已经确定,Long、Double的栈的深度是两个单位 其它基本数据类型是一个单位 ,栈桢的初始是空的,当方法调用时,会将类的字段、本地变量表压入操作数栈。
操作数栈在计算时,会将需要计算的数据压入操作数栈,然后与取出来进行字节码指令操作,如两个int类型操作,在计算之前两个值 应该是已经在操作数栈中,然后执行iadd指令计算 ,计算 后的结果会再将压入操作数栈中。
保证操作数栈的数据正确性,是class文件 校验过程中强制保证的。

动态链
每人栈桢保存了指向运行常量池的引用。用于方法在运行时动态链接,方法中使用的成员变量,和其它类的变量和方法调用都是用的符号引用,需要在将它们解析真正的存储结构中偏移量(内存地址)。而类加载的回程就是将这些没有解析的符号引用,解析成真正的存储结构中偏移量。让方法运行时指向变量和方法的实际直接引用。
其它类的方法和变量实现的是晚期绑定,所以其它类的方法和变量发生了变化,也不会影响调用它们的方法。

方法调用正常完成
方法正常完成时,会使用方法调用完成指令,并通知PC寄存器的计数器正确的递增,以跳过正在执行的方法指令,并返回正确的方法结果到调用者方法的栈桢中,调用 者方法会继续执行。

方法调用异常结束
当方法调任出现athrow指令或者显示的抛出异常时,方法结束,不会有返回值

运行常量池

运行常量池属于方法区的一部分,是所有线程共享区

每个一个类或接口会有的常量池,这个常量池是一些CONTANS_开头的符号引用和CLASS内的常量字面值,常量池的符号引用 如:CONTANS_METHODREF_INFO,包含了CLASS的方法的符号引用 ,CLASS在加载、链接的时候通过这些常量池中的符号引用找到其在内存的偏移量(直接引用)。运行常量池也是方法区的一部分,JVM将它单独划分出来。

方法区

方法是所有线程可见的共享区,可能会抛出OutOfMemoryError

方法区存储的CLASS的方法、字段、类名称的定义及类、接口、实例在初始化时用的特殊方法(cinit),这个方法不是JAVA的规范方法,收虚拟机创建,不能在存在编码阶段。方法区属于堆的逻辑组成。在虚拟机创建的时候被创建。可以不在方法区中使用GC,因为都是CLASS的一些结构定义信息。

堆是由虚拟机启动时创建 ,所有线程共享

堆存储了所有CLASS的实例信息及数组对象实例信息,JVM的GC也主要 是针对堆中实例。堆是有可能抛出OutOfMemoryError

虚拟机

我们常说的虚拟机其它是指Oracle 的HotSpot VM,它的对象是指向了一个句柄指针,句柄指针包含两个指针,一个指向一个表格,表格包含对象的各个方法和一个指向CLASS对象(用于表示对象 的类型)的指针,一个指向对象的实例地址

原创粉丝点击