
抓到Netty一个Bug,聊一下Netty是如何高效接收网络连接的(六)
6. ChannelRead事件的响应
接收客户端连接.png
在前边介绍接收连接的整体核心流程框架的时候,我们提到main reactor线程是在一个do{.....}while(...)循环read loop中不断的调用ServerSocketChannel#accept方法来接收客户端的连接。
当满足退出read loop循环的条件有两个:
1.在限定的16次读取中,已经没有新的客户端连接要接收了。退出循环。
2.从NioServerSocketChannel中读取客户端连接的次数达到了16次,无论此时是否还有客户端连接都需要退出循环。
main reactor就会退出read loop循环,此时接收到的客户端连接NioSocketChannel暂存与List<Object> readBuf集合中。
随后main reactor线程会遍历List<Object> readBuf集合中的NioSocketChannel,并在NioServerSocketChannel的pipeline中传播ChannelRead事件。
传播ChannelRead事件.png
最终ChannelRead事件会传播到ServerBootstrapAcceptor中,这里正是Netty处理客户端连接的核心逻辑所在。
ServerBootstrapAcceptor主要的作用就是初始化客户端NioSocketChannel,并将客户端NioSocketChannel注册到Sub Reactor Group中,并监听OP_READ事件。
在ServerBootstrapAcceptor 中会初始化客户端NioSocketChannel的这些属性。
比如:从Reactor组EventLoopGroup childGroup,用于初始化NioSocketChannel中的pipeline用到的ChannelHandler childHandler,以及NioSocketChannel中的一些childOptions和childAttrs。
正是在这里,netty会将我们在?《详细图解Netty Reactor启动全流程》的启动示例程序中在ServerBootstrap中配置的客户端NioSocketChannel的所有属性(child前缀配置)初始化到NioSocketChannel中。
以上示例代码中通过ServerBootstrap配置的NioSocketChannel相关属性,会在Netty启动并开始初始化NioServerSocketChannel的时候将ServerBootstrapAcceptor的创建初始化工作封装成异步任务,然后在NioServerSocketChannel注册到Main Reactor中成功后执行。
在经过ServerBootstrapAccptor#chanelRead回调的处理之后,此时客户端NioSocketChannel中pipeline的结构为:
客户端channel pipeline初始结构.png
随后会将初始化好的客户端NioSocketChannel向Sub Reactor Group中注册,并监听OP_READ事件。
如下图中的步骤3所示:
netty中的reactor.png
