`
mabusyao
  • 浏览: 254656 次
  • 性别: Icon_minigender_1
  • 来自: 南京
社区版块
存档分类
最新评论

Tomcat 中的有状态线程池

阅读更多
Tomcat中的connector负责将从客户端发出的请求封装成Request对象,再交由processor进行处理。

为了提高性能,connector内部实现了一个简单的多例模式来获取processor,在启动阶段,会有一定数量的processor提前被产生并保留在内存中,当需要时直接从内存中取。如果当前所有processor都被占用,则会继续产生新的processor并丢进内存缓存。
    /**
     * The current number of processors that have been created.
     */
    private int curProcessors = 0;
    
    /**
     * The minimum number of processors to start at initialization time.
     */
    protected int minProcessors = 5;

    /**
     * The maximum number of processors allowed, or <0 for unlimited.
     */
    private int maxProcessors = 20;

    /**
     * The set of processors that have been created but are not currently
     * being used to process a request.
     */
    private Stack<HttpProcessor> processors = new Stack<HttpProcessor>();

    /**
     * Get Processor from stack if there still exist, or create new one 
     * if current processor number didn't more than max number.
     * Otherwise, null will be returned.
     * 
     * @return instance of HttpProcessor
     */
	protected HttpProcessor getProcessor() {
        synchronized (processors) {
            if (processors.size() > 0) {
                return  processors.pop();
            }
            if ((maxProcessors > 0) && (curProcessors < maxProcessors)) {
                return (newProcessor());
            } else {
                if (maxProcessors < 0) {
                    return (newProcessor());
                } else {
                    return (null);
                }
            }
        }
       }

	private HttpProcessor newProcessor() {
          HttpProcessor processor = new HttpProcessor(this);
          processor.start();
        
          curProcessors++;
        
          return processor;
	}

	public void recycle(HttpProcessor processor) {
		processors.push(processor);
	}


由于processor本身并不消耗资源,因此如此创建方式对性能并没有多大的提升。重点是对于每个processor实例,Tomcat将启动一个新的线程来处理socket,以此来或多更大的吞吐量。

以下是Tomcat如何启动多线程的processor并不断监听状态变化的方案。

HttpProcessor继承Runable接口,每当我们调用其start()方法时,都会启动一个新的线程:
	public void start() {
		Thread thread = new Thread(this);
		thread.setDaemon(true);

		thread.start();
	}

	public void run() {
		while (!stopped) {
			Socket socket = await();

			if (socket == null) {
				continue;
			}

			process(socket);

			connector.recycle(this);
		}
	}

	private synchronized Socket await() {
		while (!available) {
			try {
				wait();
			} catch (InterruptedException e) {
				// Do nothing.
			}
		}

		Socket socket = this.socket;
		available = false;
		notifyAll();

		return socket;
	}

当processor新线程启动时,它做了这样一系列的事情:
1. 等待其他线程通知,当某个通知到来时,验证available是否为false,如果为true,继续等待,否则进入第二步。
2. 获取实例变量socket的值,
3. 将available改成false。
4. 通知其他线程状态改变。
5. 对socket进行相应处理(process方法)。
6. connector资源回收该对象。

而在connector主线程中,是通过这种方式调用processor的:
      HttpProcessor processor = getProcessor();

      processor.assign(socket);


processor的assign方法如下:
	/**
	 * The entry point of HttpProcessor. Assign an socket to the processor, it
	 * will start a new thread.
	 * 
	 * 
	 * @param socket
	 */
	public synchronized void assign(Socket socket) {
		while(available) {
			try {
				wait();
			} catch (InterruptedException e) {
				// Do nothing.
			}
		}
		
		this.socket = socket;
		available = true;
		notifyAll();
	}

这个方法首先监听其他线程通知,一旦获得available为false了,便将socket值设置为新的值,并将available值改为true,最后通知其他线程。

assign方法和run方法运行在两个不同的线程中: connector主线程以及processor子线程。当主线程获得一个新的socket,就会assign给processor对象,并通知processor子线程。一旦通知完毕,主线程就返回继续监听其它socket。 而processor子线程收到通知后会对被assign的socket进行相应的处理。

通过这种方式,线程之间各司其职,获得了最大的性能提升。
分享到:
评论

相关推荐

    Tomcat6.0共享线程池配置

    在深入探讨Tomcat 6.0中的线程池配置之前,有必要对线程池的基本概念进行简单回顾: - **线程池**:预先创建一定数量的线程,并存储在一个池子中,当有新的任务提交时,可以从池中取出一个空闲线程来执行该任务。 - ...

    TOMCAT的线程池源码

    当队列满时,提交任务的线程会被阻塞,直到队列中有空闲位置。反之,当队列为空时,等待工作的线程会被阻塞,直到有新任务加入。这种设计使得线程池能够根据实际负载动态调整工作线程的数量。 TaskThread则封装了...

    Tomcat线程池实现简介

    Java实现的线程池位于`tomcat-util.jar`中,初始化时创建了一个200维的线程数组,预创建了5个线程作为初始的空闲线程。这些线程在没有请求时处于等待状态,当收到请求时,线程池会分配一个空闲线程来处理请求。...

    检测Tomcat运行状态-自动重启

    - **类结构**:程序主要由`CheckTomcat`类构成,其中包含了`checkTomcatIsAlive`方法用于检测Tomcat状态,以及`main`方法作为程序入口。 - **代码示例**: - **初始化配置**:在`main`方法中初始化`monitorurl`和`...

    tomcat中文帮助文档

    在Windows、Linux或Mac OS等不同操作系统上安装Tomcat的过程略有差异。通常,你需要下载对应平台的Tomcat二进制包,解压到合适的目录,然后根据系统环境变量配置`CATALINA_HOME`指向Tomcat的安装路径。在Windows上...

    Tomcat深入剖析pdf+源码(Tomcat运行原理)

    9. **JMX管理**:通过Java Management Extensions(JMX),开发者可以远程监控和管理Tomcat的运行状态,如查看线程池状态、内存使用情况等。 10. **性能优化**:优化Tomcat涉及调整线程池大小、缓存设置、减少上...

    自动监控 Windows平台Tomcat运行监控并自动重启

    另一个可能的解决方案是使用第三方监控工具,例如Nagios、Zabbix或Prometheus等,这些工具能提供更全面的系统监控,包括CPU使用率、内存占用、网络状态以及Tomcat特定的指标,如线程池状态和HTTP请求响应时间。...

    Tomcat参考手册中文版chm

    这份《Tomcat参考手册中文版chm》为开发者提供了全面的指引,无论是初学者还是有经验的管理员,都能从中获取所需的信息,解决在使用Tomcat过程中遇到的问题。通过深入学习和实践,我们可以更好地驾驭这个强大的Java...

    Tomcat 接口文档 API

    8. **JMX (Java Management Extensions)**: Tomcat使用JMX暴露管理MBeans(Managed Beans),允许通过JMX代理远程监控和管理Tomcat服务器的状态,包括启动/停止应用、查看线程池状态、调整配置等。 9. **Clustering...

    Tomcat压缩包

    5. **部署Web应用**:在Tomcat中部署Web应用通常有以下几种方式: - 将应用的WAR文件放入`webapps`目录下,Tomcat会自动解压并部署。 - 使用`manager`应用通过HTTP上传WAR文件。 - 在Eclipse中右键点击项目,选择...

    tomcat6.0.18 解压缩版

    7. **日志和错误处理**: Tomcat的运行日志主要记录在`logs`目录下,如`catalina.out`、`host-manager.out`等,这对于排查问题和监控服务器状态非常重要。 8. **安全性**: Tomcat支持基本的身份验证和授权,如通过`...

    tomcat自动关闭原因

    - **死锁**:多线程应用程序中可能出现的死锁问题,也会使Tomcat服务陷入不可恢复的状态,最终导致服务自动关闭。 - **资源泄露**:如数据库连接、文件句柄等资源的不正确释放,随着时间推移,会逐渐消耗系统资源,...

    linux tomcat 64

    5. **配置服务器**:在`conf/server.xml`文件中,你可以配置Tomcat的端口、线程池、连接器以及其他服务器设置。默认情况下,Tomcat使用8080端口监听HTTP请求。 6. **部署应用**:将你的Java Web应用程序(WAR文件)...

    Tomcat8.0.53

    定期更新Tomcat到最新稳定版本有助于保持系统的安全性和稳定性。 总之,Apache Tomcat 8.0.53作为一个流行的Java Web服务器,是开发和部署Java应用的重要工具。理解和掌握其工作原理、配置与管理方法,对于任何Java...

    apache-tomcat-11.0.0-M17-windows-x64.zip

    8. **性能优化**:Tomcat可以通过调整线程池大小、内存分配、连接器设置等方式进行性能优化。例如,增加`maxThreads`参数可以处理更多并发请求。 9. **监控与管理**:通过内置的JMX(Java Management Extensions)...

    How Tomcat Works 中文版

    10. **错误处理与日志**:Tomcat有详细的错误页面机制,可以根据不同的HTTP状态码返回相应的错误页面。Juli日志系统提供了灵活的日志配置,可以根据需求定制日志级别和格式。 《How Tomcat Works》这本书将帮助读者...

    apache-tomcat-7.0.100

    7. **性能优化**:Tomcat可以通过调整线程池大小、启用连接器优化、缓存管理等方式进行性能优化。例如,`conf/server.xml`中的`Connector`元素允许配置最大连接数、空闲超时等参数。 8. **部署应用**:Web应用程序...

    tomcat服务器8.0版本 apache-tomcat-8.0.15.zip

    在本文中,我们将深入探讨Tomcat 8.0的关键特性、安装与配置过程以及如何部署Web应用程序。 首先,Tomcat 8.0引入了Java EE 7的兼容性,这是它的一大改进。这意味着它可以支持包括WebSocket API、JAX-RS 2.0 ...

    tomcat中多线程对于servlet处理的4篇资料

    在处理请求时,Tomcat会从一个预先创建的线程池中取出线程来执行Servlet的service方法。这个线程池通常被称为" Coyote Connector ",负责接收并处理来自HTTP连接器的请求。 2. **线程池管理** 在Tomcat 5.5.17版本...

    Tomcat7性能优化

    Tomcat支持三种运行模式:BIO、NIO 和 APR,每种模式都有其特点和适用场景: - **BIO (Blocking I/O)**:这是Tomcat默认的模式,每个连接都会占用一个独立的线程来处理请求,适用于低并发场景。但在高并发环境下,...

Global site tag (gtag.js) - Google Analytics