Feature #10532
closed[PATCH] accept_nonblock supports "exception: false"
Description
This is analogous to functionality found in IO#read_nonblock and
IO#wait_nonblock.  Raising exceptions for common failures on
non-blocking servers is expensive and makes $DEBUG too noisy.
This also increases performance slightly, see patch for benchmarks.
I also intend to support this in the "openssl" extension as well as
supporting connect_nonblock if this is accepted.
Files
        
           Updated by normalperson (Eric Wong) almost 11 years ago
          Updated by normalperson (Eric Wong) almost 11 years ago
          
          
        
        
      
      normalperson@yhbt.net wrote:
I also intend to support this in the "openssl" extension as well as
accept_nonblock for openssl:
http://80x24.org/spew/m/f453956f3b04d2445e54d3141cc564a2529ce0f7.txt
Also pushed to the "more_nonblock" branch on git://80x24.org/ruby
        
           Updated by matz (Yukihiro Matsumoto) over 10 years ago
          Updated by matz (Yukihiro Matsumoto) over 10 years ago
          
          
        
        
      
      - Status changed from Open to Feedback
I like the basic idea. Once someone review the patch (Nobu, are you willing?), it's OK to merge.
Matz.
        
           Updated by nobu (Nobuyoshi Nakada) over 10 years ago
          Updated by nobu (Nobuyoshi Nakada) over 10 years ago
          
          
        
        
      
      Why only OpenSSL?
Doesn't Socket#accept_nonblock need it?
        
           Updated by nobu (Nobuyoshi Nakada) over 10 years ago
          Updated by nobu (Nobuyoshi Nakada) over 10 years ago
          
          
        
        
      
      Sorry, I've read the second link only.
Both look fine.
        
           Updated by Anonymous over 10 years ago
          Updated by Anonymous over 10 years ago
          
          
        
        
      
      - Status changed from Feedback to Closed
- % Done changed from 0 to 100
Applied in changeset r49948.
accept_nonblock supports "exception: false"
This is analogous to functionality found in IO#read_nonblock and
IO#wait_nonblock.  Raising exceptions for common failures on
non-blocking servers is expensive and makes $DEBUG too noisy.
Benchmark results:
user     system      total        real
default                         2.790000   0.870000   3.660000 (  3.671597)
exception: false                1.120000   0.800000   1.920000 (  1.922032)
exception: false (cached arg)   0.820000   0.770000   1.590000 (  1.589267)
--------------------- benchmark script ------------------------
require 'socket'
require 'benchmark'
require 'tmpdir'
nr = 1000000
Dir.mktmpdir('nb_bench') do |path|
  sock_path = "#{path}/test.sock"
  s = UNIXServer.new(sock_path)
  Benchmark.bmbm do |x|
    x.report("default") do
      nr.times do
        begin
          s.accept_nonblock
        rescue IO::WaitReadable
        end
      end
    end
    x.report("exception: false") do
      nr.times do
        begin
          s.accept_nonblock(exception: false)
        rescue IO::WaitReadable
          abort "should not raise"
        end
      end
    end
    x.report("exception: false (cached arg)") do
      arg = { exception: false }
      nr.times do
        begin
          s.accept_nonblock(arg)
        rescue IO::WaitReadable
          abort "should not raise"
        end
      end
    end
  end
end
- ext/socket/init.c (rsock_s_accept_nonblock):
 support exception: false
 [ruby-core:66385] [Feature #10532]
- ext/socket/init.c (rsock_init_socket_init): define new symbols
- ext/socket/rubysocket.h: adjust prototype
- ext/socket/socket.c (sock_accept_nonblock): support exception: false
- ext/openssl/ossl_ssl.c (ossl_ssl_accept_nonblock): ditto
- ext/socket/socket.c (Init_socket): adjust accept_nonblock definition
- ext/openssl/ossl_ssl.c (Init_ossl_ssl): ditto
- ext/socket/tcpserver.c (rsock_init_tcpserver): ditto
- ext/socket/unixserver.c (rsock_init_unixserver): ditto
- ext/socket/tcpserver.c (tcp_accept_nonblock): adjust
 rsock_s_accept_nonblock call
- ext/socket/unixserver.c (unix_accept_nonblock): ditto
- ext/openssl/ossl_ssl.c (ossl_start_ssl): support no_exception
- ext/openssl/ossl_ssl.c (ossl_ssl_connect): adjust ossl_start_ssl call
- ext/openssl/ossl_ssl.c (ossl_ssl_connect_nonblock): ditto
- ext/openssl/ossl_ssl.c (ossl_ssl_accept): ditto
- test/socket/test_nonblock.rb (test_accept_nonblock): test for
 "exception :false"
- test/socket/test_tcp.rb (test_accept_nonblock): new test
- test/socket/test_unix.rb (test_accept_nonblock): ditto
- test/openssl/test_pair.rb (test_accept_nonblock_no_exception): ditto