summaryrefslogtreecommitdiffstats
path: root/contrib/tools/python3/Modules/socketmodule.c
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/tools/python3/Modules/socketmodule.c')
-rw-r--r--contrib/tools/python3/Modules/socketmodule.c463
1 files changed, 266 insertions, 197 deletions
diff --git a/contrib/tools/python3/Modules/socketmodule.c b/contrib/tools/python3/Modules/socketmodule.c
index 7f2ebba9884..becdf9af718 100644
--- a/contrib/tools/python3/Modules/socketmodule.c
+++ b/contrib/tools/python3/Modules/socketmodule.c
@@ -105,14 +105,14 @@ Local naming conventions:
# pragma weak inet_aton
#endif
-#define PY_SSIZE_T_CLEAN
#include "Python.h"
+#include "pycore_capsule.h" // _PyCapsule_SetTraverse()
#include "pycore_fileutils.h" // _Py_set_inheritable()
#include "pycore_moduleobject.h" // _PyModule_GetState
-#include "structmember.h" // PyMemberDef
+#include "pycore_time.h" // _PyTime_AsMilliseconds()
#ifdef _Py_MEMORY_SANITIZER
-# include <sanitizer/msan_interface.h>
+# include <sanitizer/msan_interface.h>
#endif
/* Socket object documentation */
@@ -149,7 +149,7 @@ listen([n]) -- start listening for incoming connections\n\
recv(buflen[, flags]) -- receive data\n\
recv_into(buffer[, nbytes[, flags]]) -- receive data (into a buffer)\n\
recvfrom(buflen[, flags]) -- receive data and sender\'s address\n\
-recvfrom_into(buffer[, nbytes, [, flags])\n\
+recvfrom_into(buffer[, nbytes, [, flags]])\n\
-- receive data and sender\'s address (into a buffer)\n\
sendall(data[, flags]) -- send all data\n\
send(data[, flags]) -- send data, may not send all of it\n\
@@ -264,7 +264,7 @@ shutdown(how) -- shut down traffic in one or both directions\n\
#ifdef HAVE_NETDB_H
# include <netdb.h>
#endif
-# include <unistd.h>
+#include <unistd.h> // close()
/* Headers needed for inet_ntoa() and inet_addr() */
# include <arpa/inet.h>
@@ -393,16 +393,10 @@ remove_unusable_flags(PyObject *m)
break;
}
else {
- PyObject *flag_name = PyUnicode_FromString(win_runtime_flags[i].flag_name);
- if (flag_name == NULL) {
+ if (PyDict_PopString(dict, win_runtime_flags[i].flag_name,
+ NULL) < 0) {
return -1;
}
- PyObject *v = _PyDict_Pop(dict, flag_name, Py_None);
- Py_DECREF(flag_name);
- if (v == NULL) {
- return -1;
- }
- Py_DECREF(v);
}
}
return 0;
@@ -479,37 +473,42 @@ remove_unusable_flags(PyObject *m)
# define SOCKETCLOSE close
#endif
-#if (defined(HAVE_BLUETOOTH_H) || defined(HAVE_BLUETOOTH_BLUETOOTH_H)) && !defined(__NetBSD__) && !defined(__DragonFly__)
-#define USE_BLUETOOTH 1
-#if defined(__FreeBSD__)
-#define BTPROTO_L2CAP BLUETOOTH_PROTO_L2CAP
-#define BTPROTO_RFCOMM BLUETOOTH_PROTO_RFCOMM
-#define BTPROTO_HCI BLUETOOTH_PROTO_HCI
-#define SOL_HCI SOL_HCI_RAW
-#define HCI_FILTER SO_HCI_RAW_FILTER
-#define sockaddr_l2 sockaddr_l2cap
-#define sockaddr_rc sockaddr_rfcomm
-#define hci_dev hci_node
-#define _BT_L2_MEMB(sa, memb) ((sa)->l2cap_##memb)
-#define _BT_RC_MEMB(sa, memb) ((sa)->rfcomm_##memb)
-#define _BT_HCI_MEMB(sa, memb) ((sa)->hci_##memb)
-#elif defined(__NetBSD__) || defined(__DragonFly__)
-#define sockaddr_l2 sockaddr_bt
-#define sockaddr_rc sockaddr_bt
-#define sockaddr_hci sockaddr_bt
-#define sockaddr_sco sockaddr_bt
-#define SOL_HCI BTPROTO_HCI
-#define HCI_DATA_DIR SO_HCI_DIRECTION
-#define _BT_L2_MEMB(sa, memb) ((sa)->bt_##memb)
-#define _BT_RC_MEMB(sa, memb) ((sa)->bt_##memb)
-#define _BT_HCI_MEMB(sa, memb) ((sa)->bt_##memb)
-#define _BT_SCO_MEMB(sa, memb) ((sa)->bt_##memb)
-#else
-#define _BT_L2_MEMB(sa, memb) ((sa)->l2_##memb)
-#define _BT_RC_MEMB(sa, memb) ((sa)->rc_##memb)
-#define _BT_HCI_MEMB(sa, memb) ((sa)->hci_##memb)
-#define _BT_SCO_MEMB(sa, memb) ((sa)->sco_##memb)
-#endif
+#if defined(HAVE_BLUETOOTH_H) || defined(HAVE_BLUETOOTH_BLUETOOTH_H)
+# define USE_BLUETOOTH 1
+# if defined(HAVE_BLUETOOTH_BLUETOOTH_H) // Linux
+# define _BT_L2_MEMB(sa, memb) ((sa)->l2_##memb)
+# define _BT_RC_MEMB(sa, memb) ((sa)->rc_##memb)
+# define _BT_HCI_MEMB(sa, memb) ((sa)->hci_##memb)
+# define _BT_SCO_MEMB(sa, memb) ((sa)->sco_##memb)
+# elif defined(__FreeBSD__)
+# define BTPROTO_L2CAP BLUETOOTH_PROTO_L2CAP
+# define BTPROTO_RFCOMM BLUETOOTH_PROTO_RFCOMM
+# define BTPROTO_HCI BLUETOOTH_PROTO_HCI
+# define SOL_HCI SOL_HCI_RAW
+# define HCI_FILTER SO_HCI_RAW_FILTER
+# define sockaddr_l2 sockaddr_l2cap
+# define sockaddr_rc sockaddr_rfcomm
+# define hci_dev hci_node
+# define _BT_L2_MEMB(sa, memb) ((sa)->l2cap_##memb)
+# define _BT_RC_MEMB(sa, memb) ((sa)->rfcomm_##memb)
+# define _BT_HCI_MEMB(sa, memb) ((sa)->hci_##memb)
+# else // NetBSD, DragonFly BSD
+# define sockaddr_l2 sockaddr_bt
+# define sockaddr_rc sockaddr_bt
+# define sockaddr_hci sockaddr_bt
+# define sockaddr_sco sockaddr_bt
+# define bt_l2 bt
+# define bt_rc bt
+# define bt_sco bt
+# define bt_hci bt
+# define bt_cid bt_channel
+# define SOL_HCI BTPROTO_HCI
+# define HCI_DATA_DIR SO_HCI_DIRECTION
+# define _BT_L2_MEMB(sa, memb) ((sa)->bt_##memb)
+# define _BT_RC_MEMB(sa, memb) ((sa)->bt_##memb)
+# define _BT_HCI_MEMB(sa, memb) ((sa)->bt_##memb)
+# define _BT_SCO_MEMB(sa, memb) ((sa)->bt_##memb)
+# endif
#endif
#ifdef MS_WINDOWS_DESKTOP
@@ -554,7 +553,7 @@ typedef struct _socket_state {
PyObject *socket_gaierror;
/* Default timeout for new sockets */
- _PyTime_t defaulttimeout;
+ PyTime_t defaulttimeout;
#if defined(HAVE_ACCEPT) || defined(HAVE_ACCEPT4)
#if defined(HAVE_ACCEPT4) && defined(SOCK_CLOEXEC)
@@ -779,13 +778,13 @@ internal_setblocking(PySocketSockObject *s, int block)
}
static int
-internal_select(PySocketSockObject *s, int writing, _PyTime_t interval,
+internal_select(PySocketSockObject *s, int writing, PyTime_t interval,
int connect)
{
int n;
#ifdef HAVE_POLL
struct pollfd pollfd;
- _PyTime_t ms;
+ PyTime_t ms;
#else
fd_set fds, efds;
struct timeval tv, *tvp;
@@ -898,10 +897,10 @@ sock_call_ex(PySocketSockObject *s,
void *data,
int connect,
int *err,
- _PyTime_t timeout)
+ PyTime_t timeout)
{
int has_timeout = (timeout > 0);
- _PyTime_t deadline = 0;
+ PyTime_t deadline = 0;
int deadline_initialized = 0;
int res;
@@ -915,7 +914,7 @@ sock_call_ex(PySocketSockObject *s,
runs asynchronously. */
if (has_timeout || connect) {
if (has_timeout) {
- _PyTime_t interval;
+ PyTime_t interval;
if (deadline_initialized) {
/* recompute the timeout */
@@ -1063,8 +1062,8 @@ init_sockobject(socket_state *state, PySocketSockObject *s,
else
#endif
{
- s->sock_timeout = state->defaulttimeout;
- if (state->defaulttimeout >= 0) {
+ s->sock_timeout = _Py_atomic_load_int64_relaxed(&state->defaulttimeout);
+ if (s->sock_timeout >= 0) {
if (internal_setblocking(s, 0) == -1) {
return -1;
}
@@ -1489,13 +1488,17 @@ makesockaddr(SOCKET_T sockfd, struct sockaddr *addr, size_t addrlen, int proto)
case BTPROTO_HCI:
{
struct sockaddr_hci *a = (struct sockaddr_hci *) addr;
-#if defined(__NetBSD__) || defined(__DragonFly__)
- return makebdaddr(&_BT_HCI_MEMB(a, bdaddr));
-#else /* __NetBSD__ || __DragonFly__ */
+#if defined(HAVE_BLUETOOTH_BLUETOOTH_H)
PyObject *ret = NULL;
ret = Py_BuildValue("i", _BT_HCI_MEMB(a, dev));
return ret;
-#endif /* !(__NetBSD__ || __DragonFly__) */
+#elif defined(__FreeBSD__)
+ const char *node = _BT_HCI_MEMB(a, node);
+ size_t len = strnlen(node, sizeof(_BT_HCI_MEMB(a, node)));
+ return PyUnicode_FromStringAndSize(node, (Py_ssize_t)len);
+#else
+ return makebdaddr(&_BT_HCI_MEMB(a, bdaddr));
+#endif
}
#if !defined(__FreeBSD__)
@@ -1720,9 +1723,6 @@ idna_converter(PyObject *obj, struct maybe_idna *data)
len = PyByteArray_Size(obj);
}
else if (PyUnicode_Check(obj)) {
- if (PyUnicode_READY(obj) == -1) {
- return 0;
- }
if (PyUnicode_IS_COMPACT_ASCII(obj)) {
data->buf = PyUnicode_DATA(obj);
len = PyUnicode_GET_LENGTH(obj);
@@ -1784,6 +1784,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
assert(path.len >= 0);
struct sockaddr_un* addr = &addrbuf->un;
+ memset(addr, 0, sizeof(struct sockaddr_un));
#ifdef __linux__
if (path.len == 0 || *(const char *)path.buf == 0) {
/* Linux abstract namespace extension:
@@ -1827,6 +1828,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
{
int pid, groups;
struct sockaddr_nl* addr = &addrbuf->nl;
+ memset(addr, 0, sizeof(struct sockaddr_nl));
if (!PyTuple_Check(args)) {
PyErr_Format(
PyExc_TypeError,
@@ -1854,6 +1856,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
{
unsigned int node, port;
struct sockaddr_qrtr* addr = &addrbuf->sq;
+ memset(addr, 0, sizeof(struct sockaddr_qrtr));
if (!PyTuple_Check(args)) {
PyErr_Format(
PyExc_TypeError,
@@ -1931,6 +1934,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
return 0;
}
struct sockaddr_in* addr = &addrbuf->in;
+ memset(addr, 0, sizeof(struct sockaddr_in));
result = setipaddr(s->state, host.buf, (struct sockaddr *)addr,
sizeof(*addr), AF_INET);
idna_cleanup(&host);
@@ -1976,6 +1980,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
return 0;
}
struct sockaddr_in6* addr = &addrbuf->in6;
+ memset(addr, 0, sizeof(struct sockaddr_in6));
result = setipaddr(s->state, host.buf, (struct sockaddr *)addr,
sizeof(*addr), AF_INET6);
idna_cleanup(&host);
@@ -2014,12 +2019,14 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
struct sockaddr_l2 *addr = &addrbuf->bt_l2;
memset(addr, 0, sizeof(struct sockaddr_l2));
_BT_L2_MEMB(addr, family) = AF_BLUETOOTH;
- if (!PyArg_ParseTuple(args, "si", &straddr,
- &_BT_L2_MEMB(addr, psm))) {
+ unsigned short psm;
+ if (!PyArg_ParseTuple(args, "sH", &straddr, &psm)) {
PyErr_Format(PyExc_OSError,
"%s(): wrong format", caller);
return 0;
}
+ _BT_L2_MEMB(addr, psm) = psm;
+
if (setbdaddr(straddr, &_BT_L2_MEMB(addr, bdaddr)) < 0)
return 0;
@@ -2031,13 +2038,23 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
{
const char *straddr;
struct sockaddr_rc *addr = &addrbuf->bt_rc;
+ memset(addr, 0, sizeof(struct sockaddr_rc));
_BT_RC_MEMB(addr, family) = AF_BLUETOOTH;
- if (!PyArg_ParseTuple(args, "si", &straddr,
- &_BT_RC_MEMB(addr, channel))) {
- PyErr_Format(PyExc_OSError,
- "%s(): wrong format", caller);
+#ifdef MS_WINDOWS
+ unsigned long channel;
+# define FORMAT_CHANNEL "k"
+#else
+ unsigned char channel;
+# define FORMAT_CHANNEL "B"
+#endif
+ if (!PyArg_ParseTuple(args, "s" FORMAT_CHANNEL,
+ &straddr, &channel)) {
+ PyErr_Format(PyExc_OSError, "%s(): wrong format", caller);
return 0;
}
+#undef FORMAT_CHANNEL
+ _BT_RC_MEMB(addr, channel) = channel;
+
if (setbdaddr(straddr, &_BT_RC_MEMB(addr, bdaddr)) < 0)
return 0;
@@ -2048,25 +2065,36 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
case BTPROTO_HCI:
{
struct sockaddr_hci *addr = &addrbuf->bt_hci;
-#if defined(__NetBSD__) || defined(__DragonFly__)
- const char *straddr;
+ memset(addr, 0, sizeof(struct sockaddr_hci));
_BT_HCI_MEMB(addr, family) = AF_BLUETOOTH;
- if (!PyBytes_Check(args)) {
+#if defined(HAVE_BLUETOOTH_BLUETOOTH_H)
+ unsigned short dev = _BT_HCI_MEMB(addr, dev);
+ if (!PyArg_ParseTuple(args, "H", &dev)) {
+ PyErr_Format(PyExc_OSError,
+ "%s(): wrong format", caller);
+ return 0;
+ }
+ _BT_HCI_MEMB(addr, dev) = dev;
+#else
+ const char *straddr;
+ if (!PyArg_Parse(args, "s", &straddr)) {
PyErr_Format(PyExc_OSError, "%s: "
"wrong format", caller);
return 0;
}
- straddr = PyBytes_AS_STRING(args);
- if (setbdaddr(straddr, &_BT_HCI_MEMB(addr, bdaddr)) < 0)
- return 0;
-#else /* __NetBSD__ || __DragonFly__ */
- _BT_HCI_MEMB(addr, family) = AF_BLUETOOTH;
- if (!PyArg_ParseTuple(args, "i", &_BT_HCI_MEMB(addr, dev))) {
- PyErr_Format(PyExc_OSError,
- "%s(): wrong format", caller);
+# if defined(__FreeBSD__)
+ if (strlen(straddr) > sizeof(_BT_HCI_MEMB(addr, node))) {
+ PyErr_Format(PyExc_ValueError, "%s: "
+ "node too long", caller);
return 0;
}
-#endif /* !(__NetBSD__ || __DragonFly__) */
+ strncpy(_BT_HCI_MEMB(addr, node), straddr,
+ sizeof(_BT_HCI_MEMB(addr, node)));
+# else
+ if (setbdaddr(straddr, &_BT_HCI_MEMB(addr, bdaddr)) < 0)
+ return 0;
+# endif
+#endif
*len_ret = sizeof *addr;
return 1;
}
@@ -2076,13 +2104,24 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
const char *straddr;
struct sockaddr_sco *addr = &addrbuf->bt_sco;
+ memset(addr, 0, sizeof(struct sockaddr_sco));
_BT_SCO_MEMB(addr, family) = AF_BLUETOOTH;
- if (!PyBytes_Check(args)) {
+
+ if (PyBytes_Check(args)) {
+ if (!PyArg_Parse(args, "y", &straddr)) {
+ return 0;
+ }
+ }
+ else if (PyUnicode_Check(args)) {
+ if (!PyArg_Parse(args, "s", &straddr)) {
+ return 0;
+ }
+ }
+ else {
PyErr_Format(PyExc_OSError,
"%s(): wrong format", caller);
return 0;
}
- straddr = PyBytes_AS_STRING(args);
if (setbdaddr(straddr, &_BT_SCO_MEMB(addr, bdaddr)) < 0)
return 0;
@@ -2153,6 +2192,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
return 0;
}
struct sockaddr_ll* addr = &addrbuf->ll;
+ memset(addr, 0, sizeof(struct sockaddr_ll));
addr->sll_family = AF_PACKET;
addr->sll_protocol = htons((short)protoNumber);
addr->sll_ifindex = ifr.ifr_ifindex;
@@ -2237,6 +2277,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
struct ifreq ifr;
Py_ssize_t len;
struct sockaddr_can *addr = &addrbuf->can;
+ memset(addr, 0, sizeof(struct sockaddr_can));
if (!PyTuple_Check(args)) {
PyErr_Format(PyExc_TypeError,
@@ -2289,6 +2330,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
unsigned long int rx_id, tx_id;
struct sockaddr_can *addr = &addrbuf->can;
+ memset(addr, 0, sizeof(struct sockaddr_can));
if (!PyArg_ParseTuple(args, "O&kk", PyUnicode_FSConverter,
&interfaceName,
@@ -2336,6 +2378,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
uint8_t j1939_addr;
struct sockaddr_can *addr = &addrbuf->can;
+ memset(addr, 0, sizeof(struct sockaddr_can));
if (!PyArg_ParseTuple(args, "O&KIB", PyUnicode_FSConverter,
&interfaceName,
@@ -2388,6 +2431,7 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
case SYSPROTO_CONTROL:
{
struct sockaddr_ctl *addr = &addrbuf->ctl;
+ memset(addr, 0, sizeof(struct sockaddr_ctl));
addr->sc_family = AF_SYSTEM;
addr->ss_sysaddr = AF_SYS_CONTROL;
@@ -2605,6 +2649,11 @@ getsockaddrlen(PySocketSockObject *s, socklen_t *len_ret)
/* RDS sockets use sockaddr_in: fall-through */
#endif /* AF_RDS */
+#ifdef AF_DIVERT
+ case AF_DIVERT:
+ /* FreeBSD divert(4) sockets use sockaddr_in: fall-through */
+#endif /* AF_DIVERT */
+
case AF_INET:
{
*len_ret = sizeof (struct sockaddr_in);
@@ -2637,12 +2686,12 @@ getsockaddrlen(PySocketSockObject *s, socklen_t *len_ret)
case BTPROTO_HCI:
*len_ret = sizeof (struct sockaddr_hci);
return 1;
-#if !defined(__FreeBSD__)
+#endif /* BTPROTO_HCI */
+#ifdef BTPROTO_SCO
case BTPROTO_SCO:
*len_ret = sizeof (struct sockaddr_sco);
return 1;
-#endif /* !__FreeBSD__ */
-#endif /* BTPROTO_HCI */
+#endif /* BTPROTO_SCO */
default:
PyErr_SetString(PyExc_OSError, "getsockaddrlen: "
"unknown BT protocol");
@@ -3024,13 +3073,13 @@ Returns True if socket is in blocking mode, or False if it\n\
is in non-blocking mode.");
static int
-socket_parse_timeout(_PyTime_t *timeout, PyObject *timeout_obj)
+socket_parse_timeout(PyTime_t *timeout, PyObject *timeout_obj)
{
#ifdef MS_WINDOWS
struct timeval tv;
#endif
#ifndef HAVE_POLL
- _PyTime_t ms;
+ PyTime_t ms;
#endif
int overflow = 0;
@@ -3073,7 +3122,7 @@ socket_parse_timeout(_PyTime_t *timeout, PyObject *timeout_obj)
static PyObject *
sock_settimeout(PySocketSockObject *s, PyObject *arg)
{
- _PyTime_t timeout;
+ PyTime_t timeout;
if (socket_parse_timeout(&timeout, arg) < 0)
return NULL;
@@ -3125,7 +3174,7 @@ sock_gettimeout(PySocketSockObject *s, PyObject *Py_UNUSED(ignored))
Py_RETURN_NONE;
}
else {
- double seconds = _PyTime_AsSecondsDouble(s->sock_timeout);
+ double seconds = PyTime_AsSecondsDouble(s->sock_timeout);
return PyFloat_FromDouble(seconds);
}
}
@@ -4395,8 +4444,8 @@ sock_sendall(PySocketSockObject *s, PyObject *args)
Py_buffer pbuf;
struct sock_send ctx;
int has_timeout = (s->sock_timeout > 0);
- _PyTime_t timeout = s->sock_timeout;
- _PyTime_t deadline = 0;
+ PyTime_t timeout = s->sock_timeout;
+ PyTime_t deadline = 0;
int deadline_initialized = 0;
PyObject *res = NULL;
@@ -4533,6 +4582,7 @@ sock_sendto(PySocketSockObject *s, PyObject *args)
}
if (PySys_Audit("socket.sendto", "OO", s, addro) < 0) {
+ PyBuffer_Release(&pbuf);
return NULL;
}
@@ -4688,11 +4738,13 @@ sock_sendmsg(PySocketSockObject *s, PyObject *args)
if (cmsg_arg == NULL)
ncmsgs = 0;
else {
- if ((cmsg_fast = PySequence_Fast(cmsg_arg,
- "sendmsg() argument 2 must be an "
- "iterable")) == NULL)
+ cmsg_fast = PySequence_Tuple(cmsg_arg);
+ if (cmsg_fast == NULL) {
+ PyErr_SetString(PyExc_TypeError,
+ "sendmsg() argument 2 must be an iterable");
goto finally;
- ncmsgs = PySequence_Fast_GET_SIZE(cmsg_fast);
+ }
+ ncmsgs = PyTuple_GET_SIZE(cmsg_fast);
}
#ifndef CMSG_SPACE
@@ -4712,8 +4764,9 @@ sock_sendmsg(PySocketSockObject *s, PyObject *args)
controllen = controllen_last = 0;
while (ncmsgbufs < ncmsgs) {
size_t bufsize, space;
+ PyObject *item = PyTuple_GET_ITEM(cmsg_fast, ncmsgbufs);
- if (!PyArg_Parse(PySequence_Fast_GET_ITEM(cmsg_fast, ncmsgbufs),
+ if (!PyArg_Parse(item,
"(iiy*):[sendmsg() ancillary data items]",
&cmsgs[ncmsgbufs].level,
&cmsgs[ncmsgbufs].type,
@@ -4885,17 +4938,17 @@ sock_sendmsg_afalg(PySocketSockObject *self, PyObject *args, PyObject *kwds)
/* op is a required, keyword-only argument >= 0 */
if (opobj != NULL) {
- op = _PyLong_AsInt(opobj);
+ op = PyLong_AsInt(opobj);
}
if (op < 0) {
- /* override exception from _PyLong_AsInt() */
+ /* override exception from PyLong_AsInt() */
PyErr_SetString(PyExc_TypeError,
"Invalid or missing argument 'op'");
goto finally;
}
/* assoclen is optional but must be >= 0 */
if (assoclenobj != NULL) {
- assoclen = _PyLong_AsInt(assoclenobj);
+ assoclen = PyLong_AsInt(assoclenobj);
if (assoclen == -1 && PyErr_Occurred()) {
goto finally;
}
@@ -5013,7 +5066,7 @@ sock_shutdown(PySocketSockObject *s, PyObject *arg)
int how;
int res;
- how = _PyLong_AsInt(arg);
+ how = PyLong_AsInt(arg);
if (how == -1 && PyErr_Occurred())
return NULL;
Py_BEGIN_ALLOW_THREADS
@@ -5212,9 +5265,9 @@ static PyMethodDef sock_methods[] = {
/* SockObject members */
static PyMemberDef sock_memberlist[] = {
- {"family", T_INT, offsetof(PySocketSockObject, sock_family), READONLY, "the socket family"},
- {"type", T_INT, offsetof(PySocketSockObject, sock_type), READONLY, "the socket type"},
- {"proto", T_INT, offsetof(PySocketSockObject, sock_proto), READONLY, "the socket protocol"},
+ {"family", Py_T_INT, offsetof(PySocketSockObject, sock_family), Py_READONLY, "the socket family"},
+ {"type", Py_T_INT, offsetof(PySocketSockObject, sock_type), Py_READONLY, "the socket type"},
+ {"proto", Py_T_INT, offsetof(PySocketSockObject, sock_proto), Py_READONLY, "the socket protocol"},
{0},
};
@@ -6339,14 +6392,18 @@ AF_UNIX if defined on the platform; otherwise, the default is AF_INET.");
#endif /* HAVE_SOCKETPAIR */
+/*[clinic input]
+_socket.socket.ntohs
+ x: int
+ /
+
+Convert a 16-bit unsigned integer from network to host byte order.
+[clinic start generated code]*/
+
static PyObject *
-socket_ntohs(PyObject *self, PyObject *args)
+_socket_socket_ntohs_impl(PySocketSockObject *self, int x)
+/*[clinic end generated code: output=a828a61a9fb205b2 input=9a79cb3a71652147]*/
{
- int x;
-
- if (!PyArg_ParseTuple(args, "i:ntohs", &x)) {
- return NULL;
- }
if (x < 0) {
PyErr_SetString(PyExc_OverflowError,
"ntohs: can't convert negative Python int to C "
@@ -6362,11 +6419,6 @@ socket_ntohs(PyObject *self, PyObject *args)
return PyLong_FromUnsignedLong(ntohs((unsigned short)x));
}
-PyDoc_STRVAR(ntohs_doc,
-"ntohs(integer) -> integer\n\
-\n\
-Convert a 16-bit unsigned integer from network to host byte order.");
-
static PyObject *
socket_ntohl(PyObject *self, PyObject *arg)
@@ -6402,14 +6454,18 @@ PyDoc_STRVAR(ntohl_doc,
Convert a 32-bit integer from network to host byte order.");
+/*[clinic input]
+_socket.socket.htons
+ x: int
+ /
+
+Convert a 16-bit unsigned integer from host to network byte order.
+[clinic start generated code]*/
+
static PyObject *
-socket_htons(PyObject *self, PyObject *args)
+_socket_socket_htons_impl(PySocketSockObject *self, int x)
+/*[clinic end generated code: output=d785ee692312da47 input=053252d8416f4337]*/
{
- int x;
-
- if (!PyArg_ParseTuple(args, "i:htons", &x)) {
- return NULL;
- }
if (x < 0) {
PyErr_SetString(PyExc_OverflowError,
"htons: can't convert negative Python int to C "
@@ -6425,11 +6481,6 @@ socket_htons(PyObject *self, PyObject *args)
return PyLong_FromUnsignedLong(htons((unsigned short)x));
}
-PyDoc_STRVAR(htons_doc,
-"htons(integer) -> integer\n\
-\n\
-Convert a 16-bit unsigned integer from host to network byte order.");
-
static PyObject *
socket_htonl(PyObject *self, PyObject *arg)
@@ -6466,14 +6517,17 @@ Convert a 32-bit integer from host to network byte order.");
/* socket.inet_aton() and socket.inet_ntoa() functions. */
-PyDoc_STRVAR(inet_aton_doc,
-"inet_aton(string) -> bytes giving packed 32-bit IP representation\n\
-\n\
-Convert an IP address in string format (123.45.67.89) to the 32-bit packed\n\
-binary format used in low-level network functions.");
+/*[clinic input]
+_socket.socket.inet_aton
+ ip_addr: str
+ /
-static PyObject*
-socket_inet_aton(PyObject *self, PyObject *args)
+Convert an IP address in string format (123.45.67.89) to the 32-bit packed binary format used in low-level network functions.
+[clinic start generated code]*/
+
+static PyObject *
+_socket_socket_inet_aton_impl(PySocketSockObject *self, const char *ip_addr)
+/*[clinic end generated code: output=5bfe11a255423d8c input=a120e20cb52b9488]*/
{
#ifdef HAVE_INET_ATON
struct in_addr buf;
@@ -6486,11 +6540,6 @@ socket_inet_aton(PyObject *self, PyObject *args)
/* Have to use inet_addr() instead */
unsigned int packed_addr;
#endif
- const char *ip_addr;
-
- if (!PyArg_ParseTuple(args, "s:inet_aton", &ip_addr))
- return NULL;
-
#ifdef HAVE_INET_ATON
@@ -6539,30 +6588,29 @@ socket_inet_aton(PyObject *self, PyObject *args)
}
#ifdef HAVE_INET_NTOA
-PyDoc_STRVAR(inet_ntoa_doc,
-"inet_ntoa(packed_ip) -> ip_address_string\n\
-\n\
-Convert an IP address from 32-bit packed binary format to string format");
+/*[clinic input]
+_socket.socket.inet_ntoa
+ packed_ip: Py_buffer
+ /
-static PyObject*
-socket_inet_ntoa(PyObject *self, PyObject *args)
+Convert an IP address from 32-bit packed binary format to string format.
+[clinic start generated code]*/
+
+static PyObject *
+_socket_socket_inet_ntoa_impl(PySocketSockObject *self, Py_buffer *packed_ip)
+/*[clinic end generated code: output=b671880a3f62461b input=95c2c4a1b2ee957c]*/
{
- Py_buffer packed_ip;
struct in_addr packed_addr;
- if (!PyArg_ParseTuple(args, "y*:inet_ntoa", &packed_ip)) {
- return NULL;
- }
-
- if (packed_ip.len != sizeof(packed_addr)) {
+ if (packed_ip->len != sizeof(packed_addr)) {
PyErr_SetString(PyExc_OSError,
"packed IP wrong length for inet_ntoa");
- PyBuffer_Release(&packed_ip);
+ PyBuffer_Release(packed_ip);
return NULL;
}
- memcpy(&packed_addr, packed_ip.buf, packed_ip.len);
- PyBuffer_Release(&packed_ip);
+ memcpy(&packed_addr, packed_ip->buf, packed_ip->len);
+ PyBuffer_Release(packed_ip);
SUPPRESS_DEPRECATED_CALL
return PyUnicode_FromString(inet_ntoa(packed_addr));
@@ -6754,7 +6802,7 @@ socket_getaddrinfo(PyObject *self, PyObject *args, PyObject* kwargs)
if (PySys_Audit("socket.getaddrinfo", "OOiii",
hobj, pobj, family, socktype, protocol) < 0) {
- return NULL;
+ goto err;
}
memset(&hints, 0, sizeof(hints));
@@ -6930,11 +6978,12 @@ static PyObject *
socket_getdefaulttimeout(PyObject *self, PyObject *Py_UNUSED(ignored))
{
socket_state *state = get_module_state(self);
- if (state->defaulttimeout < 0) {
+ PyTime_t timeout = _Py_atomic_load_int64_relaxed(&state->defaulttimeout);
+ if (timeout < 0) {
Py_RETURN_NONE;
}
else {
- double seconds = _PyTime_AsSecondsDouble(state->defaulttimeout);
+ double seconds = PyTime_AsSecondsDouble(timeout);
return PyFloat_FromDouble(seconds);
}
}
@@ -6949,13 +6998,13 @@ When the socket module is first imported, the default is None.");
static PyObject *
socket_setdefaulttimeout(PyObject *self, PyObject *arg)
{
- _PyTime_t timeout;
+ PyTime_t timeout;
if (socket_parse_timeout(&timeout, arg) < 0)
return NULL;
socket_state *state = get_module_state(self);
- state->defaulttimeout = timeout;
+ _Py_atomic_store_int64_relaxed(&state->defaulttimeout, timeout);
Py_RETURN_NONE;
}
@@ -7056,34 +7105,34 @@ PyDoc_STRVAR(if_nameindex_doc,
\n\
Returns a list of network interface information (index, name) tuples.");
+/*[clinic input]
+_socket.socket.if_nametoindex
+ oname: unicode_fs_encoded
+ /
+
+Returns the interface index corresponding to the interface name if_name.
+[clinic start generated code]*/
+
static PyObject *
-socket_if_nametoindex(PyObject *self, PyObject *args)
+_socket_socket_if_nametoindex_impl(PySocketSockObject *self, PyObject *oname)
+/*[clinic end generated code: output=f7fc00511a309a8e input=242c01253c533053]*/
{
- PyObject *oname;
#ifdef MS_WINDOWS
NET_IFINDEX index;
#else
unsigned long index;
#endif
- if (!PyArg_ParseTuple(args, "O&:if_nametoindex",
- PyUnicode_FSConverter, &oname))
- return NULL;
+ errno = ENODEV; // in case 'if_nametoindex' does not set errno
index = if_nametoindex(PyBytes_AS_STRING(oname));
- Py_DECREF(oname);
if (index == 0) {
- /* if_nametoindex() doesn't set errno */
- PyErr_SetString(PyExc_OSError, "no interface with this name");
+ PyErr_SetFromErrno(PyExc_OSError);
return NULL;
}
return PyLong_FromUnsignedLong(index);
}
-PyDoc_STRVAR(if_nametoindex_doc,
-"if_nametoindex(if_name)\n\
-\n\
-Returns the interface index corresponding to the interface name if_name.");
static PyObject *
socket_if_indextoname(PyObject *self, PyObject *arg)
@@ -7104,6 +7153,7 @@ socket_if_indextoname(PyObject *self, PyObject *arg)
return NULL;
}
+ errno = ENXIO; // in case 'if_indextoname' does not set errno
char name[IF_NAMESIZE + 1];
if (if_indextoname(index, name) == NULL) {
PyErr_SetFromErrno(PyExc_OSError);
@@ -7228,19 +7278,15 @@ static PyMethodDef socket_methods[] = {
{"socketpair", socket_socketpair,
METH_VARARGS, socketpair_doc},
#endif
- {"ntohs", socket_ntohs,
- METH_VARARGS, ntohs_doc},
+ _SOCKET_SOCKET_NTOHS_METHODDEF
{"ntohl", socket_ntohl,
METH_O, ntohl_doc},
- {"htons", socket_htons,
- METH_VARARGS, htons_doc},
+ _SOCKET_SOCKET_HTONS_METHODDEF
{"htonl", socket_htonl,
METH_O, htonl_doc},
- {"inet_aton", socket_inet_aton,
- METH_VARARGS, inet_aton_doc},
+ _SOCKET_SOCKET_INET_ATON_METHODDEF
#ifdef HAVE_INET_NTOA
- {"inet_ntoa", socket_inet_ntoa,
- METH_VARARGS, inet_ntoa_doc},
+ _SOCKET_SOCKET_INET_NTOA_METHODDEF
#endif
#ifdef HAVE_INET_PTON
{"inet_pton", socket_inet_pton,
@@ -7263,8 +7309,7 @@ static PyMethodDef socket_methods[] = {
#if defined(HAVE_IF_NAMEINDEX) || defined(MS_WINDOWS)
{"if_nameindex", socket_if_nameindex,
METH_NOARGS, if_nameindex_doc},
- {"if_nametoindex", socket_if_nametoindex,
- METH_VARARGS, if_nametoindex_doc},
+ _SOCKET_SOCKET_IF_NAMETOINDEX_METHODDEF
{"if_indextoname", socket_if_indextoname,
METH_O, if_indextoname_doc},
#endif
@@ -7330,20 +7375,39 @@ os_init(void)
}
#endif
+static int
+sock_capi_traverse(PyObject *capsule, visitproc visit, void *arg)
+{
+ PySocketModule_APIObject *capi = PyCapsule_GetPointer(capsule, PySocket_CAPSULE_NAME);
+ assert(capi != NULL);
+ Py_VISIT(capi->Sock_Type);
+ return 0;
+}
+
+static int
+sock_capi_clear(PyObject *capsule)
+{
+ PySocketModule_APIObject *capi = PyCapsule_GetPointer(capsule, PySocket_CAPSULE_NAME);
+ assert(capi != NULL);
+ Py_CLEAR(capi->Sock_Type);
+ return 0;
+}
+
static void
-sock_free_api(PySocketModule_APIObject *capi)
+sock_capi_free(PySocketModule_APIObject *capi)
{
- Py_DECREF(capi->Sock_Type);
+ Py_XDECREF(capi->Sock_Type); // sock_capi_free() can clear it
Py_DECREF(capi->error);
Py_DECREF(capi->timeout_error);
PyMem_Free(capi);
}
static void
-sock_destroy_api(PyObject *capsule)
+sock_capi_destroy(PyObject *capsule)
{
void *capi = PyCapsule_GetPointer(capsule, PySocket_CAPSULE_NAME);
- sock_free_api(capi);
+ assert(capi != NULL);
+ sock_capi_free(capi);
}
static PySocketModule_APIObject *
@@ -7448,14 +7512,18 @@ socket_exec(PyObject *m)
}
PyObject *capsule = PyCapsule_New(capi,
PySocket_CAPSULE_NAME,
- sock_destroy_api);
+ sock_capi_destroy);
if (capsule == NULL) {
- sock_free_api(capi);
+ sock_capi_free(capi);
goto error;
}
- int rc = PyModule_AddObjectRef(m, PySocket_CAPI_NAME, capsule);
- Py_DECREF(capsule);
- if (rc < 0) {
+ if (_PyCapsule_SetTraverse(capsule,
+ sock_capi_traverse, sock_capi_clear) < 0) {
+ sock_capi_free(capi);
+ goto error;
+ }
+
+ if (PyModule_Add(m, PySocket_CAPI_NAME, capsule) < 0) {
goto error;
}
@@ -7667,13 +7735,13 @@ socket_exec(PyObject *m)
#ifdef BTPROTO_HCI
ADD_INT_MACRO(m, BTPROTO_HCI);
ADD_INT_MACRO(m, SOL_HCI);
-#if !defined(__NetBSD__) && !defined(__DragonFly__)
+#if defined(HCI_FILTER)
ADD_INT_MACRO(m, HCI_FILTER);
-#if !defined(__FreeBSD__)
+#endif
+#if defined(HCI_TIME_STAMP)
ADD_INT_MACRO(m, HCI_TIME_STAMP);
ADD_INT_MACRO(m, HCI_DATA_DIR);
-#endif /* !__FreeBSD__ */
-#endif /* !__NetBSD__ && !__DragonFly__ */
+#endif
#endif /* BTPROTO_HCI */
#ifdef BTPROTO_RFCOMM
ADD_INT_MACRO(m, BTPROTO_RFCOMM);
@@ -7925,6 +7993,9 @@ socket_exec(PyObject *m)
#ifdef SO_BINDTODEVICE
ADD_INT_MACRO(m, SO_BINDTODEVICE);
#endif
+#ifdef SO_BINDTOIFINDEX
+ ADD_INT_MACRO(m, SO_BINDTOIFINDEX);
+#endif
#ifdef SO_PRIORITY
ADD_INT_MACRO(m, SO_PRIORITY);
#endif
@@ -8095,7 +8166,7 @@ socket_exec(PyObject *m)
#endif
#if defined(HAVE_LINUX_CAN_RAW_H) || defined(HAVE_NETCAN_CAN_H)
ADD_INT_MACRO(m, CAN_RAW_FILTER);
-#ifdef CAN_RAW_ERR_FILTER
+#ifdef HAVE_LINUX_CAN_RAW_H
ADD_INT_MACRO(m, CAN_RAW_ERR_FILTER);
#endif
ADD_INT_MACRO(m, CAN_RAW_LOOPBACK);
@@ -8808,6 +8879,9 @@ socket_exec(PyObject *m)
#ifdef NI_DGRAM
ADD_INT_MACRO(m, NI_DGRAM);
#endif
+#ifdef NI_IDN
+ ADD_INT_MACRO(m, NI_IDN);
+#endif
/* shutdown() parameters */
#ifdef SHUT_RD
@@ -8846,13 +8920,7 @@ socket_exec(PyObject *m)
};
int i;
for (i = 0; i < Py_ARRAY_LENGTH(codes); ++i) {
- PyObject *tmp = PyLong_FromUnsignedLong(codes[i]);
- if (tmp == NULL) {
- goto error;
- }
- int rc = PyModule_AddObjectRef(m, names[i], tmp);
- Py_DECREF(tmp);
- if (rc < 0) {
+ if (PyModule_Add(m, names[i], PyLong_FromUnsignedLong(codes[i])) < 0) {
goto error;
}
}
@@ -8893,6 +8961,7 @@ error:
static struct PyModuleDef_Slot socket_slots[] = {
{Py_mod_exec, socket_exec},
{Py_mod_multiple_interpreters, Py_MOD_PER_INTERPRETER_GIL_SUPPORTED},
+ {Py_mod_gil, Py_MOD_GIL_NOT_USED},
{0, NULL},
};