In-depth understanding of Java Virtual Machine notes---class loading process

Source: Internet
Author: User
Tags field table sap netweaver

First, load
The load (Loading) stage is a phase of the class Loading process. During the load phase, the virtual machine needs to complete the following three things:
A. Get a binary byte stream that defines this class by using the full restricted name of a class.
B. Convert the static storage structure represented by this byte stream into the run-in data structure of the method area.
C. Generate a Java.lang.Class object representing this class in the Java heap as the access entry for the data in the method area.
This three-point requirement for the virtual machine specification is not actually specific, so the virtual machine implementation is considerably more flexible than the specific application. For example, "to obtain a binary byte stream defined by a class's fully restricted name" does not indicate that the binary stream is to be obtained from a class file, but that it is not exactly where it is to be obtained and how it is obtained. Virtual machine design Team The loading phase has created a fairly open, broad stage, in the Java development process, many important Java technologies are built on this basis, for example:
A. Read from a Zip package, which is common and eventually becomes the basis for future Jar,ear,war formats
B. Obtained from the network, the most typical application of this scenario is the applet
C. Run-time compute generation, the most used of this scenario is dynamic Agent technology, in Java.lang.reflect.Proxy, is to use the Proxygenerator.generatproxyclass to generate for a specific interface *$ A binary byte stream of proxy classes for proxies.
D. Generated by other files, typical scenario: JSP application.
E. read from the database, this scenario is relatively rare, some middleware servers (such as SAP Netweaver) can choose to install the program into the database to complete the program code between the cluster distribution.
F........

The load phase and part of the connection phase (such as a subset of bytecode file format validation actions) are interleaved, the loading phase is not complete, the connection phase may have started, but the actions taken during the loading phase of these clips are still the contents of the attribute connection phase, and the start time of the two phases remains in the order of fixation.

Second, verification
Validation is the first step in the connection phase, which is designed to ensure that the information contained in the byte stream of a class file conforms to the requirements of the current virtual machine and does not compromise the security of the virtual machine itself.
Although the validation phase is important, the effort in the validation phase accounts for a significant portion of the virtual machine's class-loading subsystem. If you verify that the input byte stream does not conform to the storage format of the class file, it throws a java.lang.VerifyError error or its child error. Specifically, you should check which aspects, how to check, when to check, the virtual machine specification is not clearly stated, so different virtual machines for the implementation of the validation may be different, but will generally complete the four stages of the verification process: file format verification, metadata validation, bytecode verification and symbol reference verification.

Third, prepare
The prep phase is a phase that formally allocates memory for class variables and sets the initial value of class variables, which are allocated in the method area. It is necessary to emphasize that the memory allocation at this time includes only class variables, not instance variables, and the instance variables will be allocated in the Java heap along with the object when the object is instantiated. The second is that the initial value described here is the 0 value of the data type under "normal circumstances", assuming that a class variable is defined as:
public static int value = 123;
Then the initial value of the variable value after the prep phase is 0 instead of 123, since no Java method has started executing, and the putstatic instruction that assigns value 123 is stored in the class constructor "<clinit>" method after the program is compiled. , so an action that assigns value to 123 will not be executed until the initialization stage.
The initial value under "normal conditions" mentioned above is zero, but if the Constantvalue attribute exists in the field attribute table of the class field, the value of the prepare-phase variable is initially initialized to the values specified by the Constantvalue property. Assume that the above class variable value is defined as:
public static final int value = 123;
Compile-time Javac will generate the Constantvalue property sheet for value, and in the preparation phase the virtual will assign value to 123 based on the settings of Constantvalue.

Iv. Analysis
The parsing phase is the process by which a virtual machine replaces a symbolic reference within a constant pool with a direct reference, and in the Class file it constant_class_info,constant_fieldref_info,constant_methodref_ Constants for types such as info are present. The Association of a direct reference to a symbol reference is:
A. Symbolic references (symbolic References) describe the referenced directory in a set of symbols, which can be any form of literal, as long as it can be used without ambiguity to locate the target. The symbolic reference is independent of the memory layout implemented by the virtual machine, and the referenced target is not necessarily loaded into memory.
B. A direct reference can be a pointer to a target directly, a relative offset, or a handle that can be indirectly anchored to the target. The direct reference is related to the memory layout implemented by the virtual machine, and the same symbolic reference is generally not the same as the direct reference translated on different virtual machine instances. If there is a direct reference, the referenced target must already exist in memory.
The virtual machine specification does not specify the time at which the parsing phase occurs and only requires that the newarray,heckcast,getfield,etstatic,instanceof,invokeinterface,invokespecial be executed. Nvokestatic,invokevritual,multianewarray,new,putfield and putstatic These 13 byte-code directives used to manipulate symbol references, first parse the symbol references that they use. So the virtual machine implementation is judged by the need to parse a symbolic reference in a constant pool when the ClassLoader is loaded, or to parse a symbol reference when it is about to be used.
The same symbol reference may make multiple resolution requests, and the virtual machine implementation may cache the results of the first resolution to avoid repeating the parsing action. Regardless of whether the virtual machine needs to be guaranteed to be in the same entity or not, if a symbolic reference is successfully parsed, subsequent parsing requests should be successful, and similarly, if the first parse fails, the other directive should receive the same exception for the parse request that is referenced by the symbol.
The parsing action is mainly for classes or interfaces, fields, methods, interface methods, and four types of symbolic references, corresponding to the constant_class_info,constant_fieldref_info,constant_methodref_ of the constant pool, respectively. Info and constant_interfacemetodref_info four types of constants. The following are the parsing procedures for these four references.
1. Class or interface parsing process
Assuming that the current code is in the Class D, if you want to parse a never-parsed symbol reference n into a direct reference to a class or interface C, the virtual machine will complete the entire parsing process by including the following 3 steps:
A. If C is not an array type, the virtual machine will pass the fully qualified name representing N to the ClassLoader of Class D to load the Class C. During the loading process, because there is no data validation and the need for bytecode validation, it is possible to trigger loading actions for other related classes, such as loading the class's parent class or implementing an interface. Once any exception occurs in this loading process, the parsing process will fail.
B. If c is an array type and the element type of the array is an object, that is, the descriptor of n is similar to the "[Ljava.lang.Integer" form, then the array element type is loaded according to the rule of point A. If the descriptor of N is a previously assumed form, the element type that needs to be loaded is "Java.lang.Integer", and then the virtual machine generates an array object representing this array and element.
C. If there are no exceptions to the above steps, then C is actually a valid class or interface in the virtual machine, but before parsing is done, it is necessary to verify that C has access to D, and if no specific access rights are found, it will throw Java.lang.IllegalAccessError Error.
2. Field resolution
To parse a field symbol reference that has not been resolved, first the Constant_class_info symbol reference for the index in the Class_index item in the field table is parsed, that is, the symbol reference for the class or interface to which the field is a property. If any exception occurs during parsing of this class or interface symbol reference, the field symbol reference resolution fails. If the parsing completes successfully, then the class or interface of the attribute of this field is represented in C, and the virtual machine specification requires the following steps to search for C for subsequent fields:
A. If C itself contains a field with a simple name and a field descriptor that matches the target, the direct reference to the field is returned, and the lookup ends.
B. Otherwise, if the interface is implemented in C, the interface and its parent interface will be searched recursively from top to bottom, and if the interface contains a field whose simple name the field descriptor matches the target, the direct reference to the field is returned, and the lookup ends.
C. Otherwise, if C is not a java.lang.Object, the parent class will be searched recursively from top to bottom, if the parent class contains a simple name and the field descriptor matches the Target field, the direct reference to the field is returned, and the lookup ends.
D. Otherwise, the lookup fails and the recruit throws a java.lang.NoSuchFieldError error.
3. Class method parsing
The first step of the class method parsing is the same as the field resolution, which is the symbolic reference of the class or interface that needs to parse the method of the index in the Class_index item of the method table, and if the parsing succeeds, the class is still represented in C, and then the virtual machine will follow the following steps to search for the class method:
A. Class methods and interface methods symbolic references to constant type definitions are separate, and if C is found to be an interface in Class_index in the class method table, a Java.lang.IncompatibleClassChangeError error is thrown directly.
B. If you pass step a, look in Class C for a method that has a simple name and a descriptor that matches the target, and if so, returns a direct reference to the method, ending with a lookup.
C. Otherwise, in the parent class of Class C, to find out whether there is a simple name and a method that the field descriptor matches the target, the direct reference to the method is returned, and the lookup ends.
D. Otherwise, recursively find in the list of interfaces implemented by Class C and their parent interfaces a method that has both a simple name and a field descriptor that matches the target, stating that Class C is an abstract class, when the lookup ends and throws a java.lang.AbstractMethodError error.
E. Otherwise, the lookup fails, throwing a java.lang.NoSuchMethodError error.
Finally, if the lookup process returns a direct reference successfully, a java.lang.IllegalAccessError error will be thrown if it finds no access to the method.
4. Interface Method Parsing
Interface methods also need to parse out the interface method table in the Class_index item indexed method of the class or interface of the symbol reference, if the resolution is successful, still use C to represent the interface, the next virtual machine will follow the following steps to follow the interface adapting search:
A. In contrast to the class method parsing, if the Class_index index in the interface method table is found to be a class instead of an interface, the Java.lang.IncompatibleClassChangeError error is thrown directly.
B. Otherwise, find out if there is a method in interface C that has a simple name that matches the target, and if so, returns a direct reference to the method, ending with a lookup.
C. No, recursive lookup in the parent interface of interface C until the Java.lang.Object class, see if there is a simple name and descriptor matching the target method, if any, return the direct reference to the method, the end of the lookup.
D. Otherwise, declare the lookup failed, throwing a java.lang.NoSuchMethodError error.
Because all methods in the interface are public by default, there is no access problem, so symbolic parsing of interface methods should not throw java.lang.IllegalAccessError errors.

V. Initialization
Class initialization is the last step in the class loading process, and the previous class load action, except in the load phase, where the user application can participate through a custom ClassLoader, the rest of the action is entirely dominated and controlled by the virtual machine. In the initialization phase, the Java program code (or bytecode) that is defined in the class is actually executed.
In the preparation phase, the variable has already assigned the initial value of the system requirement, while in the initialization phase, the class variables and other resources are initialized according to the programmer's subjective plan, or can be expressed from another angle: The initialization phase is the process of executing the class constructor <clinit> () method. The <clinit> () method execution process may affect some of the characteristics and details of the program's behavior, as follows:
The 1.<clinit> () method is generated by the compiler's automatic collection of assignment actions for all class variables in the class and statements in the static statement block (static{}), the order in which the compiler collects is determined by the order in which the statements appear in the source file. A static statement block can only access variables defined before a static statement block, defined after it, and is assignable in the preceding static statement block, but cannot be accessed.
The 2.<clinit> () method differs from the class's constructor <init> (), which does not require a display to call the parent class constructor, and the virtual opportunity guarantees that the parent class's <clinit> ( ) method has been executed. So the first class of the <clinit> () method in a virtual machine is definitely java.lang.Object.
3. Because the <clinit> () method of the parent class executes first, it means that the static statement block defined in the parent class takes precedence over the class variable assignment operation of the child class.
The 4.<clinit> () method is not necessary for a class or interface, and if there is no static statement block in a class and no assignment to the class variable, the compiler may not generate the <clinit> () method for such a class.
5. A static statement block cannot be used in an interface, but can still have a colleague operation with variable initialization, so an interface is generated as a <clinit> () method as a class, but unlike a class, the <clinit> () method that executes the interface does not need to first perform the parent interface's < Clinit> () method. The parent interface is initialized only if the variable defined in the parent interface is used. In addition, the implementation class of the interface does not execute the <clinit> () method of the interface at initialization time.
6. Virtual opportunity to ensure that a class of <clinit> () method in a multithreaded environment is correctly locked synchronization, if multiple threads to initialize a class at the same time, then there will only one thread to execute the class of the <clinit> () method, other threads need to block wait, Until the active thread executes the <clinit> () method is complete. If there is a time-consuming operation in the <clinit> () method of a class, it can cause multiple threads to block, which is often hidden in practical applications.

In-depth understanding of Java Virtual Machine notes---class loading process

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.