Details
-
Type:
Bug
-
Status:
Resolved
-
Priority:
Minor
-
Resolution: Fixed
-
Affects Version/s: JRuby 1.5.3
-
Fix Version/s: JRuby 1.7.0.pre1
-
Component/s: None
-
Labels:None
-
Environment:repros under os x 10.6.4 with 1.6.0_22 and centos 5.4 with 1.6.0_21
-
Number of attachments :
Description
After doing a connect_nonblock then it appears that IO.select will always return immediately and indicate the socket is not writable, when it should instead block and eventually return that it is writable, assuming the connection succeeds.
Example below. Note that this does not appear to be a timing specific issue; the sleep 5 gives it plenty of time to connect, and the select does not wait for the timeout before returning. Presumably calling connect_nonblock again updates some state that was out of sync.
>> @timeout=5
=> 5
>> @host='google.com'
=> "google.com"
>> @port=80
=> 80
>> addrinfo = ::Socket::getaddrinfo(@host, @port).first
=> ["AF_INET", 80, "pz-in-f99.1e100.net", "74.125.127.99", 2, 2, 17]
>> @handle = ::Socket.new(addrinfo[4], ::Socket::SOCK_STREAM, 0)
=> #<Socket:0x417470d0>
>> sockaddr = ::Socket.sockaddr_in(addrinfo[1], addrinfo[3])
=> "\020\002\000PJ}\177c\000\000\000\000\000\000\000\000"
>> @handle.connect_nonblock(sockaddr)
Errno::EINPROGRESS: Operation now in progress - Operation now in progress
from (irb):18:in `connect_nonblock'
from (irb):18
>> sleep(5)
=> 5
>> t=Time.now; IO.select(nil, [ @handle ], nil, @timeout); puts Time.now-t
0.001
=> nil
>> @handle.connect_nonblock(sockaddr)
Errno::EISCONN: Socket is already connected - Socket is already connected
from (irb):21:in `connect_nonblock'
from (irb):21
>> IO.select(nil, [ @handle ], nil, @timeout)
=> [[], [#<Socket:0x417470d0>], []]
Issue Links
- relates to
-
JRUBY-5165
non-blocking IO does not function correctly: connect_nonblock followed by an IO.select
-
This was cloned from
JRUBY-5165, for which pull request 109 (https://github.com/jruby/jruby/pull/109) was merged in along with some other tweaks. I believe a more proper fix would be to have RubySocket track that it is in nonblocking mode and do a finishConnect before use if there's still a connection pending, rather than putting socket-specific logic in SelectBlob. This bug is to track that, hopefully to be fixed for 1.7.