If I would write:
int selectedChannels = selector.select(); Set selectedKeys = selector.selectedKeys(); if ( selectedChannels != selectedKeys.size() ) { // Selector.select() returned because of a call to Selector.wakeup() // so do synchronization. } // Continue with handling selected channels.
would it correctly detect the wakeup-call?
Backgroundinformation:
I'm writing a server which most of the time just receives packets and stores them in a file. Very rarely the application has the need to send itself a special packet. For this it initiates a connection (from a different thread) to the server socket:
SocketChannel channel = SocketChannel.open(); channel.configureBlocking( false ); channel.connect( new InetSocketAddress( InetAddress.getLocalHost(), PORT )); selector.wakeup(); SelectionKey key = channel.register( selector, SelectionKey.OP_CONNECT );
The problem is that SelectableChannel.register() might block if the main thread is already in Selector.select(). To prevent this from happening I'm calling Selector.wakeup() which let's the main thread return prematurely from select(). To make sure the other thread has the chance to complete the register-call, I would have to synchronize the main thread, but I would have to do it after every return from select(). If I could detect whether it returned from select() because of a wakeup() call, then I could optimize it for just this case.
So, in theory the top code snippet should work, but I was wondering whether it would only do so, because it relies on some unspecified behavior?
Thanks for any hints.