The :mod:`socket` module also offers various network-related services:
+.. function:: close(fd)
+
+ Close a socket file descriptor. This is like :func:`os.close`, but for
+ sockets. On some platforms (most noticeable Windows) :func:`os.close`
+ does not work for socket file descriptors.
+
+ .. versionadded:: 3.7
+
.. function:: getaddrinfo(host, port, family=0, type=0, proto=0, flags=0)
Translate the *host*/*port* argument into a sequence of 5-tuples that contain
self.assertRaises(ValueError, fp.writable)
self.assertRaises(ValueError, fp.seekable)
+ def test_socket_close(self):
+ sock = socket.socket()
+ try:
+ sock.bind((HOST, 0))
+ socket.close(sock.fileno())
+ with self.assertRaises(OSError):
+ sock.listen(1)
+ finally:
+ with self.assertRaises(OSError):
+ # sock.close() fails with EBADF
+ sock.close()
+ with self.assertRaises(TypeError):
+ socket.close(None)
+ with self.assertRaises(OSError):
+ socket.close(-1)
+
def test_makefile_mode(self):
for mode in 'r', 'rb', 'rw', 'w', 'wb':
with self.subTest(mode=mode):
Py_RETURN_NONE;
}
-PyDoc_STRVAR(close_doc,
+PyDoc_STRVAR(sock_close_doc,
"close()\n\
\n\
Close the socket. It cannot be used after this call.");
{"bind", (PyCFunction)sock_bind, METH_O,
bind_doc},
{"close", (PyCFunction)sock_close, METH_NOARGS,
- close_doc},
+ sock_close_doc},
{"connect", (PyCFunction)sock_connect, METH_O,
connect_doc},
{"connect_ex", (PyCFunction)sock_connect_ex, METH_O,
\n\
Return the protocol number for the named protocol. (Rarely used.)");
+static PyObject *
+socket_close(PyObject *self, PyObject *fdobj)
+{
+ SOCKET_T fd;
+ int res;
+
+ fd = PyLong_AsSocket_t(fdobj);
+ if (fd == (SOCKET_T)(-1) && PyErr_Occurred())
+ return NULL;
+ Py_BEGIN_ALLOW_THREADS
+ res = SOCKETCLOSE(fd);
+ Py_END_ALLOW_THREADS
+ /* bpo-30319: The peer can already have closed the connection.
+ Python ignores ECONNRESET on close(). */
+ if (res < 0 && !CHECK_ERRNO(ECONNRESET)) {
+ return set_error();
+ }
+ Py_RETURN_NONE;
+}
+
+PyDoc_STRVAR(close_doc,
+"close(integer) -> None\n\
+\n\
+Close an integer socket file descriptor. This is like os.close(), but for\n\
+sockets; on some platforms os.close() won't work for socket file descriptors.");
#ifndef NO_DUP
/* dup() function for socket fds */
METH_VARARGS, getservbyport_doc},
{"getprotobyname", socket_getprotobyname,
METH_VARARGS, getprotobyname_doc},
+ {"close", socket_close,
+ METH_O, close_doc},
#ifndef NO_DUP
{"dup", socket_dup,
METH_O, dup_doc},