One, the life cycle of a Java Virtual machine:
The life cycle of a Java virtual machine A running Java Virtual machine has a clear task: Executing a java program. He runs when the program starts, and he stops at the end of the program. You run three programs on the same machine and there are three running Java virtual machines. The Java Virtual machine always starts with a main () method, which must be public, return void, and be directly affected by an array of strings. When the program executes, you must indicate to the Java Virtual machine the class name of the replacement main () method. The Main () method is the beginning of the program, and the thread that he is executing is initialized to the program's initial thread. The other threads in the program are started by him. There are two types of threads in Java: The daemon thread (daemon) and the normal thread (Non-daemon). A daemon thread is a thread that the Java virtual machine uses itself, such as a thread that is responsible for garbage collection, which is a daemon thread. Of course, you can also set your own program as the daemon thread. The initial thread that contains the main () method is not a daemon thread. As long as there are normal threads executing in the Java virtual machine, the Java Virtual machine will not stop. If you have sufficient permissions, you can call the exit () method to terminate the program.
Second, the Java Virtual Machine architecture:
A series of subsystems, memory regions, data types, and usage guidelines are defined in the specification of a Java virtual machine. These components constitute the internal structure of the Java Virtual machine, and they not only provide a clear internal structure for the implementation of the Java Virtual machine, but also strictly stipulate the external behavior of the Java Virtual Machine implementation. Each Java Virtual machine consists of a class loader subsystem (class loader subsystem) that is responsible for loading the types (classes and interfaces) in the program and giving unique names. Each Java Virtual machine has an execution engine (execution engine) responsible for executing the instructions contained in the loaded class. The execution of a program requires a certain amount of memory space, such as bytecode, additional information about the loaded class, objects in the program, parameters of the method, return values, local variables, intermediate variables to process, and so on. The Java Virtual machine stores this information in the data areas. Although the implementation of each Java virtual machine contains a data area, the Java Virtual Machine specification is very abstract about the data area provisions. Many of the structural details are left to the Java Virtual Machine implementation to play by itself. The memory structures on different Java Virtual machine implementations vary widely. Some implementations may consume a lot of memory, while others may consume little memory; Some implementations may use virtual memory, while others do not. This relatively refined Java Virtual Machine Memory specification enables Java Virtual machines to be implemented on a wide range of platforms. Part of the data area is common to the entire program, and other parts are controlled by separate threads. Each Java Virtual machine contains a method area and heap, which are shared by the entire program. After a Java virtual machine loads and parses a class, the information parsed from the class file is saved in the method area. Objects that are created when the program executes are saved in the heap. When a thread is created, it is allocated only to his own PC register "PC Register" (program counter) and Java stack (Java stacks). When the thread does not fall off with the local method, the next instruction that the thread executes is saved in the PC register. The Java stack holds a state when a thread invokes a method, including local variables, parameters that invoke methods, return values, and intermediate variables to process. The state when the local method is called is saved in the local methods stack (native method stacks), possibly in registers or other non-platform independent memory. The Java stack consists of a stack frames (or frames). The stack block contains the state of the Java method call. When a thread calls a method, the Java virtual Opportunity presses a new block into the Java stack, and when the method runs at the end, the Java Virtual opportunity pops up the corresponding block and discards it. The Java Virtual machine does not use registers to hold the computed intermediate results, but instead uses the Java stack to store the intermediate results. This is the Java Virtual Machine instructions are more compact and easier to implement a Java virtual machine on a device without a register. The Java stack in the diagram grows downward, and the PC register midline Cheng is grayed out because it is executing the local method, and his next execution instruction is not stored in the PC register.
three, class loader subsystem:
The ClassLoader in a Java Virtual machine is divided into two types: the original ClassLoader (primordial class loader) and the class loader object (class loader objects). The original ClassLoader is part of the Java Virtual Machine implementation, and the ClassLoader object is part of a running program. Classes loaded by different classloader are split by different namespaces. The ClassLoader calls many of the other parts of the Java Virtual Machine and many of the classes in the Java.lang package. For example, the class loading object is an instance of the Java.lang.ClassLoader subclass, and the methods in the ClassLoader class can access the class loading mechanism in the virtual machine; Each class loaded by a Java virtual machine is represented as an instance of a Java.lang.Class class. Like other objects, the ClassLoader object and the class object are stored in the heap, and the loaded information is saved in the method area. 1, loading, connecting, initializing (Loading, linking and initialization) class loading subsystem is not only responsible for locating and loading the class file, he has done a lot of other things according to the following strict steps: (see Chapter seventh, "Life cycle of Class") 1), Load: Find and import binary information for the specified type (class and Interface) 2), connect: Validate, prepare, and parse ① validation: Ensure the correctness of the import type ② prepare: Allocate memory for type and initialize to default value ③ parsing: Parsing a character reference to direct drinking 3), initializing: Calling Java code, initializing the class variable to the appropriate value 2, the original ClassLoader (the primordial class Loader) Each Java Virtual machine must implement a The original class loader, he was able to load those classes that complied with the class file format and was trusted. However, the specification of the Java Virtual machine does not define how the class is loaded, as determined by the Java Virtual Machine implementation itself. For the type of the given type name, the original-the loader must find the file with the type name plus ". Class" and load it into the virtual machine. 3. Class Loader Object Although the ClassLoader object is part of a Java program, the three methods in the ClassLoader class can access the class loading subsystem in the Java Virtual machine. 1), Protected final Class defineclass (...) : Use this method to enter and exit a byte array and define a new type. 2), proTected class Findsystemclass (String name): Loads the specified class and returns directly if it is already loaded. 3), Protected final void Resolveclass (Class C): The DefineClass () method simply loads a class that is responsible for subsequent dynamic joins and initializations. For specific information, see Chapter Eighth, "Connection model" (the linking models). 4. Namespaces when more than one class loader loads the same class, in order to ensure the uniqueness of their names, it is necessary to precede the class name with the identity of the class loader that loads the class. For specific information, see Chapter Eighth, "Connection model" (the linking models).
Four, method area:
In a Java virtual machine, information about the loaded type is saved in the method area. This writing information in memory is defined by the implementation of the virtual machine, for example, the virtual machine works on a "Little-endian" processor, he can save the information in "Little-endian" format, although in the Java class file they are " Big-endian "format is saved. The designer can store the data in a format that is most suitable for the machine, ensuring that the program executes at the fastest possible speed. However, on a device with only a small amount of memory, the implementation of the virtual machine does not occupy a large amount of memory. All threads in the program share a method area, so methods that access the method area information must be thread-safe. If you have two threads to load a class called Lava, then only one thread will be allowed to load the class, and the other must wait. When the program is running, the size of the method area is variable, and the program can be extended at run time. Some implementations of a Java Virtual machine can also customize the initial size, minimum and maximum values of the method area through parameters. The method area can also be garbage collected. Because the inside of the program is dynamically loaded by the ClassLoader, all classes may become non-referenced (unreferenced) states. When the class becomes this state, he may be garbage collected. Classes that are not loaded include two states, one that is really not loaded, and another that is "unreferenced". For more information, see the life cycle of the class in chapter seventh (the Lifetime of a class). 1, type information each loaded type, in the Java Virtual machine will save the following information in the method area: 1), the full name of the type (the fully qualified name of the type 2), the full name of the type's parent type (unless there is no parent type, or the Java.lang.Object form) (the fully qualified name of the Typeís direct superclass) 3), to the type is a class or interface (class or an interface) (Whether or not the type is a Class) 4), type of modifier (public,private,protected,st Atic,final,volatile,transient, etc.) (the Typeís modifiers) 5),A list with the parent interface full name (an ordered list of the fully qualified names of any direct superinterfaces) type the data structure that is saved is defined by the virtual machine's implementation. In addition, the Java Virtual machine also holds the following information for each type: 1), type Chang (the constant pool for the type) 2), Type field information (field information) 3), the Type method information (method information) 4), All static class variable (non-amount) information (all class (static) variables declared in the type, except C onstants) 5), a reference to the ClassLoader (a reference to class ClassLoader) 6), a reference to class class (a reference to class class) 1), type Chang (the constant pool for the type) is a constant pool in which all types are stored in an ordered set of constants that contain direct constants (literals) constants such as strings, integers, floating-point numbers, and the type, field, and party The symbolic reference of the method. Every persisted constant in a constant pool has an index, just like a field in an array. Because a constant pool holds a character reference to the type, field, and method used by all types, it is also the primary object of the dynamic connection. For more information, see Chapter Sixth, "The Java Class File". 2), Type field information (field information) field name, field type, field modifier (public,private,protected,static,final,volatile,transient, etc.), field defined in class The order. 3), type method information method name, method's return value type (or void), number of method arguments, type and their order, field modifier (public,private,protected,static,fin Al,volatile,trAnsient, etc.), the order in which the method is defined in the class if it is not abstract and local This method also needs to save the bytecode of the method, the size of the operand stack of the method, and the size of the local variable area (details later), the exception list (for more information, see Chapter 17th "Exceptions". ) 4), class (Static) variable (class Variables) class variables are shared by instances of all classes, even if they are not accessed through an instance of the class. These variables are bound on the class (not on the instance of the class), so they are part of the logical data for the class. Before the Java virtual machine uses this class, it is necessary to assign memory constants (final) to class variables (non-final) in such a way that the class variable (non-final) is not the same. Each type is copied to its own constant pool when a constant is used. Constants are also stored in the method area like class variables, except that they are stored in a constant pool. (It is possible that class variables are shared by all instances, whereas constant pools are unique to each instance). The Non-final class variable is saved as part of the definition of his type data (that is, declares them), and the final constant is saved as an Part. See chapter Sixth, "The Java class Filethe Java class File" 5), a reference to the ClassLoader (a reference to class ClassLoader), each Java virtual The type of the machine to be loaded, the virtual machine must save whether the type is loaded by the original class loader or the ClassLoader. Those types that are loaded by the ClassLoader must hold a reference to the ClassLoader. This information is used when the ClassLoader is dynamically connected. When a class references another class, the virtual machine must save that the referenced type is loaded by the same ClassLoader, which is also the process of maintaining a different namespace for the virtual machine. See chapter Eighth, "The linking Model" 6), a reference to class class (a reference to class Class) A Java Virtual machine creates a java.lang.Clas for each loaded type An instance of the S class. You can also use the class method: public static class forname (String className) to find or load a class and getAn instance of the corresponding class class. With this class instance, we can access the information in the Java Virtual Machine method area. Refer to the Javadoc of class in detail. 2. Method Tables for more efficient access to all data stored in the method area, the storage structure of the data must be carefully designed. In all method areas, in addition to the original information above, there is a data structure designed to speed up access, such as a list of methods. For each non-abstract class that is loaded, the Java Virtual machine generates a list of methods that hold references to all instance methods that the class might invoke, giving an error to the methods called in the parent class. See chapter Eighth "The linking Model" for details
When a Java program creates an instance or an array of a class, it allocates memory for the new object in the heap. There is only one heap in the virtual machine, and all the threads share him. 1. Garbage collection (garbage Collection) garbage collection is the primary method for releasing objects that are not referenced. It may also move objects in order to reduce the fragmentation of the heap. Garbage collection is not strictly defined in the specification of a Java virtual machine, but the implementation of defining a Java Virtual machine must somehow manage its own heap. See chapter Nineth "Garbage Collection" for details. 2. Object storage structure (objects representation) The specification of the Java Virtual machine does not define how the object is stored in the heap. Each object primarily stores the object variables defined in his class and in the parent class. For a reference to a given object, the virtual machine must be tender and Nou quickly to locate the object's data. Alternatively, you must provide a way to object data through the object's reference method, such as a reference to an object in the method area, so that the data stored by an object often contains a pointer to the method area in some form. One possible heap design is to divide the heap into two parts: the reference pool and the object pool. A reference to an object is a local pointer to the reference pool. Each entry in the reference pool contains two parts: A pointer to the object data in the object pool and a pointer to the object class data in the method area. This design makes it easy to defragment the Java Virtual machine heap fragments. When a virtual machine moves an object in an object pool, only the pointer address in the corresponding reference pool needs to be modified. However, each access to the object's data requires processing two pointers. Demonstrates the design of this heap. The Heapoffish applet in the Nineth chapter of "Garbage collection" demonstrates this design. Another heap design is that a reference to an object is a pointer to a heap of data and an offset to the corresponding object. This design facilitates access to objects, but the movement of objects becomes unusually complex. Demonstrates this design when a program attempts to convert an object to another type, the virtual machine needs to determine whether the conversion is the type of the object, or his parent type. Similar things are done when the program applies instanceof statements. When a program calls a method of an object, the virtual machine needs to be dynamically bound, and he must determine which type of method to invoke. This also requires making the above judgments. Regardless of the design used by the virtual machine's implementation, he might save a list of similar methods for each object. Because he can raise the speed of object method calls, it is important to improve the performance of the virtual machine, but the specification of the virtual machine has no requirement to implement a similar data structure. Describes this structure. The figure shows all the data structures associated with an object reference, including: 1), a pointer to the type Data 2), a list of methods for an object. The method list is an array of pointers to all of the methods that may be called objects. The method data includes three parts: the size of the opcode stack and the local variable area of the method stack; The byte code of the method; the exception list. Objects in each Java virtual machine must be associated with a lock (mutex) for synchronizing multithreading. At the same time, only one object can have a lock on this object. When a lock has this object, he can apply for the lock multiple times, but must also release the corresponding number of locks to actually release the object lock. Many objects are not locked for the entire life cycle, so this information needs to be added only when needed. Many implementations of a Java virtual machine do not include "lock data" in the object's data, but generate the corresponding data only when needed. In addition to implementing object locking, each object is logically associated with the implementation of a "wait set". Locking helps the group thread to handle the shared data independently, without interfering with other threads. The wait set works together to accomplish the same goal for the group threads. The wait set is often implemented through the wait () and notify () methods of the object class. Garbage collection also requires information about whether the objects in the heap are associated. The Java Virtual Machine specification states that garbage collection is a finalizer method that runs an object once, but allows the finalizer method to re-reference the object, and when the object is not referenced again, it does not need to call the Finalize method again. So the virtual machine also needs to save the information that the Finalize method is running. For more information, see Chapter Nineth, "Garbage collection" 3, saving arrays (array representation) in Java, an array is an object that is completely meaningful, stored in the heap like an object, and has a reference to a class class instance. All arrays of the same dimension and type have the same class, and the length of the array is not considered. The name of the corresponding class is expressed as a dimension and a type. For example, an integer data class is "[I", a byte-type three-dimensional array class named "[[[B], two-D object data class named" [[Ljava.lang.Object]. The array must hold the length of the array in the heap, the data of the array, and references to some object array type data. Referenced by an array, the virtual machine should be able to obtain the length of an array through which the index can access specific data and be able to invoke the method defined by the object. Object is the immediate parent class for all data classes. For more information, see Chapter Sixth, "Class files".
VI. Basic structure:
From the logical structure of the Java platform, we can never understand the JVM:
The differences between the JDK and the JRE can be learned from the clear view of the various logical modules contained in the Java platform.
The physical structure of the JVM itself
This figure shows the JVM memory structure
The JVM memory structure consists of two subsystems and two components. The two subsystems are ClassLoader subsystem and executionengine (execution engine) subsystem, and two components are Runtimedataarea (runtime data region) component and Nativeinterface (local interface) component respectively.
The role of the ClassLoader subsystem:
Loads the contents of a class file into a Methodarea (method area) in Runtimedataarea, given a fully qualified name Class name (such as Java.lang.Object). Java programmers can extendsjava.lang.ClassLoader classes to write their own classloader.
The role of the Executionengine subsystem:
Executes the instructions in the classes. The core of any jvmspecification implementation (JDK) is executionengine, and the different JDK, such as Sun's JDK and IBM's JDK, depends largely on the quality of their respective executionengine.
Interacting with Nativelibraries is an interface for other programming language interactions. When the native method is called, it enters a completely new world that is no longer restricted by the virtual machine, so it is also easy to have nativeheapoutofmemory that the JVM cannot control.
This is what we often call the JVM's memory. It is mainly divided into five parts--
1. Heap: Only one heap space exists in a Java virtual instance
2. Methodarea (method Area): The information of the loaded class is stored in Methodarea memory. When a virtual machine loads a type, it uses the class loader to locate the appropriate class file and then reads the class file contents and transfers it to the virtual machine.
3, Javastack (Java stack): The virtual machine will only perform two operations on the Javastack: stack or stack in frames
4. Programcounter (program counter): Each thread has its own PC register, which is also created when the thread starts. The contents of the PC register always point to the next hungry address where the instruction will be executed, where the address can be either a local pointer or an offset relative to the method's start instruction in the method area.
5, Nativemethodstack (local method Stack): Save Native method to enter the address of the zone
For the study of the JVM, it seems to me that so many parts are most important:
- The entire process of compiling and executing Java code
- JVM memory management and garbage collection mechanism
The entire process of compiling and executing Java code
Java code compilation is done by the Java source compiler, and the flowchart is as follows:
The execution of Java bytecode is done by the JVM execution engine, and the flowchart is as follows:
The entire process of compiling and executing Java code consists of the following three important mechanisms:
- Java source Code compilation mechanism
- Class loading mechanism
- Class execution mechanism
Java source Code compilation mechanism
Java source code compilation consists of the following three processes: (Javac–verbose output messages about the actions the compiler is performing)
- Parse and input to symbol table
- Annotation processing
- Semantic analysis and generation of class files
The resulting class file is made up of the following sections:
- Structure information. Includes the class file format version number and the number and size of each part of the information
- Meta data. The information that corresponds to the declarations and constants in the Java source code. Contains class/inherited superclass/implemented interface declaration information, domain and method declaration information, and constant pool
- Method information. Corresponds to the information in the Java source code for statements and expressions. Includes byte code, exception Processor table, evaluation stack and local variable size, type record of evaluation stack, debug symbol information
Class loading mechanism
The class loading of the JVM is done through ClassLoader and its subclasses, and the hierarchy and loading order of the classes can be described as follows:
1) Bootstrap ClassLoader/Start class loader
$JAVA _home All classes in Jre/lib/rt.jar, implemented by C + +, not classloader subclasses
2) Extension classloader/Extension class loader
Some jar packages that are responsible for loading the extensions in the JAVA platform, including the jar packages in $java_home Jre/lib/*.jar or-djava.ext.dirs specified directories
3) App classloader/System class Loader
Responsible for documenting the jar packages specified in the Classpath and the class in the directory
4) Custom classloader/user-defined class loader (subclass of Java.lang.ClassLoader)
The ClassLoader that the application customizes according to its own needs, such as Tomcat and JBoss, will be implemented according to the Java EE specification itself ClassLoader
The load process checks to see if the class is loaded, the check order is bottom-up, and the custom ClassLoader to bootstrap ClassLoader-by-layer check, as long as a certain classloader is loaded as if the class has been loaded. Ensure that only all classloader of this class are loaded once. The order of loading is top-down, that is, the upper layer tries to load the class one at a level.
Introduction and analysis of class loading parental delegation mechanism
Here, it should be emphasized that the JVM defaults to the parent delegation mechanism when loading the class. In layman's words, when a particular class loader receives a request to load a class, it first delegates the load task to the parent class loader, recursively, and returns if the parent ClassLoader can complete the class load task, only to load itself when the parent ClassLoader cannot complete the load task.
Class execution mechanism
The JVM is a stack-based architecture that executes class bytecode. After the thread is created, the program counter (PC) and stack (stack) are generated, and the program counter holds the offset of the next instruction to be executed in the method, and the stack frames are stored in each stack frame, and each stack frame corresponds to each call of each method, and the stack frame is made up of the local variable area and the operand stack. Local variables are used to store local variables and parameters in the method, which are used to store the intermediate results produced during the execution of the method.
Memory management and garbage collection JVM memory composition structure
The JVM stack consists of heaps, stacks, local method stacks, method areas, and so on, as shown in the following chart:
JVM Memory Reclamation
Sun's jvmgenerationalcollecting (garbage collection) principle is that it divides objects into younger generations (young), older generations (tenured), and persistent generations (Perm), using different algorithms for objects of different lifecycles. (Based on the object life cycle analysis)
1.Young (Young Generation)
The young generation is divided into three districts. One Eden area, two survivor districts. Most objects are generated in the Eden area. When the Eden Zone is full, the surviving objects will be copied to the Survivor area (one of two), and when the survivor area is full, the surviving objects of this area will be copied to another survivor area, when the survivor is full, Objects that are copied from the first survivor area and that are still alive will be duplicated in the old age zone (tenured. It should be noted that the two areas of the survivor are symmetrical and have no relationship, so the same area may exist at the same time from Eden copied objects, and from the previous survivor copied objects, and copied to the old quarter only from the first survivor to come over the object. Moreover, there is always an empty survivor area.
2.Tenured (Old Generation)
Older generations store objects that survive from younger generations. In general, older generations are storing long-term objects.
Used to store static files, now Java classes, methods, and so on. The persistence generation has no significant impact on garbage collection, but some applications may dynamically generate or invoke some classes, such as Hibernate, at which point a large, persistent generation space is required to store the new class in these runs. The persistent generation size is set by-xx:maxpermsize=.
For example, when an object is generated in a program, the normal object allocates space in the younger generation, and if the object is too large, it may be generated directly in the old generation (it is observed that each time a program is run, a 10 trillion space is generated for sending and receiving messages, and this memory is allocated directly to the old generation). The young generation will initiate a memory recovery when the space is allocated, most of the memory will be recycled, a portion of the surviving memory will be copied to the survivor from zone, and after multiple collections, if the From zone memory is also allocated, then a memory recycle will occur and the remaining objects will be copied to the to area. When the to area is full, a memory recycle occurs and the surviving objects are copied to the old quarter.
Usually we say that the JVM memory recycle is always referred to as heap memory recycling, indeed only the content in the heap is dynamically requested to allocate, so the young and old generations of the above objects refer to the JVM's heap space, and the persistent generation is the previously mentioned Methodarea, not the heap.
Some suggestions on JVM memory management
1. Manually set the generated garbage object, the intermediate object to null, and speed up the memory reclamation.
2. Object pooling technology If the resulting object is a reusable object, but the attributes are not the same, you can consider using an object pool to produce fewer objects. If a free object is removed from the object pool, no new objects are generated, which greatly increases the object's reuse rate.
3, JVM tuning by configuring the parameters of the JVM to increase the speed of garbage collection, if there is no memory leak and the above two methods can not guarantee the JVM memory recovery, you may consider the JVM tuning method to solve, but must go through the physical machine long-term testing, because different parameters may cause different effects. such as-XNOCLASSGC parameters.
The principle of JVM in Java "Go"