tomcat8.5中,Acceptor线程与PollerClient线程的工作流程

本文详细介绍了Tomcat8.5中Acceptor和Poller线程的启动流程及两者如何协作处理请求。Acceptor线程通过NioEndpoint的startInternal()启动,Poller线程在启动时创建Selector。当Acceptor接收到客户端连接时,将通道注册到Poller的事件队列。Poller线程循环检查事件队列并处理,通过线程池执行具体任务。整个过程基于NIO编程实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

tomcat启动后,有两个(两类)线程在工作,Acceptor和PollerClient,分别在idea中frams栈帧中可以debug看到。主要功能在这篇文章中有简单介绍。

原文链接:https://blog.youkuaiyun.com/u011385186/article/details/53148702

这里主要记录两个问题,
1.Acceptor和Poller作为runnable,他们的start()是如何开启的?

tomcat启动过程主要是catlina,coyote,processor,endpoint等组件的链式调用,先init链式调用一遍,再start和startInternal链式调用一遍
在这里插入图片描述

acceptor线程的start:NioEndPoint的startInternal()方法中的startAcceptorThreads()方法调用
poller线程的start:NioEndPoint的startInternal()方法中调用,其中poller的空参构造调用了selector.open(),即一个poller对应一个selector
在这里插入图片描述

2.tomcat启动后,二者run()方法运行中如何产生关联去处理请求的?

第1个问题说明了acceptor和PollerClient这俩线程是如何开启的,现在要记录这两个线程是如何工作的,也就是他们的run方法。

acceptor的run()方法:
1. socketChannel = serverSocketChannel.accept(); nio中的serverSocketChannel一直接收客户端请求,
2. setSocketOptions -> getPoller0().register(channel) -> addEvent® -> events.offer(event) -> queue[insert++] = t; serversocketchannel接收到客户端的channel后,取到一个poller线程,包装channel后注册channel,然后添加到poller的事件队列(同步队列SyncronizedQueue)events中

poller的run()方法():

  1. while true循环中, hasEvents = events();检查事件同步队列中events.poll()是否有事件,有就开始处理事件(此事件是由acceptor线程添加到队列当中的);
  2. .Iterator iterator =selector.selectedKeys().iterator()并遍历,处理所有事件 -> processKey() -> processSocket(READ/WRITE分别处理) -> Executor executor = getExecutor(); -> executor.execute(sc);调用线程池处理。
    《这里的线程池,就是在tomcat配置文件server.xml中配置的线程池,如果对其命名,接下来debug会看到该名字的线程在处理请求》
    在这里插入图片描述
    在这里插入图片描述
    主要核心应该是tomcat基于nio编程的NioEndPoint和NioChannel这两个类,更多地mark以后有机会再看。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值