[前][次][番号順一覧][スレッド一覧]

ruby-changes:10911

From: akr <ko1@a...>
Date: Sun, 22 Feb 2009 00:58:05 +0900 (JST)
Subject: [ruby-changes:10911] Ruby:r22486 (trunk): * io.c (io_getpartial): error message describes what should be

akr	2009-02-22 00:57:52 +0900 (Sun, 22 Feb 2009)

  New Revision: 22486

  http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=22486

  Log:
    * io.c (io_getpartial): error message describes what should be
      waited after nonblocking error.
      (rb_io_write_nonblock): ditto.
    * ext/socket/init.c (s_recvfrom_nonblock): ditto.
      (s_accept_nonblock): ditto.
    
    * ext/socket/socket.c (sock_connect_nonblock): ditto.
    
    * ext/socket/ancdata.c (bsock_sendmsg_internal): ditto.
      (bsock_recvmsg_internal): ditto.

  Modified files:
    trunk/ChangeLog
    trunk/ext/socket/ancdata.c
    trunk/ext/socket/init.c
    trunk/ext/socket/socket.c
    trunk/io.c
    trunk/test/ruby/test_io.rb
    trunk/test/socket/test_nonblock.rb

Index: ChangeLog
===================================================================
--- ChangeLog	(revision 22485)
+++ ChangeLog	(revision 22486)
@@ -1,3 +1,17 @@
+Sun Feb 22 00:51:58 2009  Tanaka Akira  <akr@f...>
+
+	* io.c (io_getpartial): error message describes what should be
+	  waited after nonblocking error.
+	  (rb_io_write_nonblock): ditto.
+
+	* ext/socket/init.c (s_recvfrom_nonblock): ditto.
+	  (s_accept_nonblock): ditto.
+
+	* ext/socket/socket.c (sock_connect_nonblock): ditto.
+
+	* ext/socket/ancdata.c (bsock_sendmsg_internal): ditto.
+	  (bsock_recvmsg_internal): ditto.
+
 Sun Feb 22 00:31:42 2009  Tanaka Akira  <akr@f...>
 
 	* ext/socket/ancdata.c (bsock_recvmsg_internal): check recvmsg error
Index: io.c
===================================================================
--- io.c	(revision 22485)
+++ io.c	(revision 22486)
@@ -1754,6 +1754,8 @@
         if (n < 0) {
             if (!nonblock && rb_io_wait_readable(fptr->fd))
                 goto again;
+            if (nonblock && errno == EWOULDBLOCK)
+                rb_sys_fail("WANT_READ");
             rb_sys_fail_path(fptr->pathv);
         }
 	else if (n == 0) {
@@ -1952,7 +1954,11 @@
     rb_io_set_nonblock(fptr);
     n = write(fptr->fd, RSTRING_PTR(str), RSTRING_LEN(str));
 
-    if (n == -1) rb_sys_fail_path(fptr->pathv);
+    if (n == -1) {
+        if (errno == EWOULDBLOCK)
+            rb_sys_fail("WANT_WRITE");
+        rb_sys_fail_path(fptr->pathv);
+    }
 
     return LONG2FIX(n);
 }
Index: ext/socket/init.c
===================================================================
--- ext/socket/init.c	(revision 22485)
+++ ext/socket/init.c	(revision 22486)
@@ -192,6 +192,8 @@
     slen = recvfrom(fd, RSTRING_PTR(str), buflen, flags, (struct sockaddr*)&buf, &alen);
 
     if (slen < 0) {
+        if (errno == EWOULDBLOCK)
+            rb_sys_fail("recvfrom(2) WANT_READ");
 	rb_sys_fail("recvfrom(2)");
     }
     if (slen < RSTRING_LEN(str)) {
@@ -453,6 +455,8 @@
     rb_io_set_nonblock(fptr);
     fd2 = accept(fptr->fd, (struct sockaddr*)sockaddr, len);
     if (fd2 < 0) {
+        if (errno == EWOULDBLOCK || errno == ECONNABORTED || errno == EPROTO)
+            rb_sys_fail("accept(2) WANT_READ");
         rb_sys_fail("accept(2)");
     }
     make_fd_nonblock(fd2);
Index: ext/socket/socket.c
===================================================================
--- ext/socket/socket.c	(revision 22485)
+++ ext/socket/socket.c	(revision 22486)
@@ -311,6 +311,8 @@
     rb_io_set_nonblock(fptr);
     n = connect(fptr->fd, (struct sockaddr*)RSTRING_PTR(addr), RSTRING_LEN(addr));
     if (n < 0) {
+        if (errno == EINPROGRESS)
+            rb_sys_fail("connect(2) WANT_WRITE");
 	rb_sys_fail("connect(2)");
     }
 
Index: ext/socket/ancdata.c
===================================================================
--- ext/socket/ancdata.c	(revision 22485)
+++ ext/socket/ancdata.c	(revision 22486)
@@ -1030,8 +1030,11 @@
         goto retry;
     }
 
-    if (ss == -1)
+    if (ss == -1) {
+        if (nonblock && errno == EWOULDBLOCK)
+            rb_sys_fail("sendmsg(2) WANT_WRITE");
 	rb_sys_fail("sendmsg(2)");
+    }
 
     return SSIZET2NUM(ss);
 }
@@ -1290,8 +1293,11 @@
         goto retry;
     }
 
-    if (ss == -1)
+    if (ss == -1) {
+        if (nonblock && errno == EWOULDBLOCK)
+            rb_sys_fail("recvmsg(2) WANT_READ");
 	rb_sys_fail("recvmsg(2)");
+    }
 
     if (grow_buffer) {
 	int grown = 0;
Index: test/ruby/test_io.rb
===================================================================
--- test/ruby/test_io.rb	(revision 22485)
+++ test/ruby/test_io.rb	(revision 22486)
@@ -857,6 +857,30 @@
     end)
   end
 
+  def test_read_nonblock_error
+    return if !have_nonblock?
+    with_pipe {|r, w|
+      begin
+        r.read_nonblock 4096
+      rescue Errno::EWOULDBLOCK
+        assert_match(/WANT_READ/, $!.message)
+      end
+    }
+  end
+
+  def test_write_nonblock_error
+    return if !have_nonblock?
+    with_pipe {|r, w|
+      begin
+        loop {
+          w.write_nonblock "a"*100000
+        }
+      rescue Errno::EWOULDBLOCK
+        assert_match(/WANT_WRITE/, $!.message)
+      end
+    }
+  end
+
   def test_gets
     pipe(proc do |w|
       w.write "foobarbaz"
Index: test/socket/test_nonblock.rb
===================================================================
--- test/socket/test_nonblock.rb	(revision 22485)
+++ test/socket/test_nonblock.rb	(revision 22486)
@@ -124,9 +124,18 @@
     af, port, host, addr = serv.addr
     c = TCPSocket.new(addr, port)
     s = serv.accept
-    return c, s
+    if block_given?
+      begin
+        yield c, s
+      ensure
+        c.close if !c.closed?
+        s.close if !s.closed?
+      end
+    else
+      return c, s
+    end
   ensure
-    serv.close if serv
+    serv.close if serv && !serv.closed?
   end
 
   def test_tcp_recv_nonblock
@@ -181,4 +190,65 @@
   end
 =end
 
+  def test_sendmsg_nonblock_error
+    tcp_pair {|c, s|
+      begin
+        loop {
+          c.sendmsg_nonblock("a" * 100000)
+        }
+      rescue Errno::EWOULDBLOCK
+        assert_match(/WANT_WRITE/, $!.message)
+      end
+    }
+  end
+
+  def test_recvmsg_nonblock_error
+    tcp_pair {|c, s|
+      begin
+        c.recvmsg_nonblock(4096)
+      rescue Errno::EWOULDBLOCK
+        assert_match(/WANT_READ/, $!.message)
+      end
+    }
+  end
+
+  def test_recv_nonblock_error
+    tcp_pair {|c, s|
+      begin
+        c.recv_nonblock(4096)
+      rescue Errno::EWOULDBLOCK
+        assert_match(/WANT_READ/, $!.message)
+      end
+    }
+  end
+
+  def test_connect_nonblock_error
+    serv = TCPServer.new("127.0.0.1", 0)
+    af, port, host, addr = serv.addr
+    c = Socket.new(:INET, :STREAM)
+    begin
+      c.connect_nonblock(Socket.sockaddr_in(port, "127.0.0.1"))
+    rescue Errno::EINPROGRESS
+      assert_match(/WANT_WRITE/, $!.message)
+    end
+  ensure
+    serv.close if serv && !serv.closed?
+    c.close if c && !c.closed?
+  end
+
+  def test_accept_nonblock_error
+    serv = Socket.new(:INET, :STREAM)
+    serv.bind(Socket.sockaddr_in(0, "127.0.0.1"))
+    serv.listen(5)
+    port = serv.local_address.ip_port
+    begin
+      s, _ = serv.accept_nonblock
+    rescue Errno::EWOULDBLOCK, Errno::ECONNABORTED, Errno::EPROTO
+      assert_match(/WANT_READ/, $!.message)
+    end
+  ensure
+    serv.close if serv && !serv.closed?
+    s.close if s && !s.closed?
+  end
+
 end if defined?(Socket)

--
ML: ruby-changes@q...
Info: http://www.atdot.net/~ko1/quickml/

[前][次][番号順一覧][スレッド一覧]