NOTE
2.72 3.注册selector
调用 bind - doBind - initAndRegister - channelFactory.newChannel() - init(channel) - ChannelFuture regFuture = config().group().register(channel);我们重点看这
这是历史学习笔记,可能存在过时或不完整的理解。
调用
bind
- doBind
- initAndRegister
- channelFactory.newChannel()
- init(channel)
- ChannelFuture regFuture = config().group().register(channel);我们重点看这个
在register上打个断点,最终经过的调用栈 io.netty.channel.MultithreadEventLoopGroup#register(io.netty.channel.Channel) io.netty.channel.SingleThreadEventLoop#register(io.netty.channel.Channel) io.netty.channel.SingleThreadEventLoop#register(io.netty.channel.ChannelPromise) io.netty.channel.AbstractChannel.AbstractUnsafe#register
public final void register(EventLoop eventLoop, final ChannelPromise promise) {
if (eventLoop == null) {
throw new NullPointerException("eventLoop");
}
if (isRegistered()) {
promise.setFailure(new IllegalStateException("registered to an event loop already"));
return;
}
if (!isCompatible(eventLoop)) {
promise.setFailure(
new IllegalStateException("incompatible event loop type: " + eventLoop.getClass().getName()));
return;
}
//将eventLoop关联到此channel,之后channel的所有操作都是通过eventLoop
AbstractChannel.this.eventLoop = eventLoop;
if (eventLoop.inEventLoop()) {
register0(promise);//实际注册
} else {
try {
eventLoop.execute(new Runnable() {
@Override
public void run() {
register0(promise);
}
});
} catch (Throwable t) {
logger.warn(
"Force-closing a channel whose registration task was not accepted by an event loop: {}",
AbstractChannel.this, t);
closeForcibly();
closeFuture.setClosed();
safeSetFailure(promise, t);
}
}
}
- register0
doRegister();//调用jdk底层注册io.netty.channel.nio.AbstractNioChannel#doRegister
pipeline.invokeHandlerAddedIfNeeded();
//调用channelhandler的channelRegistered方法
pipeline.fireChannelRegistered();