From normalperson at yhbt.net Sun Oct 4 22:15:41 2009 From: normalperson at yhbt.net (Eric Wong) Date: Sun, 4 Oct 2009 19:15:41 -0700 Subject: [Rev-talk] [PATCH 0/2] listener error handling cleanups Message-ID: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> I've been hitting EAGAIN (first patch) a lot in testing, I don't think I've hit ECONNABORTED yet but I know it's certainly possible. Eric Wong (2): listener: remove warning about spuriously readable sockets listener: ignore ECONNABORTED on accept() Both of these patches are also pushed to git://yhbt.net/rev lib/rev/listener.rb | 3 +-- 1 files changed, 1 insertions(+), 2 deletions(-) -- Eric Wong From normalperson at yhbt.net Sun Oct 4 22:15:42 2009 From: normalperson at yhbt.net (Eric Wong) Date: Sun, 4 Oct 2009 19:15:42 -0700 Subject: [Rev-talk] [PATCH 1/2] listener: remove warning about spuriously readable sockets In-Reply-To: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> References: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> Message-ID: <1254708943-13516-2-git-send-email-normalperson@yhbt.net> Non-blocking accept() calls to a listen socket shared between multiple processes is prone to (harmless) EAGAIN errors. This is because kernels can wakeup all sleeping processes sharing that listen socket to accept() and only one of the thundering herd of will be successful in accept()-ing the client. --- lib/rev/listener.rb | 1 - 1 files changed, 0 insertions(+), 1 deletions(-) diff --git a/lib/rev/listener.rb b/lib/rev/listener.rb index 7069737..d5d02a7 100644 --- a/lib/rev/listener.rb +++ b/lib/rev/listener.rb @@ -40,7 +40,6 @@ module Rev begin on_connection @listen_socket.accept_nonblock rescue Errno::EAGAIN - STDERR.puts "warning: listener socket spuriously readable" end end end -- Eric Wong From normalperson at yhbt.net Sun Oct 4 22:15:43 2009 From: normalperson at yhbt.net (Eric Wong) Date: Sun, 4 Oct 2009 19:15:43 -0700 Subject: [Rev-talk] [PATCH 2/2] listener: ignore ECONNABORTED on accept() In-Reply-To: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> References: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> Message-ID: <1254708943-13516-3-git-send-email-normalperson@yhbt.net> ECONNABORTED can happen if a client resets/closes the socket before the accept() has been called by the receiver. These are less common in most modern servers with accept filters, but still possible. Since these errors are harmless like EAGAIN, avoid propagating them up the stack. --- lib/rev/listener.rb | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/lib/rev/listener.rb b/lib/rev/listener.rb index d5d02a7..a9ac5b6 100644 --- a/lib/rev/listener.rb +++ b/lib/rev/listener.rb @@ -39,7 +39,7 @@ module Rev def on_readable begin on_connection @listen_socket.accept_nonblock - rescue Errno::EAGAIN + rescue Errno::EAGAIN, Errno::ECONNABORTED end end end -- Eric Wong From normalperson at yhbt.net Mon Oct 5 14:26:06 2009 From: normalperson at yhbt.net (Eric Wong) Date: Mon, 5 Oct 2009 11:26:06 -0700 Subject: [Rev-talk] [PATCH 0/2] listener error handling cleanups In-Reply-To: References: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> Message-ID: <20091005182606.GB25569@dcvr.yhbt.net> Tony Arcieri wrote: > Can you include the rationale you've provided for swallowing these > exceptions in the comments? Yup, here it is (also pushed to git://yhbt.net/rev): >From 79e2768ece2473c38d1c4cda27e1b994cf2f2c51 Mon Sep 17 00:00:00 2001 From: Eric Wong Date: Mon, 5 Oct 2009 11:22:51 -0700 Subject: [PATCH] listener: document rationale for EAGAIN/ECONNABORTED handling --- lib/rev/listener.rb | 9 +++++++++ 1 files changed, 9 insertions(+), 0 deletions(-) diff --git a/lib/rev/listener.rb b/lib/rev/listener.rb index a9ac5b6..c4795c1 100644 --- a/lib/rev/listener.rb +++ b/lib/rev/listener.rb @@ -40,6 +40,15 @@ module Rev begin on_connection @listen_socket.accept_nonblock rescue Errno::EAGAIN, Errno::ECONNABORTED + # EAGAIN can be triggered here if the socket is shared between + # multiple processes and a thundering herd is woken up to accept + # one connection, only one process will get the connection and + # the others will be awoken. + # ECONNABORTED is documented in accept() manpages but modern TCP + # stacks with syncookies and/or accept()-filtering for DoS + # protection do not see it. In any case this error is harmless + # and we should instead spend our time with clients that follow + # through on connection attempts. end end end -- Eric Wong From normalperson at yhbt.net Mon Oct 5 18:12:39 2009 From: normalperson at yhbt.net (Eric Wong) Date: Mon, 5 Oct 2009 15:12:39 -0700 Subject: [Rev-talk] [PATCH 0/2] listener error handling cleanups In-Reply-To: References: <1254708943-13516-1-git-send-email-normalperson@yhbt.net> <20091005182606.GB25569@dcvr.yhbt.net> Message-ID: <20091005221239.GA32379@dcvr.yhbt.net> Tony Arcieri wrote: > Would you mind updating the 0.3.1 section of the CHANGES file to reflect > what you've done? Not at all, done and also pushed out to git://yhbt.net/rev >From 3dc8dcaa479695824a47b41c800ee41b0dc6056c Mon Sep 17 00:00:00 2001 From: Eric Wong Date: Mon, 5 Oct 2009 15:10:37 -0700 Subject: [PATCH] update CHANGES with the latest Rev::Listener changes --- CHANGES | 6 +++++- 1 files changed, 5 insertions(+), 1 deletions(-) diff --git a/CHANGES b/CHANGES index 67be935..39d9668 100644 --- a/CHANGES +++ b/CHANGES @@ -1,6 +1,10 @@ 0.3.1: -* +* Removed warning about spuriously readable sockets from Rev::Listener + +* Rev::Listener ignores ECONNABORTED from accept_nonblock + +* Document rationale for EAGAIN/ECONNABORTED handling in Rev::Listener 0.3.0: -- Eric Wong From normalperson at yhbt.net Tue Oct 13 03:54:05 2009 From: normalperson at yhbt.net (Eric Wong) Date: Tue, 13 Oct 2009 00:54:05 -0700 Subject: [Rev-talk] bump Rev::VERSION for next release Message-ID: <20091013075405.GA20447@dcvr.yhbt.net> Looks like this hasn't been updated in a couple of releases. --- This is just a reminder since I don't actually do releases and hence don't control version numbers. I just got confused when writing something that spits out Rev::VERSION lib/rev.rb | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/lib/rev.rb b/lib/rev.rb index 620fd19..1b82f1c 100644 --- a/lib/rev.rb +++ b/lib/rev.rb @@ -23,6 +23,6 @@ require 'iobuffer' end module Rev - Rev::VERSION = '0.2.3' unless defined? Rev::VERSION + Rev::VERSION = '0.3.1' unless defined? Rev::VERSION def self.version() VERSION end end -- Eric Wong From normalperson at yhbt.net Sun Oct 18 22:38:38 2009 From: normalperson at yhbt.net (Eric Wong) Date: Sun, 18 Oct 2009 19:38:38 -0700 Subject: [Rev-talk] [PATCH] fix on_timer event_callback for TimerWatcher Message-ID: <20091019023837.GA17116@dcvr.yhbt.net> There was a timer_watcher event_callback defined for the IOWatcher class in the timer_watcher.rb file. I assume this is a copy-and-paste error and a grep of the source shows no "timer_watcher" methods ever being dispatched. So change this to allow the "on_timer" method to be overidden when given a block. Also added a spec to show it works. --- As usual, pushed up to git://yhbt.net/rev lib/rev/timer_watcher.rb | 4 +- spec/timer_watcher_spec.rb | 49 ++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 51 insertions(+), 2 deletions(-) create mode 100644 spec/timer_watcher_spec.rb diff --git a/lib/rev/timer_watcher.rb b/lib/rev/timer_watcher.rb index ecc5b52..8fe59ca 100644 --- a/lib/rev/timer_watcher.rb +++ b/lib/rev/timer_watcher.rb @@ -5,13 +5,13 @@ #++ module Rev - class IOWatcher + class TimerWatcher # The actual implementation of this class resides in the C extension # Here we metaprogram proper event_callbacks for the callback methods # These can take a block and store it to be called when the event # is actually fired. extend Meta - event_callback :timer_watcher + event_callback :on_timer end end diff --git a/spec/timer_watcher_spec.rb b/spec/timer_watcher_spec.rb new file mode 100644 index 0000000..dde994c --- /dev/null +++ b/spec/timer_watcher_spec.rb @@ -0,0 +1,49 @@ +require File.dirname(__FILE__) + '/../lib/rev' + +describe Rev::TimerWatcher do + + it "can have the on_timer callback defined after creation" do + @watcher = Rev::TimerWatcher.new(0.01, true) + nr = '0' + @watcher.on_timer { nr.succ! }.should == nil + @watcher.attach(Rev::Loop.default).should == @watcher + nr.should == '0' + Rev::Loop.default.run_once + nr.should == '1' + end + + it "can be subclassed" do + class MyTimerWatcher < Rev::TimerWatcher + TMP = '0' + + def on_timer + TMP.succ! + end + end + @watcher = MyTimerWatcher.new(0.01, true) + @watcher.attach(Rev::Loop.default).should == @watcher + MyTimerWatcher::TMP.should == '0' + Rev::Loop.default.run_once + MyTimerWatcher::TMP.should == '1' + end + + it "can have the on_timer callback redefined between runs" do + @watcher = Rev::TimerWatcher.new(0.01, true) + nr = '0' + @watcher.on_timer { nr.succ! }.should == nil + @watcher.attach(Rev::Loop.default).should == @watcher + nr.should == '0' + Rev::Loop.default.run_once + nr.should == '1' + @watcher.detach + @watcher.on_timer { nr = :foo }.should == nil + @watcher.attach(Rev::Loop.default).should == @watcher + nr.should == '1' + Rev::Loop.default.run_once + nr.should == :foo + end + + after :each do + @watcher.detach if defined?(@watcher) + end +end -- Eric Wong From normalperson at yhbt.net Mon Oct 19 14:58:44 2009 From: normalperson at yhbt.net (Eric Wong) Date: Mon, 19 Oct 2009 11:58:44 -0700 Subject: [Rev-talk] [ANN] Rainbows! HTTP server powered by Revactor (or Rev) Message-ID: <20091019185844.GD11442@dcvr.yhbt.net> Hi all, Just wanted to make sure that fans of Revactor and/or Rev know there's a new HTTP server that can use either Revactor or Rev (without Revactor) as it's network concurrency backend[1]. It's based on Unicorn so it supports the Rack specification and uses Unix-only preforking[2] + signal management. Linux 2.6+ is recommended for epoll support, but it should work for kqueue users since it's all based on libev. Feedback from users of all systems supported by Rev would be greatly appreciated. On a related note: Revactor has been really nice to work with, hopefully this can help increase 1.9 adoption :) [1] - it also supports two threading models that can be loaded independently of Rev/Revactor and will eventually support EventMachine, too. [2] - local concurrency != remote concurrency, (this really is the whole point of Unicorn + Rainbows!). Preforking is to handle the former, Rev/Revactor is for the latter. Links: * http://rainbows.rubyforge.org/ * rainbows-talk at rubyforge.org * git://git.bogomips.org/rainbows.git This will be my first/last announcement to {rev,revactor}-talk lists, but of course I'll post any improvements I have for rev/revactor on here in the future :> -- Eric Wong