Java bytecode technology

Java Bytecode consists of one-byte instructions and theoretically supports a maximum of 256 opcodes. Java actually uses only about 200 opcodes, with some remaining opcodes reserved for debugging operations.

According to the nature of the instructions, they can be divided into four categories:

1. Stack operation instructions, including instructions to interact with local variables.

Example 3: iconst2 pushes the constant 2 onto the stack

2. Program flow control instructions.

Example: 1: if_icmpne

3. Object operation instructions, including method call instructions.

Example 2: Invokevirtual: used to invoke non-private instance methods

  1. Invokestatic: used to invokestatic methods.
  2. Invokespecial: Used to call private instance methods, constructors, and instance methods or constructors of the parent class using the super keyword, and the default method of the interface implemented.
  3. Invokevirtual: Used to invoke non-private instance methods.
  4. Invokeinterface: used to invokeinterface methods.
  5. Invokedynamic: used to invokedynamic methods.

Arithmetic operations and type conversion instructions.

For example, 4: i2d int to double

5. Others:

A. Exception handling

From ->to represents the monitoring code location.

Target: indicates the position where exception processing starts.

Type: indicates the type of the exception that is triggered.

B. Bytecode implementation of reflection

Invokevirtual method. invoke // Reflection calls copy codeCopy the code

Java class loader

Class lifecycle:

Loading: Looking for a Class file

2. Verification: Verification format and dependencies

3. Preparation: allocate memory for static fields, parse out the method table method table, allocate symbol references for other classes and their methods, fields corresponding to the specific address.

4. Resolution: Symbols are resolved to references (loading is triggered if symbolic references point to classes that are not loaded).

5. Initialization: constructors, static variable assignments, static code blocks.

Class loading timing

  1. When the VM starts, initialize the main class specified by the user.
  2. Initialize the target class of the new instruction when it encounters a new instruction for creating an instance of the target class.
  3. When an instruction that calls a static method is encountered, initialize the class of the static method;
  4. When an instruction is encountered that accesses a static field, initialize the class in which the static field resides.
  5. Initialization of a subclass triggers initialization of its parent class;
  6. If an interface defines the default method, the initialization of the class that implements the interface directly or indirectly triggers the initialization of the interface.
  7. Initialize a class when a reflection call is made to the class using the reflection API;
  8. The first time you call a MethodHandle instance, you initialize the class to which the method points.

Does not initialize (may be loaded)

1. Using a subclass to refer to a static field of a parent class triggers initialization of the parent class, not the subclass.

2. Define an array of objects without triggering initialization of the class.

3. Constants are stored in the constant pool of the calling class during compilation. In essence, there is no direct reference to the class in which the constant is defined, and the class in which the constant is defined is not triggered.

4. Getting a Class object by its name does not trigger Class initialization. Hello

.

5. If initialize is false, the Class will not be touched

Initialize the class. This parameter tells the virtual machine whether to initialize the class. Class.forName

(” Jvm.hello “) loads the Hello class by default.

6. The default loadClass method of the ClassLoader also does not trigger the initialization action (loaded, but

Uninitialized).

Java class loader

The bootstrapClassLoader is responsible for loading the most basic and important classes, such as those stored in jar packages in the LIB directory of the JRE (as well as those specified by the virtual machine parameter -xbootCLASspath). In addition to the launcher class loader, two other important class loaders are the Extension Class Loader and the Application Class Loader, both provided by the Java Core class library.

The parent of an ExtClassLoader is the launcher class loader. It is responsible for loading relatively minor but generic classes, such as those stored in jar packages in the LIB /ext directory of the JRE (and those specified by the system variable java.ext.dirs).

The parent of the AppClassLoader is the extension classloader. It is responsible for loading classes under the application path. (In this case, the application path is the path specified by the vm parameter -cp/-classpath, system variable java.class.path, or environment variable classpath.) By default, classes contained in an application are loaded by the application class loader.

Features: parent delegate, responsible dependency, cache loading.