Graceful socket shutdown

J. Papa jpapa at websense.com
Fri Jun 14 22:06:53 CEST 2002


I am posting this because I just spend too many hours
debugging and I wanted to save someone else the angst.

According to MSDN the proper way to close a winsock connection
is to:

1. shutdown( SD_SEND );
2. call recv in a loop until it returns 0 or SOCKET_ERROR
3. close()


So in Python:

# This is not robust.
# s.close()

# This is, hideous, but correct for Win32
s.shutdown( 1 )
while 1:
	try:
		byte = s.recv( 1 )
		if "" == byte:
			break
	except:
		break
s.close()


The only time you will see this bug is if your recv buffer still has
data in it
when you try and close() the socket. This happened to me because my
client
was a wininet app. Wininet, for some mysterious reason, appends an
extra "\r\n" to POSTed data. (I swear I sniffed it, its true.) This
extra "\r\n" is not included in the Content-Length of the POST. Hence,
there were two extra bytes in the recv buffer when I went to close()
my socket. Instead of sending a FIN a RST is sent instead that gets
ugly.

Regards,
J. Papa



More information about the Python-list mailing list