-
Notifications
You must be signed in to change notification settings - Fork 714
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Event Re-Registration #45
Comments
I accept. How does level triggered & reregistration work on other platforms (not counting windows)? |
IIRC, kqueue is edge triggered only, but it does support one-shot. |
Quick google search:
So it seems possible to implement on those systems. What API do you have in mind? Add an option to Also, how would a re-registration API differ from the existing register fn? |
Two ways:
I'd allow register to selectively specify interest (maybe supply an IoEventKInd of IOEVENTALL as a convenience for people) |
Re 1), register should take the interests, see #33. 2 makes sense, I had unloaded epoll from my brain :P |
Resolved by 0122914 |
There are a couple fundamental flaws in using Edge Triggered without One Shot.
Data Loss due to non notification
The first and most major is that if the read() in response to a read-event doesn't consume all of the data from the socket's buffer, it will never be notified about data again, which means the read-event won't be called again and the data will remain forever alone.
Starvation
The model of needing to consume all data out of a socket can lead to starvation of other sockets if there is an extreme amount of data being sent into that socket. A better model would be to consume a small amount of data per each socket, in turn, and go back to epoll_wait.
There are two solutions to this:
Level Triggered
This is easier for people to get right, as you'll always be notified if data is present in the case of read, or the socket is ready in case of write. The downside is it can be spammy, you don't need to be constantly notified of Writable events if you don't care about writing. A web server is a great example, it only needs to write after it receives a request. The solution is, obviously, to allow an application to un-register its interest in writing when it doesn't care about writing.
Edge Triggered with One Shot
This is the recommended approach. This would also require frequent re-registration, but epol_ctl is a very cheap syscall (cheaper than read() returning EAGAIN)
This would require every read and writer to re-register their interest in reading and writing after every epoll_wait call that returns events for that FD.
This solves both of the above problems. Epoll_wait will return fds who have data waiting regardless of whether it has been resting a while or has recently arrived.
IMO, the best approach is to let the user specify if they want edge triggered vs level triggered. But regardless of that model, there should definitely be a reregister function.
The text was updated successfully, but these errors were encountered: