jvm-运行时数据区域

原文链接: https://my.oschina.net/u/3286119/blog/1928996

总览

      在Java虚拟机规范(Java SE 7版)中,jvm内存区域划分如下: jvm-运行时数据区域_第1张图片

  • 线程共享的区域有方法区和堆
  • 线程私有的区域有程序计数器,虚拟机栈,本地方法栈

详解

  1. 程序计数器
          在单个线程中,指令的执行是有序的,程序计数器即可看成是字节码执行行号指针。如果正在执行的是一个java方法,这个计数器记录的是当前执行字节码指令的地址;如果执行的是一个native方法,这个计数器值为underfined。
          此区域是在规范中唯一没有定义OutOfMemoryError的区域。

  2. Java虚拟机栈
          虚拟机栈即我们常说的堆栈中的栈,它是线程私有的,主要用来完成栈帧的入栈出栈操作和线程局部变量的保存,栈帧即方法运行时的基础数据结构,具体内容包含局部变量表、操作数栈、动态链接、方法出口等,每个方法从调用到完成对应着此栈帧在虚拟机栈中的入栈到出栈过程,栈大小在jdk1.8中默认为 1024k,可通过 jinfo -flag ThreadStackSize pid 查询,通过 -Xss1m 方式设置栈大小,栈大小设置关乎应用所能创建线程数量,应根据实际需要进行设置,在其他条件相同的情况下,栈帧大小与栈深度成反比。
          此区域有两种异常状况:如果栈深度大于虚拟机定义深度,会抛出StackOverflowError异常;栈支持扩展,如果在扩展过程中无法申请足够的内存,会抛出OutOfMemoryError。

  3. 本地方法栈
          本地方法栈为虚拟机使用到的Native方法服务,本地方法栈也会抛出StackOverflowError和OutOfMemoryError异常。

  4. Java 堆
          被所有线程共享的一块区域,几乎所有的对象实例都在这里分配(现在存在栈上分配等优化技术),从垃圾回收的角度来说,基本都采用分代收集算法(除G1),所以java堆还可以分为:新生代(from survivor,to survivor,eden)、老年代。堆大小在jvm启动时通过-Xmx、-Xms配置,当无法为实例分配足够大的堆内存时,会抛出OutOfMemoryError异常。

  5. 方法区
          方法区也是所有线程共享,主要存储类信息、常量、静态变量、即时编译器编译后的代码等,在使用hotspot的应用中经常也被称为永久代(Permanent Generation)。在方法区中有个很重要的组成部分是运行时常量池,用于存放编译期生成的字面量和符号引用,当方法区无法满足内存分配需求时,将抛出OutOfMemoryError。

转载于:https://my.oschina.net/u/3286119/blog/1928996

你可能感兴趣的:(jvm-运行时数据区域)