/** * Allocate an initialized instance of this Servlet that is ready to have * its <code>service()</code> method called. If the servlet class does * not implement <code>SingleThreadModel</code>, the (only) initialized * instance may be returned immediately. If the servlet class implements * <code>SingleThreadModel</code>, the Wrapper implementation must ensure * that this instance is not allocated again until it is deallocated by a * call to <code>deallocate()</code>. * 分配此Servlet的初始化实例,该实例已准备好调用其service()方法。 * 如果servlet类没有实现SingleThreadModel,则可能立即返回(only)初始化的实例。 * 如果servlet类实现了SingleThreadModel, * 包装器实现必须确保在调用deallocate()释放该实例之前不会再次分配该实例。 * * @exception ServletException if the servlet init() method threw * an exception * @exception ServletException if a loading error occurs */ @Override public Servlet allocate()throws ServletException { //如果当前正在卸载此servlet,则抛出异常 if (unloading) { thrownewServletException(sm.getString("standardWrapper.unloading", getName())); } booleannewInstance=false;
// If not SingleThreadedModel, return the same instance every time // 如果不是SingleThreadedModel,则每次返回相同的实例 // singleThreadModel:这个servlet是否实现了SingleThreadModel接口?,这个接口已经被弃用了。 // 也就是说实现了singleThreadModel接口,每次返回不同的Servlet if (!singleThreadModel) { // 如果需要,加载并初始化我们的实例 if (instance == null || !instanceInitialized) { synchronized (this) { //如果没有实例的话,加载Servlet if (instance == null) { try { if (log.isDebugEnabled()) { log.debug("Allocating non-STM instance"); }
// Note: We don't know if the Servlet implements // SingleThreadModel until we have loaded it. instance = loadServlet(); newInstance = true; if (!singleThreadModel) { // For non-STM, increment here to prevent a race // condition with unload. Bug 43683, test case // #3 countAllocated.incrementAndGet(); } } catch (ServletException e) { throw e; } catch (Throwable e) { ExceptionUtils.handleThrowable(e); thrownewServletException(sm.getString("standardWrapper.allocate"), e); } } //如果没有初始化的话,初始化Servlet if (!instanceInitialized) { initServlet(instance); } } }
if (singleThreadModel) { if (newInstance) { // Have to do this outside of the sync above to prevent a // possible deadlock synchronized (instancePool) { instancePool.push(instance); nInstances++; } } } else { if (log.isTraceEnabled()) { log.trace(" Returning non-STM instance"); } // For new instances, count will have been incremented at the // time of creation if (!newInstance) { countAllocated.incrementAndGet(); } return instance; } }
/** * Return this previously allocated servlet to the pool of available * instances. If this servlet class does not implement SingleThreadModel, * no action is actually required. * * @param servlet The servlet to be returned * * @exception ServletException if a deallocation error occurs */ @Override publicvoiddeallocate(Servlet servlet)throws ServletException {
// If not SingleThreadModel, no action is required if (!singleThreadModel) { countAllocated.decrementAndGet(); return; }
// Unlock and free this instance //解锁并释放此实例 synchronized (instancePool) { countAllocated.decrementAndGet(); instancePool.push(servlet); instancePool.notify(); }