Class Loading Architecture Java Class Loaders

The findClass method uses whatever mechanism it deems appropriate to load the class e.g., by reading a class file from the file system or from an HTTP server. It is then responsible for creating the protection domain associated with the class and using the next method to create the Class class object.

6.3.2.3 The defineClass methods

These methods all take an array of Java bytecodes and some information that specifies the permissions associated with the class represented by those bytecodes. They all return the Class class object: protected final Class defineClassString name, byte[] b, int off, int len throws ClassFormatError protected final Class defineClassString name, byte[] b, int off, int len, ProtectionDomain protectionDomain throws ClassFormatError protected final Class defineClassString name, byte[] b, int off, int len, CodeSource cs throws ClassFormatError Create a class based on the bytecodes in the given array. The protection domain associated with the class varies based on which form is used: In the first method, the class is assigned to the default protection domain. ◊ In the second method, the class is assigned to the given protection domain. ◊ In the third method, the protection domain is defined by the class loader based on the given code source. ◊ The third method in this list is available only within the SecureClassLoader class and its subclasses including the URLClassLoader class. When you use that method, the class loader will ask what permissions are associated with a particular code source by calling this method: protected PermissionCollection getPermissionsCodeSource cs Return the permissions that should be associated with the given code source. The default implementation of this method calls the getPermissions method of the Policy class. Note that this gives you two effective ways in which to override the policy set up by policy files: by supplying your own Policy class or by supplying your own secure class loader that overrides this method.

6.3.3 Responsibilities of the Class Loader

When you implement a class loader, you override some or all of the methods weve just listed. In sum, the class loader must perform the following steps: The security manager is consulted to see if this program is allowed to access the class in question. If it is not, a security exception is thrown. This step is optional; it should be implemented at the beginning of the loadClass method. This corresponds to the use of the accessClassInPackage permission. 1. If the class loader has already loaded this class, it finds the previously defined class object and returns that object. This step is built into the loadClass method. 2. Otherwise, the class loader consults its parent to see if the parent knows how to load the class. This is a recursive operation, so the system class loader will always be asked first to load a class. This prevents programs from providing alternate definitions of classes in the core API but a clever class loader can defeat that protection. This step is built into the loadClass method. 3. The security manager is consulted to see if this program is allowed to create the class in question. If it is not, a security exception is thrown. This step is optional; if implemented, it should appear at the 4. 104 beginning of the findClass method. Note that this step should take place after the parent class loader is queried rather than at the beginning of the operation as is done with the access check. No Sun−supplied class loader implements this step; it corresponds to the defineClassInPackage permission. The class file is read into an array of bytes. The mechanism by which the class loader reads the file and creates the byte array will vary depending on the class loader which, after all, is one of the points of having different class loaders. This occurs in the findClass method. 5. The appropriate protection domain is created for the class. This can come from the default security model i.e., from the policy files, and it can be augmented or even replaced by the class loader. Alternately, you can create a code source object and defer definition of the protection domain. This occurs in the findClass method. 6. Within the findClass method, a Class object is constructed from the bytecodes by calling the defineClass method. If you used a code source in step 6, the getPermissions method will be called to find the permissions associated with the code source. The defineClass method also ensures that the bytecodes are run through the bytecode verifier. 7. Before the class can be used, it must be resolved −− which is to say that any classes that it immediately references must also be found by this class loader. The set of classes that are immediately referenced contains any classes that the class extends as well as any classes used by the static initializers of the class. Note that classes that are used only as instance variables, method parameters, or local variables are not normally loaded in this phase: they are loaded when the class actually references them although certain compiler optimizations may require that these classes be loaded when the class is resolved. This step happens in the loadClass method. 8. In the next two sections, well see how this plays out in each of the class loader types. Note that we do not show how to subclass the ClassLoader class directly: all class loaders should subclass the SecureClassLoader class or its subclasses instead.

6.3.4 Using the URL Class Loader

If you want to use a custom class loader, the easiest route is to use the URL class loader. This limits the number of methods that you have to override. To construct an instance of this class, use one of the following constructors: public URLClassLoaderURL urls[] public URLClassLoaderURL urls[], ClassLoader parent Construct a class loader based on the given array of URLs. This class loader attempts to find a class by searching each URL in the order in which it appears in the array. The parent of this class loader will be the class loader passed to the constructor or, if one is not provided, the class loader of the class that is creating the URLClassLoader object. An instance of the URLClassLoader class may also be obtained via one of these methods: public static URLClassLoader newInstanceURL[] urls public static URLClassLoader newInstanceURL[] urls, ClassLoader parent Create and return a URL class loader. The difference between these methods and constructing a URL class loader directly is that the class loader returned from these methods will call the security managers checkPackageAccess method before it attempts to define a class. Only class loaders obtained this way will perform that optional step unless you write your own class loader to perform that step. Chapter 6. Java Class Loaders