Survey
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
Prof. Dr. Th. Letschert CS5233 Components – Models and Engineering - Komponententechnologien Master of Science (Informatik) Class Loading I Seite 1 Classloading / survey Java Virtual Machine Components Byte Code verifier Interpreter Just In Time Compiler Security Manager Garbage Collector Class Loader These components perform the following actions: The class loader loads a .class file. The class file is verified by the Byte code verifier. The Interpreter interprets and byte code. The Just in Time compiler translates it into machine language. The garbage collector will regularly check for unreferenced variables and frees the memory. Seite 2 Th Letschert Classloading / survey Class Loading Class loading is an essential and unique feature of Java Classes are the one and only “real” (run-time) component of Java Class loading thus is the foundation of all component technology based on Java Try java -verbose:class test.Test to see what classes get loaded. Seite 3 Th Letschert Classloading / Survey Process of Class Loading – Physical loading find and read the bytecode – Linking create class and resolve links to other classes Verify bytecode Create data structure (fields, methods, ···) resolve links to other classes – Initializing initialize static components of the class Seite 4 Th Letschert Classloading / Survey Class loader survey Bootstrap class loader (native code within the JVM) loads core Java classes (like java.lang.String) Extension class loader (sun.misc.Launcher$ExtClassLoader) loads system wide extensions without naming them on the class path System class loader (sun.misc.Launcher$AppClassLoader) loads classes on the class path User defined class loaders Seite 5 Th Letschert Classloading / Example public class CheckLoaders { public static void main(String[] args) throws ClassNotFoundException { System.out.println("class loader for Integer: " + Integer.class.getClassLoader()); System.out.println("class loader for this class: " + CheckLoaders.class.getClassLoader()); System.out.println("Loader for an extension class : " + Class.forName("sun.net.spi.nameservice.dns.DNSNameService").getClassLoader()); System.out.println("class loader for application class loader (i.e. for " + CheckLoaders.class.getClassLoader().getClass().getCanonicalName() + ") : " + CheckLoaders.class.getClassLoader().getClass().getClassLoader()); } } class loader for Integer: null class loader for this class: sun.misc.Launcher$AppClassLoader@6d6f0472 Loader for an extension class : sun.misc.Launcher$ExtClassLoader@138d107f class loader for application class loader (i.e. for sun.misc.Launcher.AppClassLoader) : null Remarks: null means no Java-loader loaded, the bootstrap loader loaded sun.net.spi.nameservice.dns.DNSNameService is a class in ../jdk1.6.0_23/jre/lib/ext/dnsns.jar Seite 6 Th Letschert Classloading / Bootstrap Class Loader Bootstrap (Primodal) Class Loader Part of the JVM Loads internal classes (e.g. the application class loader) Loads basic classes in package java.* Path to classes is defined by system property sun.boot.class.path Typically the essential jar is <jdk>/jre/lib/rt.jar Path can be set by JVM options -Xbootclasspath:<directories and/or jars> -Xbootclasspath/a:<directories and/or jars> -Xbootclasspath/p:<directories and/or jars> sets the paths appends to the path prepends to the path System. out .println(System. getProperty ("sun.boot.class.path" )); /usr/lib64/jvm/java-1.6.0-openjdk-1.6.0/jre/lib/resources.jar :/usr/lib64/jvm/java-1.6.0-openjdk-1.6.0/jre/lib/rt.jar : ... java -Xbootclasspath:/usr/lib64/jvm/java-1.6.0-openjdk-1.6.0/jre/lib/rt.jar test.CheckLoaders Seite 7 Th Letschert Classloading / Extension Class Loader Extension Class Loader Java Class Loads “extension classes” Extension classes – Extensions: groups of classes (jar-files) that extend the Java platform – classes of system-wide relevance that can be loaded without placing them on the classpath http://download.oracle.com/javase/tutorial/ext/index.html Path to classes is defined by system property java.ext.dirs typically <jdk>/jre/lib/ext Path can be set by JVM option -Djava.ext.dirs=<directory/directories> System. out .println(System. getProperty ("java.ext.dirs" )); /usr/lib64/jvm/java-1.6.0-openjdk-1.6.0/jre/lib/ext :/usr/java/packages/lib/ext java -Djava.ext.dirs= /usr/local/bin/Java/JDK-7/jdk1.7.0/jre/lib/ext/ test.CheckLoaders Seite 8 Th Letschert Classloading / System (Application) Class Loader System (Application) Class Loader Java Class Loads “application classes” Path to classes is defined by system property java.class.path Path can be set by JVM option -cp <directories and or jars> or -classpath <directories and or jars> or -Djava.class.path=<directories and or jars> or the CLASSPATH environment variable Class-names may appear several times on the classpath – this is not an error – it is not specified which class gets loaded – the “first one” ? System. out .println(System. getProperty ("java.class.path" )); Seite 9 Th Letschert Classloading / User-defined (Custom) Class Loaders User-defined (Custom) Class Loaders Java Classes May be user-defined Load application classes “under program control” Seite 10 Th Letschert Class Loading / Principles Class Loading Process / Example – Some Loader L loads class C public class C { void f() { D d = new D(); } } it finds and reads the bytecode creates a java.lang.Class object as run-time representative of C. L is C's defining loader the defining loader will be used when loading classes referenced by C – Class D is referenced by C When asked to create an instance of D, JVM checks whether D is already loaded, if not: loading is delegated to the defining loader of C: L.loadClass(“D”) is called and creates a java.lang.Class object as run-time representative of D. L is D's initiating loader if L actually loaded D it also D's defining loader if loading was delegated by L to some other loader L' then L' is D's defining loader JVM now can resolve the reference to D and create an instance of it Seite 11 Th Letschert Classloading / Principles Class Loading principles – Delegation model Class loaders first delegate loading to their parent classes upwards in the delegation hierarchy are always preferred – Visibility principle Classes load by parent-loaders are visible to children Classes loaded by child-loaders are invisible to parents – Uniqueness principle a class once laded will never be reloaded by another loader consequence of the delegation principle Seite 12 Th Letschert Classloading / Principles Class loader Parent First delegation model Bootstrap class Loader (inside JVM) $JAVAHOME/jre/lib/rt.jar Class loaders are organized in a tree structure Loader nearer to the root is used first Extension class Loader Loading order: $JAVAHOME/jre/lib/ext/*.jar 1. Already loaded (cache) 2. Delegate loading to parent System Class Loader User Defined Class Loader 3. Load self Reason: Security, system classes can't be overwritten $CLASSPATH User Defined Class Loader User Defined Class Loader Delegation Structure of class loaders First use loader nearer to root Seite 13 Th Letschert Class Loading / Principles Class loaders and class names defining loader (object) – Class-type identification class-types (classes for short) are identified by a combination of class name and defining loader: class loader that loaded the class (called ClassLoader.defineClass(···)) Thus class loaders define name-spaces class (-object) – Static vs dynamic class name static class name: name used by the compiler dynamic class name: class id at run-time: static name + loader Multiple classes with the same (static) name may be present at run-time – Defining and initiating loaders Defining loader : loader that loaded the class Initiating loader : loader that initiated loading: the loader that loaded a referencing class Seite 14 object public class C { void f() { D d = new D(); } } Defining loader of C is initiating loader of D Th Letschert Class Loading / Principles Class-loaders and class names Dynamic type name : <class-loader instance> + <static type name> Each class-loader instance will load at most one class with a given static name Different class-loader instances may load classes with the same static name these classes may be ● created form identical class-files or ● from completely different class-files in any case: the resulting classes are not compatible i.e.: no casts, no assignments of types with the same static name (may lead to error messages like “can not cast class C to class C”) Seite 15 Th Letschert Class Loading / Principles Class-loader name-spaces class-loader L's name-space: classes the loading of which L has initiated class C's name-space: the set of classes that C can/has reference(d) = the set of classes C's defining loader can/has load C is used somewhere and loaded by L. C references D. C and thus L initiate loading of D. D is actually loaded by L'. D references E. E's loading is initiated by D and thus by L'. E actually gets loaded by L''. C may references classes seen by L. D may reference classes seen by L'. E may reference classes seen by L''. Remark: These “run-time namespaces” add to / amend “compile-time name-spaces”, and may be associated with “run-time components”. Parent-first strategy: Search starts at the root E D defining loader defining loader public class C { void f() { D d = new D(); } } parent parent class-loader L'' parent classloader L' Name-space of loader L': all classes with L' as initiating loader classloader L C Name-space of loader L: all classes with L as initiating loader Seite 16 Th Letschert Classloading / Principles Class loaders and class names / Name-space consistency Multiple versions of a class may be loaded: – Option1: Identified if they have the same name: Solution of JVM prior to 1.2 Induces security problems – Option 2: Identified if loaded by the same defining loader Solution of JVM beginning with 1.2 Strategy (Liang / Bracha): Lazy loading with recording of loading constraints Loading Constraint: Loading of <C initiated by L1> and <C initiated by L2> will both result in <C defined by L3> Each time a class is actually loaded into the class cache all constraints are checked Each time a a new constraint is added, it is checked against all classes in the class cache Seite 17 Th Letschert Class Loading / Principles Name-space consistency Multiple versions of a class: Classes may be loaded by different loaders Old solution: they are identified! But this may lead to problems C is loaded by L1 L1 initiates loading of Delegated and of Spoofed class C { void f() { Spoofed x = Delegated.g(); } } loaded by L1 class Spoofed { ··· } loaded by L1 class Delegated { There are two versions of Spoofed } class Spoofed { ··· } loaded by L2 public static Spoofed g() { ··· } loaded by L2 Loading of Spoofed is initiated and done by L2 Loading of Delegated is initiated by L1 then is delegated to L2 conf: G. Bracha, S. Liang: Dynamic Class Loading in the Java Virtual Machine Seite 18 Th Letschert Classloading / Principles Name-space consistency Bracha / Liang solution: lazy loading with constraint recording class C { void f() { Spoofed x = Delegated.g(); } } loaded by L1 <Spoofed initiated by L 1 > <Spoofed loaded by L 3 > class Delegated { } public static Spoofed g() { ··· } loaded by L2 <Spoofed initiated by L 2 > Loading of Spoofed initiated by L1 or initiated by L2 must result in the same defining (actually loading) loader! Constraint: loading of Spoofed initiated by L 1 and loading of Spoofed initiated by L 2 will both result in Spoofed loaded by L3 for some L 3 Seite 19 Th Letschert Class Loading / Applications Class-loading from the class path package test; public class AClass { static { System.out.println("class AClass was loaded"); } { System.out.println("an Object of Aclass was created"); } } A Class package test; public class UserClass { public static void main(String[] args) { AClass anObject = new AClass(); } Loading the class from the classpath and instantiating it } class AClass was loaded an Object of Aclass was created Seite 20 Th Letschert Class Loading / Applications Class-loading from the class path via reflection package test; public class AClass { static { System.out.println("class AClass was loaded"); } { System.out.println("an Object of Aclass was created"); } } A Class package test; public class UserClass { public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException { Class<?> C = new UserClass() .getClass().getClassLoader () .loadClass("test.AClass"); Object anObject = C.newInstance(); } } Seite 21 From a class you can access its loader and use it for further loads Loading and instantiating the class Th Letschert Class Loading / Applications Class-loading via URLClassLoader load classes from outside of the classpath The URL loader will be used only if apackage.AClass can't be loaded by the system loader, i.e. is AClass is not on the classpath. (Delegation strategy!) package apackage; import java.net.MalformedURLException; import java.net.URL; import java.net.URLClassLoader; public class LoadingClass { public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, MalformedURLException { URL url = new URL("file://path/to/codebase/" ); Bootstrap class loader Extension class loader URLClassLoader urlLoader = new URLClassLoader (new URL[]{url}); Class<?> C = urlLoader.loadClass("apackage.AClass"); Object anObject = C.newInstance(); System class loader } } URL Class Loader Class loading using the URL loader Seite 22 Th Letschert Class Loading / Applications Loaded class is at place2 Class-loading via URLClassLoader ! be very careful with every syntactical detail package apackage; import java.net.MalformedURLException; import java.net.URL; import java.net.URLClassLoader; public class LoadingClass { / at the end means directory, no / means jar-file public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, MalformedURLException { URL url = new URL("file:/path/to/place2/" ); URLClassLoader urlLoader = new URLClassLoader(new URL[]{url}); } } Class<?> C = urlLoader.loadClass("apackage.AClass" ); Object anObject = C.newInstance(); Loading class is at place1 (place2 is not in the classpath) java -cp /path/to/place1 \ -Djava.security.manager \ -Djava.security.polic y=/path/to/PolicyFile.policy\ -Djava.security.debug =access,failure\ apackage.LoadingClass grant { permission java.security.AllPermission; Command line }; Policy file Seite 23 Th Letschert Class Loading / Applications Class-loading via URLClassLoader – Casts will not compile ! If a Class unknown to the compiler will be loaded Then its objects have to be used via refection! URL url = new URL("file:/path/to/place2/" ); URLClassLoader urlLoader = new URLClassLoader (new URL[]{url}); Class<?> C = urlLoader.loadClass("apackage.AClass" ); Object anObject = C.newInstance(); unknown here at place1 (not in the classpath) usage only via reflection apackage.AClass o = (apackage.AClass) anObject; o.f(); if apackage.AClass would be present at place1 (would be in the classpath) - the cast would succeed, but - AClass would be on the classpath and thus loaded by the system loader, whether you try to load it via the urlLoader or not! Method m = C.getMethod("f"); m.invoke(anObject, new Object[]{}); anObject can be used only via reflection Seite 24 Th Letschert Class Loading / Applications Compiling and loading common bases classes (interfaces) – A class CR (here Animal) referenced in C (here AnimalFarm) is implicitly loaded by the loader of C (AnimalFarm). AnimalFarm Animal Animal Animal Tiger Compile-time structure Cow url1 url2 classes have to be compiled in different but consistent source code structures A “base system” defines interface Animal and AnimalFarm. Extension1 (Component 1) contributes class Cow. Extension2 (Component 2) contributes class Tiger. Classpath of the base system contains Animal and AnimalFarm Url1 contains interface Animal and class Cow Url2 contains interface Animal and class Tiger There are three identical copies of interface Animal. They are necessary for the compiler. At run-time there should only be one instance of class Animal. Seite 25 Th Letschert Class Loading / Applications Compiling and loading common bases – Inconsistencies due to common classes loaded by different loaders are avoided by loading them by common loader upwards in the loader hierarchy – Due to the delegation model of class loading, classes loaded by different loaders may be cast to common bases types. initiating class loader AnimalFarm classpath Animal defining class loader ~ Animal Animal Run-time structure not loaded System ClassLoader URLClassLoader Cow url1 defining class loader defining class loader URLClassLoader Tiger url2 Base-class / interface Animal is referenced in AnimalFarm, Tiger and Cow. At run-time all these references go to the same class-object. (In contrast to compile time, where the references go to different class files.) As loading is delegated to the system loader, new versions of Animal are not loaded from url1 or url2. All (AnimalFarm, Cow and Tiger) use the same base class Animal! Seite 26 Th Letschert Class Loading / Available Loaders Always available ('actual') Loaders – Current class loader The loader that loads the class to which the current method belongs. Each class will use it's own loader to load other classes. So if A.class references B then B.class needs to be loadable by the loader of A.class or one of it's parents. used implicitly when a class A references another class used implicitly in calls like Class.classForName( className ) – Thread context class loader The class loader associated with the current thread is used explicitly available through Thread.getContextClassLoader() modifiable through Thread.setContextClassLoader() – System class loader (application loader) The class loader that loads from the classpath is used to load the Main-Class May be used explicitly available through ClassLoader.getSystemClassLoader() settable through the classpath or java -Djava.system.class.loader= <loader class> Seite 27 Th Letschert Class Loading / Available Loaders Thread Context Class Loader – – – – is never used implicitly is set in the main-thread to the system (application / class-path) loader is passed by a starting thread to the started thread may be used as an alternative class loader if “normal” class loading is not appropriate – e.g: usage in frameworks Seite 28 Th Letschert