JVM_5 JVM运行时数据区和JVM指令集

356 阅读2分钟

1628728501.jpg

1628762126.jpg 关于查看资料

  • jvm方面参考

1628728679.jpg

  • java语言参考

1628728756.jpg

根据jdk版本选择对应的资料

Runtime Data Area

1628729223.jpg

  1. PC 程序计数器(program counter)(线程私有)

存放指令位置

虚拟机的运行,类似于这样的循环:

while( not end ) {

​    取PC中的位置,找到对应位置的指令;

​    执行该指令;

​    PC ++;

}

  1. Method Area(是一个逻辑概念,Perm Space和Meta Space是它的具体实现)

a. Perm Space (<1.8) 永久代

 字符串常量位于PermSpace
 
 FGC不会清理
 
 大小启动的时候指定,不能变

b. Meta Space (>=1.8) 元数据区

       字符串常量位于堆

       会触发FGC清理

       不设定的话,最大就是物理内存

思考:

如何证明1.7字符串常量位于Perm,而1.8位于Heap?

提示:结合GC, 一直创建字符串常量,观察堆,和Metaspace

  1. Runtime Constant Pool

在运行时数据区里

  1. Native Method Stack(线程私有)

存储JNI信息

  1. Direct Memory(直接内存)

JVM可以直接访问的内核空间的内存 (OS 管理的内存)   老的IO需要将通过网络传输过来的数据先存到内核中,然后从内核copy到jvm中

使用NIO后,网络传输过来的数据存到直接内存中,jvm直接可以访问

NIO , 提高效率,实现zero copy

  1. JVM Stack(线程栈)(线程私有)

  Frame - 每个方法对应一个栈帧

1628731261.jpg

  • Local Variable Table(局部变量表)
  • Operand Stack(操作数栈)

   对于long的处理(store and load),多数虚拟机的实现都是原子的

   jls 17.7,没必要加volatile

  • Dynamic Linking            指向常量池中的符号引用

   blog.csdn.net/qq_41813060…

   jvms 2.6.3

  • return address(返回值地址)

      a() -> b(),方法a调用了方法b, b方法的返回值放在什么地方

例子

public static void main(String[] args) {
        int i = 8;
        i = i++;
//        i = ++i;
        System.out.println(i);
    }

翻译成汇编指令:

 0 bipush 8  压栈
 2 istore_1  将栈中数据存储到局部变量表
 3 iload_1     将局部变量表的数据压栈
 4 iinc 1 by 1    将局部变量表的数据+1
 7 istore_1        将栈中数据存储到局部变量表
  1. Heap

线程共享区域

1628730625.jpg

指令集分类

  1. 基于寄存器的指令集
  2. 基于栈的指令集

   Hotspot中的Local Variable Table 类似于JVM中的寄存器

模拟栈的执行流程

1628736339.jpg

有无返回值

1628736630.jpg

m1()有返回值的时候,调用完方法后返回值会放在main()栈帧中操作数栈的顶部

递归调用

1628737727.jpg

常用指令

store

load

pop

mul

sub

invoke

invoke指令

  1. InvokeStatic

参考【T01_InvokeStatic】

  1. InvokeVirtual

   需要多态的方法

  1. InvokeInterface

参考:【T04_InvokeInterface】

  1. InovkeSpecial

   可以直接定位,不需要多态的方法

   private 方法 , 构造方法

  1. InvokeDynamic

参考【T05_InvokeDynamic】

   JVM最难的指令    lambda表达式或者反射或者其他动态语言scala kotlin,或者CGLib ASM,动态产生的class,会用到的指令