diff options
author | Yorhel <git@yorhel.nl> | 2016-09-06 19:37:34 +0200 |
---|---|---|
committer | Yorhel <git@yorhel.nl> | 2016-09-06 19:37:34 +0200 |
commit | efe595493c9a8dd1e4df3b9045fff012521449c8 (patch) | |
tree | cb1d03aaa426707495c58427c69b81c9f62abaea /src/listener.rs | |
parent | 39515558ad68edffc6fe52936714fcefbfc58949 (diff) |
Add accept() backoff timer + tcp idle timer + minor eventloop API improvements
Diffstat (limited to 'src/listener.rs')
-rw-r--r-- | src/listener.rs | 25 |
1 files changed, 17 insertions, 8 deletions
diff --git a/src/listener.rs b/src/listener.rs index 293099e..fcac06d 100644 --- a/src/listener.rs +++ b/src/listener.rs @@ -2,8 +2,9 @@ use mio::{Ready,Token,Event}; use mio::tcp::TcpListener; use std::net::SocketAddr; use std::io::{Result,ErrorKind}; +use std::time::Duration; use config::Config; -use eventloop::{Machine,Context,EventLoop}; +use eventloop::{Machine,Context,EventLoop,TToken}; use itf_http; @@ -11,7 +12,8 @@ use itf_http; struct Listener { sock: TcpListener, addr: SocketAddr, - io: Token + io: Token, + timeout: TToken, } @@ -22,7 +24,8 @@ impl Listener { Ok(Listener { sock: sock, addr: *addr, - io: Token(0) + io: Token(0), + timeout: TToken(0), }) } } @@ -30,8 +33,8 @@ impl Listener { impl Machine for Listener { fn init(&mut self, ctx: &mut Context) { - self.io = ctx.assign(); - ctx.register(&self.sock, self.io, Ready::readable()); + self.io = ctx.register(&self.sock, Ready::readable()); + self.timeout = ctx.alloc_timeout(); info!("Listening on {}", self.addr); } @@ -42,11 +45,13 @@ impl Machine for Listener { match err.kind() { ErrorKind::WouldBlock | ErrorKind::Interrupted | - ErrorKind::TimedOut => { }, + ErrorKind::TimedOut => { /* Uninteresting temporary errors */ }, _ => { error!("Error accepting on {}: {}", self.addr, err); - // If the error is persistent, we may be getting into an infinite loop. - // TODO: Have a back-off timer here (especially for EMFILE). + // Stop listening for short time. If this error is not persistent (like + // EMFILE), it will solve itself by just waiting. Not much else we can do. + ctx.deregister(&self.sock, self.io); + ctx.reset_timeout(self.timeout, Duration::from_millis(500)); } } }, @@ -56,6 +61,10 @@ impl Machine for Listener { } } } + + fn timeout(&mut self, ctx: &mut Context, _: TToken) { + self.io = ctx.register(&self.sock, Ready::readable()); + } } |