I have a program that opens a TCPSocket, connects it to a server, and
then creates a thread which loops until the socket closes, reading from
the socket and processing the data read. It calls IO.select() to wait
until there is data available to read. Meanwhile, another thread can
close the socket in certain circumstances. If the first thread is in
IO.select() when the socket is closed, the result is unpredictable -
sometimes the select() returns and sometimes it blocks. I’m not sure of
the circumstances that cause it to block or not - it seems random.
So, is there some way to make it reliably unblock? Or is there something
that the second thread can do to cause the select() to return (set a
flag on the socket before closing it, or something)?
This is with Ruby 2.0.0 p247 on Centos 5 Linux if that’s significant.
On Mon, Jul 15, 2013 at 9:53 AM, Graham Menhennitt
<[email protected]
wrote:
Hello Rubyists,
I have a program that opens a TCPSocket, connects it to a server, and
then creates a thread which loops until the socket closes, reading from
the socket and processing the data read. It calls IO.select() to wait
until there is data available to read.
Why don’t you just use a blocking read if you have a separate thread per
socket anyway? Select is only useful if you want to have a single
thread
process several file descriptors.
Meanwhile, another thread can
close the socket in certain circumstances. If the first thread is in
IO.select() when the socket is closed, the result is unpredictable -
sometimes the select() returns and sometimes it blocks. I’m not sure of
the circumstances that cause it to block or not - it seems random.
Hmmm. That sounds a bit odd. I would have expected select to return.
Maybe there’s a race condition in the std lib.
So, is there some way to make it reliably unblock? Or is there something
that the second thread can do to cause the select() to return (set a
flag on the socket before closing it, or something)?
You could work with a timeout but that seems a bit like a workaround.
This is with Ruby 2.0.0 p247 on Centos 5 Linux if that’s significant.
I had actually simplified a bit what I told you about my use case -
there was a reason for using select(). But you’re right - I changed the
program to use a blocking read instead, and it now works. I suspect
there’s some bug in select(), but I’m not sure how to reproduce it. Yes,
a timeout would probably work, but not very elegant.
Thank for your help,
Graham
This forum is not affiliated to the Ruby language, Ruby on Rails framework, nor any Ruby applications discussed here.