From: <am...@us...> - 2009-01-29 17:59:13
|
Revision: 6001 http://jython.svn.sourceforge.net/jython/?rev=6001&view=rev Author: amak Date: 2009-01-29 17:59:04 +0000 (Thu, 29 Jan 2009) Log Message: ----------- Re-arranging the socket shutdown methods. TCP client sockets can shutdown their input streams, but this is not appropriate for either TCP server sockets or UDP sockets, which don't have input and output streams. For these latter two types, the shutdown method should have the same effect as the close method, and thus the shutdown method is a no-op for these types. I have documented this difference between cpython and jython on the wiki. This should finally resolve bug 1121: listening socket shutdown expects the wrong kind of socket http://bugs.jython.org/issue1121 Modified Paths: -------------- trunk/jython/Lib/socket.py trunk/jython/Lib/test/test_socket.py Modified: trunk/jython/Lib/socket.py =================================================================== --- trunk/jython/Lib/socket.py 2009-01-29 17:41:00 UTC (rev 6000) +++ trunk/jython/Lib/socket.py 2009-01-29 17:59:04 UTC (rev 6001) @@ -248,22 +248,6 @@ def close(self): self.jsocket.close() - def shutdownInput(self): - try: - self.jsocket.shutdownInput() - except AttributeError, ax: - pass # Fail silently server sockets - except java.lang.Exception, jlx: - raise _map_exception(jlx) - - def shutdownOutput(self): - try: - self.jsocket.shutdownOutput() - except AttributeError, ax: - pass # Fail silently server sockets - except java.lang.Exception, jlx: - raise _map_exception(jlx) - def getchannel(self): return self.jchannel @@ -340,6 +324,12 @@ else: return self._do_write_nio(buf) + def shutdown(self, how): + if how in (SHUT_RD, SHUT_RDWR): + self.jsocket.shutdownInput() + if how in (SHUT_WR, SHUT_RDWR): + self.jsocket.shutdownOutput() + class _server_socket_impl(_nio_impl): options = { @@ -371,6 +361,13 @@ new_cli_sock = self.jsocket.accept() return _client_socket_impl(new_cli_sock) + def shutdown(self, how): + # This is no-op on java, for server sockets. + # What the user wants to achieve is achieved by calling close() on + # java/jython. But we can't call that here because that would then + # later cause the user explicit close() call to fail + pass + class _datagram_socket_impl(_nio_impl): options = { @@ -406,6 +403,13 @@ """ self.jchannel.disconnect() + def shutdown(self, how): + # This is no-op on java, for datagram sockets. + # What the user wants to achieve is achieved by calling close() on + # java/jython. But we can't call that here because that would then + # later cause the user explicit close() call to fail + pass + def _do_send_net(self, byte_array, socket_address, flags): # Need two separate implementations because the java.nio APIs do not support timeouts num_bytes = len(byte_array) @@ -689,6 +693,22 @@ except java.lang.Exception, jlx: raise _map_exception(jlx) + def shutdown(self, how): + assert how in (SHUT_RD, SHUT_WR, SHUT_RDWR) + if not self.sock_impl: + raise error(errno.ENOTCONN, "Transport endpoint is not connected") + try: + self.sock_impl.shutdown(how) + except java.lang.Exception, jlx: + raise _map_exception(jlx) + + def close(self): + try: + if self.sock_impl: + self.sock_impl.close() + except java.lang.Exception, jlx: + raise _map_exception(jlx) + def _config(self): assert self.mode in _permitted_modes if self.sock_impl: @@ -878,15 +898,6 @@ except java.lang.Exception, jlx: raise _map_exception(jlx) - def shutdown(self, how): - if not self.sock_impl: - raise error(errno.ENOTCONN, "Transport endpoint is not connected") - assert how in (SHUT_RD, SHUT_WR, SHUT_RDWR) - if how in (SHUT_RD, SHUT_RDWR): - self.sock_impl.shutdownInput() - if how in (SHUT_WR, SHUT_RDWR): - self.sock_impl.shutdownOutput() - def close(self): try: if self.istream: @@ -1015,13 +1026,6 @@ def __del__(self): self.close() - def close(self): - try: - if self.sock_impl: - self.sock_impl.close() - except java.lang.Exception, jlx: - raise _map_exception(jlx) - _socketmethods = ( 'bind', 'connect', 'connect_ex', 'fileno', 'listen', 'getpeername', 'getsockname', 'getsockopt', 'setsockopt', Modified: trunk/jython/Lib/test/test_socket.py =================================================================== --- trunk/jython/Lib/test/test_socket.py 2009-01-29 17:41:00 UTC (rev 6000) +++ trunk/jython/Lib/test/test_socket.py 2009-01-29 17:59:04 UTC (rev 6001) @@ -822,10 +822,20 @@ def setUp(self): self.sock = socket.socket(socket.AF_INET,socket.SOCK_DGRAM) + def testBindSpecific(self): + self.sock.bind( (self.HOST, self.PORT) ) # Use a specific port + actual_port = self.sock.getsockname()[1] + self.failUnless(actual_port == self.PORT, + "Binding to specific port number should have returned same number: %d != %d" % (actual_port, self.PORT)) + def testBindEphemeral(self): self.sock.bind( (self.HOST, 0) ) # let system choose a free port self.failUnless(self.sock.getsockname()[1] != 0, "Binding to port zero should have allocated an ephemeral port number") + def testShutdown(self): + self.sock.bind( (self.HOST, self.PORT) ) + self.sock.shutdown(socket.SHUT_RDWR) + def tearDown(self): self.sock.close() This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |