JVM

摘自《Java面向对象编程》


Java虚拟机提供了程序运行时环境,运行时环境中最重要的一个资源是运行时数据区。运行时数据区是操作系统为Java虚拟机进程分配的内存区域,主要包括堆区、方法区和Java栈区等。

l         方法区中存放类的类型信息,类型信息包括静态变量和方法信息等,方法信息中包含类的所有方法的字节码。

l         堆区中存放对象,对象的实例变量。

l         主线程在Java栈区内有一个方法调用栈,每执行一个方法,就会向方法调用栈中压入一个包含该方法的局部变量和参数的栈帧。

 

l         方法区存放了线程所执行的字节码指令。

l         堆区存放了线程所操纵的数据(以对象的形式存放)。

l         Java栈区则是线程的工作区,保存线程的运行状态。

 

Java虚拟机进程中,执行程序代码的任务是由线程来完成的。每个线程都有一个独立的程序计数器和方法调用栈(method invocation stack)。

l         程序计数器:也称为PC寄存器,当线程执行一个方法时,程序计数器指向方法区中下一条要执行的字节码指令。

l         方法调用栈:简称方法栈,用来跟踪线程运行中一系列的方法调用过程,栈中的元素称为栈帧。每当线程调用一个方法的时候,就会向方法栈中压入一个新帧。帧用来存储方法的参数、局部变量和运算过程中的临时数据。

栈帧由以下3部分组成:

l         局部变量区:存放局部变量和方法参数。

l         操作数栈:是线程的工作区,用来存放运算过程中生成的临时数据。

l         栈数据区:为线程执行指令提供相关的信息,包括如何定位到位于堆区和方法区的特定数据,以及如何正常退出方法或异常中断方法。


摘自《The Structure of the Java Virtual Machine


http://java.sun.com/docs/books/jvms/second_edition/html/Overview.doc.html

3.5 Runtime Data Areas

The Java virtual machine defines various runtime data areas that are used during execution of a program. Some of these data areas are created on Java virtual machine start-up and are destroyed only when the Java virtual machine exits. Other data areas are per thread. Per-thread data areas are created when a thread is created and destroyed when the thread exits.

Java 虚拟机定义好几种运行期数据结构,用于程序的执行。一些数据结构是由Java虚拟机启动时创建,退出时销毁。也有一些数据结构用于线程。用于线程的数据结构是由线程启动时创建,退出时销毁。

3.5.1 The pc Register

The Java virtual machine can support many threads of execution at once (§2.19). Each Java virtual machine thread has its own pc (program counter) register. At any point, each Java virtual machine thread is executing the code of a single method, the current method (§3.6) for that thread. If that method is not native, the pc register contains the address of the Java virtual machine instruction currently being executed. If the method currently being executed by the thread is native, the value of the Java virtual machine’s pc register is undefined. The Java virtual machine’s pc register is wide enough to hold a returnAddress or a native pointer on the specific platform.

3.5.1 PC 寄存器

虚拟机支持多线程并行。每个Java线程都有自己的PC寄存器。不管怎样,Java线程只是自执行单个方法,线程的当前方法的代码。 方法不是native的话,PC寄存器就包含一个地址,指向虚拟机当前指令。 如果方法是native的话,PC寄存器的值就是undefined.因为Java虚拟机的pc寄存器是足够大,所以能够保持一个returnAddress 或一个特定平台的native指针。

3.5.2 Java Virtual Machine Stacks

Each Java virtual machine thread has a private Java virtual machine stack, created at the same time as the thread.3 A Java virtual machine stack stores frames (§3.6). A Java virtual machine stack is analogous to the stack of a conventional language such as C: it holds local variables and partial results, and plays a part in method invocation and return. Because the Java virtual machine stack is never manipulated directly except to push and pop frames, frames may be heap allocated. The memory for a Java virtual machine stack does not need to be contiguous.

The Java virtual machine specification permits Java virtual machine stacks either to be of a fixed size or to dynamically expand and contract as required by the computation. If the Java virtual machine stacks are of a fixed size, the size of each Java virtual machine stack may be chosen independently when that stack is created. A Java virtual machine implementation may provide the programmer or the user control over the initial size of Java virtual machine stacks, as well as, in the case of dynamically expanding or contracting Java virtual machine stacks, control over the maximum and minimum sizes.4

The following exceptional conditions are associated with Java virtual machine stacks:

  • If the computation in a thread requires a larger Java virtual machine stack than is permitted, the Java virtual machine throws a StackOverflowError.
  • If Java virtual machine stacks can be dynamically expanded, and expansion is attempted but insufficient memory can be made available to effect the expansion, or if insufficient memory can be made available to create the initial Java virtual machine stack for a new thread, the Java virtual machine throws an OutOfMemoryError.

3.5.2 虚拟机栈

虚拟机线程拥有一个私有的虚拟机栈,创建线程的时候也同时创建线程栈。

栈存储frames,栈类似于其他语言,如C语言中的栈。存储local 变量和中间结果。同时方法的调用和返回的操作也用到了栈。对Java 虚拟机的栈操作,只能是pushpop frames.  栈内存不需要连续。虚拟机规范栈内存可以固定大小也可以由计算程序自动扩展和缩小。

如果栈大小固定的话,当栈创建的时候,虚拟机栈的大小是有虚拟机自由选择的。没有约束。

但是,如果栈的大小是动态的扩展和缩小的话,则虚拟机可以在栈的初始化,控制栈的最大和最小值。

虚拟机栈的异常条件如下:

l        线程的计算请求的栈大小超过了虚拟机提供的最大值,则抛出StackOverflowError

l        当没有足够多的内存来创建一个新线程请求的初始化栈,则抛出OutOfMemoryError

3.5.4 Method Area

The Java virtual machine has a method area that is shared among all Java virtual machine threads. The method area is analogous to the storage area for compiled code of a conventional language or analogous to the “text” segment in a UNIX process. It stores per-class structures such as the runtime constant pool, field and method data, and the code for methods and constructors, including the special methods (§3.9) used in class and instance initialization and interface type initialization.

The method area is created on virtual machine start-up. Although the method area is logically part of the heap, simple implementations may choose not to either garbage collect or compact it. This version of the Java virtual machine specification does not mandate the location of the method area or the policies used to manage compiled code. The method area may be of a fixed size or may be expanded as required by the computation and may be contracted if a larger method area becomes unnecessary. The memory for the method area does not need to be contiguous.

A Java virtual machine implementation may provide the programmer or the user control over the initial size of the method area, as well as, in the case of a varying-size method area, control over the maximum and minimum method area size.6

The following exceptional condition is associated with the method area:

  • If memory in the method area cannot be made available to satisfy an allocation request, the Java virtual machine throws an OutOfMemoryError.

3.5.4 方法区

虚拟器有一个所有线程共享的方法区方法区类似于普通语言编译后代码的存储区,也类似于Unix进程的Text segment。存储类结构,像运行期类常量池,字段,方法数据,方法代码,构造方法代码。类中特殊代码,实例的初始化,接口的初始化。

方法区是由虚拟机启动时候创建的,虽然方法区于Java堆内存的一部分,本版虚拟机规范没有制定方法区的位置和方法区如何管理编译后的代码的策略。可以固定,也可以动态增长。内存空间可以不连续。

虚拟机栈的异常条件如下:

l        方法区的内存不能满足请求的内存大小时,则抛出OutOfMemoryError

3.5.3 Heap

The Java virtual machine has a heap that is shared among all Java virtual machine threads. The heap is the runtime data area from which memory for all class instances and arrays is allocated.

The heap is created on virtual machine start-up. Heap storage for objects is reclaimed by an automatic storage management system (known as a garbage collector); objects are never explicitly deallocated. The Java virtual machine assumes no particular type of automatic storage management system, and the storage management technique may be chosen according to the implementor’s system requirements. The heap may be of a fixed size or may be expanded as required by the computation and may be contracted if a larger heap becomes unnecessary. The memory for the heap does not need to be contiguous.

A Java virtual machine implementation may provide the programmer or the user control over the initial size of the heap, as well as, if the heap can be dynamically expanded or contracted, control over the maximum and minimum heap size.5

The following exceptional condition is associated with the heap:

  • If a computation requires more heap than can be made available by the automatic storage management system, the Java virtual machine throws an OutOfMemoryError.

3.5.3 堆区

Java的堆是所有虚拟机线程共享的。也是一个running data area. 是为类实例和array 实例分配内存的数据区。虚拟机启动创建。堆为Object分配的存储区域是由自动存储管理系统(也就是垃圾回收系统)回收的。对象自己不能显式的释放。虚拟机没有指定特定类型的垃圾回收系统,而是由实现者根据系统的需要自行制定垃圾回收技术。堆内存可以固定大小也可以动态的扩展和缩小。堆内存可以不连续。

虚拟机的实现者可以提供程序员或者使用者控制堆内存的初始化大小,如果堆内存是动态增长的话,则要控制堆内存的最大和最小值。

虚拟机栈的异常条件如下:

如果计算程序请求的内存超过了自动存储系统能够提供的内存的话,就抛出OutOfMemoryError

发表评论

邮箱地址不会被公开。 必填项已用*标注

昵称 *