While looking at Java and Android class loading mechanisms, some confusion on the way, please note.

Some conceptual understanding

What is the difference between the JDK and the JRE? JDK is the Java Development Kit. Simply said that JDK is for developers to use the SDK, it provides Java Development environment and running environment. SDK refers to Software Development Kit, which can include function libraries, compilers, etc. JRE refers to the Java Runtime environment. It is intended for users of Java programs rather than developers.

What are rt.jar, dt.jar, tools.jar? The rt.jar file is a very important one. Rt stands for runtime, which means runtime. Is an essential file for Java programs to run. Lang, java.util, java.io, java.net,java.applet, etc. Dt. jar is a library for the runtime environment, mainly swing packages, you want to use swing best add; Tools. jar is used by the system when compiling a class, that is, in javac.

What is the difference between lib/ and jre/lib? The JDK contains jar packages for the Java development environment, which are used by the JDK. For example, some tools in the JDK may need to use files in this directory. For example, compilers, etc. The lib of the JRE in the JDK is the JAR package required by the runtime in the development environment. The most typical is an imported external driver JAR package.

Before you understand what a DEX file is, take a look at the JVM, Dalvik, and ART. The JVM is a JAVA virtual machine used to run JAVA bytecode programs. Dalvik is a runtime environment designed by Google for Android platform, which is suitable for systems with limited memory and processor speed in mobile environment. ART, or Android Runtime, is a new Android Runtime environment designed by Google to replace Dalvik and released in Android 4.4. ART performs better than Dalvik. Android programs are generally developed using Java language, but Dalvik VM does not support the direct execution of Java bytecode, so it will translate, reconstruct, interpret and compress the compiled.class files. This process is processed by DX. After the processing is complete, the generated product will end with.dex and is called dex file. Dex file format is a compression format designed for Dalvik. Dex files are the product of many.class files that can be executed in the Android runtime environment.

Class loaders in the JVM

Bootstrap Class Loader

Is responsible for loading core libraries in the JDK, such as rt.jar and other core classes in jre/lib. Bootstrap Class Loader is the parent Loader of all classLoaders. It’s implemented in native code

It’s mainly responsible for loading JDK internal classes, typically rt.jar and other core libraries located in $JAVA_HOME/jre/lib directory. Additionally, Bootstrap class loader serves as a parent of all the other ClassLoader instances.

This bootstrap class loader is part of the core JVM and is written in native code. Different platforms might have different implementations of this particular class loader.

Extension Class Loader

The extended class loader is implemented by Sun’s ExtClassLoader (Sun.misc.Launcher$ExtClassLoader), It is responsible for loading into memory the class libraries in

/lib/ext or at the location specified by the system variable -djava.ext. dir. Developers can use the standard extension classloader directly.

System Class Loader

The system classloader is implemented by Sun’s AppClassLoader (sun.misc.launcher $AppClassLoader), which is responsible for placing the directory indicated by the user’s classpath (java-classpath or -djava.class. path variable, That is, the path of the current class and the path of the third-party library referenced by the class is loaded into memory. Developers can use the system class loader directly.

The system or application class loader, on the other hand, takes care of loading all the application level classes into the JVM. It loads files found in the classpath environment variable, -classpath or -cp command line option. Also, it’s a child of Extensions classloader.

The extension class loader is a child of the bootstrap class loader and takes care of loading the extensions of the standard core Java classes so that it’s available to all applications running on the platform.

Extension class loader loads from the JDK extensions directory, usually $JAVA_HOME/lib/ext directory or any other directory mentioned in the java.ext.dirs system property.

For example

public void printClassLoaders(a) throws ClassNotFoundException {
 
    System.out.println("Classloader of this class:"
        + PrintClassLoader.class.getClassLoader());
 
    System.out.println("Classloader of Logging:"
        + Logging.class.getClassLoader());
 
    System.out.println("Classloader of ArrayList:"
        + ArrayList.class.getClassLoader());
}
Copy the code

The run result is

Class loader of this class:sun.misc.Launcher$AppClassLoader@18b4aac2

Class loader of Logging:sun.misc.Launcher$ExtClassLoader@3caeaf62

Class loader of ArrayList:null

Classloader class inheritance relationship

classDiagram
Object <|-- ClassLoader
ClassLoader <|-- SecureClassLoader
SecureClassLoader <|-- URLClassLoader
URLClassLoader <|-- ExtClassLoader
URLClassLoader <|-- AppClassLoader
BootStrapClassLoader <-- ExtClassLoader
ExtClassLoader <-- AppClassLoader
AppClassLoader <-- ClassLoaderA
AppClassLoader <-- ClassLoaderB
Copy the code

ExtClassLoader belongs to the Extension ClassLoader and AppClassLoader belongs to the System ClassLoader.

Parent delegation mechanism

The JVM defaults to parental delegation when loading classes. In layman’s terms, when a particular classloader receives a request to load a class, it first delegates the loading task to the parent classloader, recursively (essentially, a recursive call to the loadClass function). Therefore, all load requests should eventually be routed to the top-level boot class loader. If the parent class loader can complete the classloading request, it returns success; Only if the parent class loader is unable to complete the load request will the child loader attempt to load itself. In fact, in most cases, the more basic classes are loaded by the higher-level loader.

The loading process is as follows:

  1. The source ClassLoader checks whether the Class has been loaded. If so, it returns the Class directly. If not, it delegates to the parent ClassLoader.
  2. The parent Class loader determines whether the Class has been loaded, returns the Class if it has been loaded, and delegates it to the parent Class loader if it has not.
  3. And so on until the ancestor class loader (reference class loader).
  4. The ancestor classloader determines whether the Class has been loaded. If so, it returns the Class directly. If not, it tries to find the Class bytecode file from its corresponding classpath and loads it. Class is returned directly if the load succeeds, and delegate to the subclass loader of the ancestor Class loader if the load fails.
  5. The subclass loader of the ancestor class loader tries to find and load the class bytecode file from its corresponding classpath. Class is returned directly if the load succeeds, and delegate to the grandchild of the ancestor classloader if the load fails.
  6. And so on up to the source ClassLoader.
  7. The source ClassLoader attempts to find and load the class bytecode file from its corresponding classpath. If the load succeeds, Class is returned directly, and if the load fails, the source ClassLoader does not delegate its subclass loader, but throws an exception.

Android’s class loader

classDiagram
Object <|-- ClassLoader
ClassLoader <|-- BaseDexClassLoader
ClassLoader <|-- SecureClassLoader
SecureClassLoader <|-- URLClassLoader
BaseDexClassLoader <|-- PathClassLoader
BaseDexClassLoader <|-- DexClassLoader
BaseDexClassLoader <|-- InMemoryDexClassLoader
ClassLoader <|-- BootClassLoader
BootClassLoader <-- PathClassLoader
Copy the code

A few points

  1. In Android, classes in class.dex in APK are loaded by PathClassLoader after the App is installed on the phone.
  2. In contrast, PathClassLoader can load only dex or APk files that have been installed. DexClassLoader does not have this restriction. It can load.jar and.apk files containing class.dex from SD cards. This is also the basis for plugins and hot fixes that load the dex you need to use without installing the application.A class loader that loads classes from .jar and .apk filescontaining a classes.dex entry. This can be used to execute code notinstalled as part of an application.
  3. SecureClassLoader and URLClassLoader are the same as in JDK8
  4. InMemoryDexClassLoader is a class loader added on Android8.0. It inherits from BaseDexClassLoader and is used to load dex files in the memory.
  5. BootClassLoader is created in the entry method of the Zygote process, and PathClassLoader is created when the Zygote process creates the SystemServer process.

confusion

The BootClassLoader is created in Zygote. The BootClassLoader is created in Zygote. The BootClassLoader is created in Zygote.

So with this problem, I studied the source code of Android API-level 28, and described the creation process of PathClassLoader in app with sequence diagram.

In ActivityThread, the BIND_APPLICATION message is sent to H in the ApplicationThread bindApplication method. H is also an inner class of ActivityThread, which inherits Handler. H then calls the ActivityThread’s handleBindApplicationf method, and the ActivityThread processes the message through several layers of calls before returning the PathClassLoader.

When and by whom is the bindApplication of the ApplicationThread in ActivityThread called? The call relationship is described as follows:

As you can see, ActivityThread has a static main method, which goes through the layers of calls and through the IPC action IActivityManager, calling AMS methods, and then through the IPC action IApplicationThread, The bindApplication method of the ApplicationThread of the ActivityThread is called.

IActivityManager corresponds to AMS, and IApplicationThread corresponds to the ApplicationThread of ActivityThread.

The static main method for ActivityThread is called by the app child after Zygote forks it.

reference

  • Blog.csdn.net/justloveyou…
  • www.baeldung.com/java-classl…
  • Jaeger.itscoder.com/android/201…
  • Juejin. Cn/post / 684490…
  • www.jianshu.com/p/a1f40b39b…
  • www.jianshu.com/p/fbea00880…
  • www.zhihu.com/question/50…