StandardWrapper中的加载servlet方法

来源:互联网 发布:东莞谷歌优化 编辑:程序博客网 时间:2024/06/15 19:59


StandardWrapper

    /**     * Load and initialize an instance of this servlet, if there is not already     * at least one initialized instance.  This can be used, for example, to     * load servlets that are marked in the deployment descriptor to be loaded     * at server startup time.     */    public synchronized Servlet loadServlet() throws ServletException {        // Nothing to do if we already have an instance or an instance pool        if (!singleThreadModel && (instance != null))            return instance;        PrintStream out = System.out;        if (swallowOutput) {            SystemLogHandler.startCapture();        }        Servlet servlet;        try {            long t1=System.currentTimeMillis();            // If this "servlet" is really a JSP file, get the right class.            // HOLD YOUR NOSE - this is a kludge that avoids having to do special            // case Catalina-specific code in Jasper - it also requires that the            // servlet path be replaced by the <jsp-file> element content in            // order to be completely effective            String actualClass = servletClass;            if ((actualClass == null) && (jspFile != null)) {                Wrapper jspWrapper = (Wrapper)                    ((Context) getParent()).findChild(Constants.JSP_SERVLET_NAME);                if (jspWrapper != null) {                    actualClass = jspWrapper.getServletClass();                    // Merge init parameters                    String paramNames[] = jspWrapper.findInitParameters();                    for (int i = 0; i < paramNames.length; i++) {                        if (parameters.get(paramNames[i]) == null) {                            parameters.put                                (paramNames[i],                                  jspWrapper.findInitParameter(paramNames[i]));                        }                    }                }            }            // Complain if no servlet class has been specified            if (actualClass == null) {                unavailable(null);                throw new ServletException                    (sm.getString("standardWrapper.notClass", getName()));            }            // Acquire an instance of the class loader to be used            Loader loader = getLoader();            if (loader == null) {                unavailable(null);                throw new ServletException                    (sm.getString("standardWrapper.missingLoader", getName()));            }            ClassLoader classLoader = loader.getClassLoader();            // Special case class loader for a container provided servlet            //              if (isContainerProvidedServlet(actualClass) &&                     ! ((Context)getParent()).getPrivileged() ) {                // If it is a priviledged context - using its own                // class loader will work, since it's a child of the container                // loader                classLoader = this.getClass().getClassLoader();            }            // Load the specified servlet class from the appropriate class loader            Class classClass = null;            try {                if (System.getSecurityManager() != null){                    final ClassLoader fclassLoader = classLoader;                    final String factualClass = actualClass;                    try{                        classClass = (Class)AccessController.doPrivileged(                                new PrivilegedExceptionAction(){                                    public Object run() throws Exception{                                        if (fclassLoader != null) {                                            return fclassLoader.loadClass(factualClass);                                        } else {                                            return Class.forName(factualClass);                                        }                                    }                        });                    } catch(PrivilegedActionException pax){                        Exception ex = pax.getException();                        if (ex instanceof ClassNotFoundException){                            throw (ClassNotFoundException)ex;                        } else {                            getServletContext().log( "Error loading "                                + fclassLoader + " " + factualClass, ex );                        }                    }                } else {                    if (classLoader != null) {                        classClass = classLoader.loadClass(actualClass);                    } else {                        classClass = Class.forName(actualClass);                    }                }            } catch (ClassNotFoundException e) {                unavailable(null);                getServletContext().log( "Error loading " + classLoader + " " + actualClass, e );                throw new ServletException                    (sm.getString("standardWrapper.missingClass", actualClass),                     e);            }            if (classClass == null) {                unavailable(null);                throw new ServletException                    (sm.getString("standardWrapper.missingClass", actualClass));            }            // Instantiate and initialize an instance of the servlet class itself            try {                servlet = (Servlet) classClass.newInstance();            } catch (ClassCastException e) {                unavailable(null);                // Restore the context ClassLoader                throw new ServletException                    (sm.getString("standardWrapper.notServlet", actualClass), e);            } catch (Throwable e) {                unavailable(null);                // Restore the context ClassLoader                throw new ServletException                    (sm.getString("standardWrapper.instantiate", actualClass), e);            }            // Check if loading the servlet in this web application should be            // allowed            if (!isServletAllowed(servlet)) {                throw new SecurityException                    (sm.getString("standardWrapper.privilegedServlet",                                  actualClass));            }            // Special handling for ContainerServlet instances            if ((servlet instanceof ContainerServlet) &&                  (isContainerProvidedServlet(actualClass) ||                    ((Context)getParent()).getPrivileged() )) {                ((ContainerServlet) servlet).setWrapper(this);            }            classLoadTime=(int) (System.currentTimeMillis() -t1);            // Call the initialization method of this servlet            try {                instanceSupport.fireInstanceEvent(InstanceEvent.BEFORE_INIT_EVENT,                                                  servlet);                if( System.getSecurityManager() != null) {                    Class[] classType = new Class[]{ServletConfig.class};                    Object[] args = new Object[]{((ServletConfig)facade)};                    SecurityUtil.doAsPrivilege("init",                                               servlet,                                               classType,                                               args);                } else {                    servlet.init(facade);                }                // Invoke jspInit on JSP pages                if ((loadOnStartup >= 0) && (jspFile != null)) {                    // Invoking jspInit                    DummyRequest req = new DummyRequest();                    req.setServletPath(jspFile);                    req.setQueryString("jsp_precompile=true");                    DummyResponse res = new DummyResponse();                    if( System.getSecurityManager() != null) {                        Class[] classType = new Class[]{ServletRequest.class,                                                        ServletResponse.class};                        Object[] args = new Object[]{req, res};                        SecurityUtil.doAsPrivilege("service",                                                   servlet,                                                   classType,                                                   args);                    } else {                        servlet.service(req, res);                    }                }                instanceSupport.fireInstanceEvent(InstanceEvent.AFTER_INIT_EVENT,                                                  servlet);            } catch (UnavailableException f) {                instanceSupport.fireInstanceEvent(InstanceEvent.AFTER_INIT_EVENT,                                                  servlet, f);                unavailable(f);                throw f;            } catch (ServletException f) {                instanceSupport.fireInstanceEvent(InstanceEvent.AFTER_INIT_EVENT,                                                  servlet, f);                // If the servlet wanted to be unavailable it would have                // said so, so do not call unavailable(null).                throw f;            } catch (Throwable f) {                getServletContext().log("StandardWrapper.Throwable", f );                instanceSupport.fireInstanceEvent(InstanceEvent.AFTER_INIT_EVENT,                                                  servlet, f);                // If the servlet wanted to be unavailable it would have                // said so, so do not call unavailable(null).                throw new ServletException                    (sm.getString("standardWrapper.initException", getName()), f);            }            // Register our newly initialized instance            singleThreadModel = servlet instanceof SingleThreadModel;            if (singleThreadModel) {                if (instancePool == null)                    instancePool = new Stack();            }            fireContainerEvent("load", this);            loadTime=System.currentTimeMillis() -t1;        } finally {            if (swallowOutput) {                String log = SystemLogHandler.stopCapture();                if (log != null && log.length() > 0) {                    if (getServletContext() != null) {                        getServletContext().log(log);                    } else {                        out.println(log);                    }                }            }        }        return servlet;    }



    /**     * Unload all initialized instances of this servlet, after calling the     * <code>destroy()</code> method for each instance.  This can be used,     * for example, prior to shutting down the entire servlet engine, or     * prior to reloading all of the classes from the Loader associated with     * our Loader's repository.     *     * @exception ServletException if an exception is thrown by the     *  destroy() method     */    public synchronized void unload() throws ServletException {        // Nothing to do if we have never loaded the instance        if (!singleThreadModel && (instance == null))            return;        unloading = true;        // Loaf a while if the current instance is allocated        // (possibly more than once if non-STM)        if (countAllocated > 0) {            int nRetries = 0;            while ((nRetries < 21) && (countAllocated > 0)) {                if ((nRetries % 10) == 0) {                    log.info(sm.getString("standardWrapper.waiting",                                          new Integer(countAllocated)));                }                try {                    Thread.sleep(100);                } catch (InterruptedException e) {                    ;                }                nRetries++;            }        }        ClassLoader oldCtxClassLoader =            Thread.currentThread().getContextClassLoader();        ClassLoader classLoader = instance.getClass().getClassLoader();        PrintStream out = System.out;        if (swallowOutput) {            SystemLogHandler.startCapture();        }        // Call the servlet destroy() method        try {            instanceSupport.fireInstanceEvent              (InstanceEvent.BEFORE_DESTROY_EVENT, instance);            Thread.currentThread().setContextClassLoader(classLoader);            if( System.getSecurityManager() != null) {                SecurityUtil.doAsPrivilege("destroy",                                           instance);                SecurityUtil.remove(instance);                                       } else {                instance.destroy();            }            instanceSupport.fireInstanceEvent              (InstanceEvent.AFTER_DESTROY_EVENT, instance);        } catch (Throwable t) {            instanceSupport.fireInstanceEvent              (InstanceEvent.AFTER_DESTROY_EVENT, instance, t);            instance = null;            instancePool = null;            nInstances = 0;            fireContainerEvent("unload", this);            unloading = false;            throw new ServletException                (sm.getString("standardWrapper.destroyException", getName()),                 t);        } finally {            // restore the context ClassLoader            Thread.currentThread().setContextClassLoader(oldCtxClassLoader);            // Write captured output            if (swallowOutput) {                String log = SystemLogHandler.stopCapture();                if (log != null && log.length() > 0) {                    if (getServletContext() != null) {                        getServletContext().log(log);                    } else {                        out.println(log);                    }                }            }        }        // Deregister the destroyed instance        instance = null;        if (singleThreadModel && (instancePool != null)) {            try {                Thread.currentThread().setContextClassLoader(classLoader);                while (!instancePool.isEmpty()) {                    if( System.getSecurityManager() != null) {                        SecurityUtil.doAsPrivilege("destroy",                                                   ((Servlet) instancePool.pop()));                        SecurityUtil.remove(instance);                                               } else {                        ((Servlet) instancePool.pop()).destroy();                    }                }            } catch (Throwable t) {                instancePool = null;                nInstances = 0;                unloading = false;                fireContainerEvent("unload", this);                throw new ServletException                    (sm.getString("standardWrapper.destroyException",                                  getName()), t);            } finally {                // restore the context ClassLoader                Thread.currentThread().setContextClassLoader                    (oldCtxClassLoader);            }            instancePool = null;            nInstances = 0;        }        singleThreadModel = false;        unloading = false;        fireContainerEvent("unload", this);    }



0 0
原创粉丝点击