@Override
    protected synchronized Class<?> loadClass(String sClassName, boolean bResolve)
    throws ClassNotFoundException
    {
        logDebug(LogArea.CLASS, "LOADING %s (resolve=%b)", sClassName, bResolve);
        // Each thread must have THIS class loader set as a context class loader. 
        // This is required to prevent failure finding a class or resource from  
        // external JAR requested by a common class loaded from rt.jar.  
        // The best example is external LnF, explained in steps:
        // 1. Application requests 'javax.swing.JOptionPane'.
        // 2. THIS class loader passes request to system default class loader 
        // to load the class from rt.jar.
        // 3. The class 'javax.swing.JOptionPane' is loaded by system default class
        // loader.
        // 4. The class 'javax.swing.JOptionPane' is requesting 'UIDefaults.getUI()'
        // for component, which resides in external LnF JAR.
        // 5. The class loader which is used to load the requested component is 
        // current thread context class loader if it is set, otherwise the parent  
        // thread context class loader, or the default system class loader
        // for the top level thread. 
        // 6. The system class loader is used to load requested component if
        // thread context class loader is not set. The default system class loader is 
        //   - sun.misc.Launcher$AppClassLoader - run from file system or JAR
        //   - com.sun.jnlp.JNLPClassLoader     - run from JNLP
        // System class loaders cannot find requested component in external 
        // JAR and throw exception.
        // 
        // Setting thread context class loader for the top thread in invokeMain()
        // method is sufficient for most cases. It fails for new threads created
        // not from the main thread.
        //
        // Setting thread context class loader below must be reconsidered 
        // for specific conditions.
        //
        // Essential reading:
        //   - Thread.getContextClassLoader() JavaDoc.
        //   - http://www.javaworld.com/javaworld/javaqa/2003-06/01-qa-0606-load.html
        Thread.currentThread().setContextClassLoader(this);
        
        Class<?> c = null;
        try {
            // Step 0. This class is already loaded by system classloader.
            if (getClass().getName().equals(sClassName)) {
                return JarClassLoader.class;
            }
            // Step 1. Load from JAR.
            if (isLaunchedFromJar()) {
                try {
                    c = findJarClass(sClassName); // Do not simplify! See "finally"!
                    return c;
                } catch (JarClassLoaderException e) {
                    if (e.getCause() == null) {
                        logDebug(LogArea.CLASS, "Not found %s in JAR by %s: %s",
                                sClassName, getClass().getName(), e.getMessage());
                    } else {
                        logDebug(LogArea.CLASS, "Error loading %s in JAR by %s: %s",
                                sClassName, getClass().getName(), e.getCause());
                    }
                    // keep looking...
                }
            }
            // Step 2. Load by parent (usually system) class loader.
            // Call findSystemClass() AFTER attempt to find in a JAR.
            // If it called BEFORE it will load class-in-jar using
            // SystemClassLoader and "infect" it with SystemClassLoader.
            // The SystemClassLoader will be used to load all dependent
            // classes. SystemClassLoader will fail to load a class from
            // jar-in-jar and to load dll-in-jar.
            try {
                // No need to call findLoadedClass(sClassName) because it's called inside:
                ClassLoader cl = getParent();
                c = cl.loadClass(sClassName);
                // System classloader does not define ProtectionDomain->CodeSource - null 
                logInfo(LogArea.CLASS, "Loaded %s by %s", sClassName, cl.getClass().getName());
                return c;
            } catch (ClassNotFoundException e) {
            }
            // What else?
            throw new ClassNotFoundException("Failure to load: " + sClassName);
        } finally {
            if (c != null  &&  bResolve) {
                resolveClass(c);
            }
        }
    } // loadClass()