negative timeout in Rainbows::Fiber::Base

Lin Jen-Shin (godfat) godfat at
Sun Aug 26 00:12:52 UTC 2012

On Sat, Aug 25, 2012 at 10:45 AM, Eric Wong <normalperson at> wrote:
> The original code looks wrong and confusing :x

I guess I know your intension in the new code now :)
I can't apply the new patch, so I'll assume the new
code is as following:

    fibs.each { |fib| fib.resume }

    max_sleep = 1.0
    if max
      max -=
      return 0 if max < 0.0
      return max_sleep if max > max_sleep

I once thought that if `max <`, it should return 0,
because apparently we don't want to wait in this case.
But I am not sure if passing timeout as 0 would mean to
wait forever... thinking that maybe 0.0001 might be better?
Not sure if this would be a concern, or 0 means don't wait
at all, that would be ideal in this case.

> It's been a while since I've looked hard at the Fiber* stuff (not a fan
> of it personally).  However, I don't think abs() is correct, either.

I can smell from the code that those are not well polished,
since it seems a lot of things are missing. For example,
there is Rainbows::Fiber::IO::Socket, but no TCPSocket.
I blindly tried to create a TCPSocket version by creating
a new class extended from Kgio::TCPSocket and include

Well, I think it works, if using correctly, for example it
does not accept domain names as built-in TCPSocket,
and not all of the methods are respecting fibers.

But I like the idea to patch the socket, that way, we can
turn existing library to run under certain network architecture.
For instance, this HTTP client accepts passing different
socket class:

    @default_socket_class = TCPSocket
    @default_ssl_socket_class = OpenSSL::SSL::SSLSocket

    class << self
      attr_accessor :default_socket_class, :default_ssl_socket_class

I didn't try if passing Rainbows' fiber sockets would work or not,
but I think in theory it should work. I think Tony did this for his:
Quoted from README:

Replacement classes: Celluloid::IO includes replacements for the core
TCPServer and TCPSocket classes which automatically use an evented
mode inside of Celluloid::IO actors. They're named
Celluloid::IO::TCPServer and Celluloid::IO::TCPSocket, so they're
automatically available inside your class when you include

Not sure if this is the way to go, but an interesting idea. At least
better than implementing every single client in both eventmachine
and built-in sockets I guess...

So speaking to celluloid-io, there's already Revactor and Coolio
support, what about celluloid-io? Last time I tried Coolio,
occasionally it would crash with internal assertion failures...
I would love to see if there's other alternatives to eventmachine.

Also, there is CoolioFiberSpawn, CoolioThreadPool and so on
so forth, why not EventMachineFiberSpawn and EventMachineThreadPool?
Actually we are running EventMachineFiberSpawn on production
at the moment, as shown in:
class REMFClient < Rainbows::EventMachine::Client
  def app_call input{ super }.resume

(well, neverblock works too, but it doesn't seem to be
maintained now and I don't understand why it's a gem
with a lot of codes but not as simple as above. As this
sense, I feel async_sinatra is so wrong, but not sure
if I missed something here.)

It works great for us at the moment, though I am thinking about
switching to threads, too, since it's a lot more flexible than fibers.

Sorry that I might be asking too many questions in a single thread.
If you're interested in how I am testing them, I put my testing codes
I am thinking about if I should be giving a talk on
about ruby application servers, promoting unicorn family.
It is one of the reasons to try out all of the options.

Thanks for your time :D

More information about the rainbows-talk mailing list