Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 9d6c669

Browse files
committed
Issue #13777: Add PF_SYSTEM sockets on OS X.
Patch by Michael Goderbauer.
1 parent 61c4e10 commit 9d6c669

8 files changed

Lines changed: 141 additions & 6 deletions

File tree

Doc/library/socket.rst

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,14 @@ created. Socket addresses are represented as follows:
9999
``'can0'``. The network interface name ``''`` can be used to receive packets
100100
from all network interfaces of this family.
101101

102+
- A string or a tuple ``(id, unit)`` is used for the :const:`SYSPROTO_CONTROL`
103+
protocol of the :const:`PF_SYSTEM` family. The string is the name of a
104+
kernel control using a dynamically-assigned ID. The tuple can be used if ID
105+
and unit number of the kernel control are known or if a registered ID is
106+
used.
107+
108+
.. versionadded:: 3.3
109+
102110
- Certain other address families (:const:`AF_BLUETOOTH`, :const:`AF_PACKET`)
103111
support specific representations.
104112

Misc/ACKS

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -366,6 +366,7 @@ Jonathan Giddy
366366
Johannes Gijsbers
367367
Michael Gilfix
368368
Yannick Gingras
369+
Michael Goderbauer
369370
Christoph Gohlke
370371
Tim Golden
371372
Tiago Gonçalves

Misc/NEWS

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,9 @@ What's New in Python 3.3 Alpha 1?
1010
Core and Builtins
1111
-----------------
1212

13+
- Issue #13777: Add PF_SYSTEM sockets on OS X.
14+
Patch by Michael Goderbauer.
15+
1316
- Issue #13908: Ready types returned from PyType_FromSpec.
1417

1518
- Issue #11235: Fix OverflowError when trying to import a source file whose

Modules/socketmodule.c

Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -218,6 +218,11 @@ if_indextoname(index) -- return the corresponding interface name\n\
218218
# include <ioctl.h>
219219
#endif
220220

221+
#ifdef __APPLE__
222+
# include <sys/ioctl.h>
223+
#endif
224+
225+
221226
#if defined(PYOS_OS2)
222227
# define INCL_DOS
223228
# define INCL_DOSERRORS
@@ -1239,6 +1244,23 @@ makesockaddr(SOCKET_T sockfd, struct sockaddr *addr, size_t addrlen, int proto)
12391244
}
12401245
#endif
12411246

1247+
#ifdef PF_SYSTEM
1248+
case PF_SYSTEM:
1249+
switch(proto) {
1250+
#ifdef SYSPROTO_CONTROL
1251+
case SYSPROTO_CONTROL:
1252+
{
1253+
struct sockaddr_ctl *a = (struct sockaddr_ctl *)addr;
1254+
return Py_BuildValue("(II)", a->sc_id, a->sc_unit);
1255+
}
1256+
#endif
1257+
default:
1258+
PyErr_SetString(PyExc_ValueError,
1259+
"Invalid address type");
1260+
return 0;
1261+
}
1262+
#endif
1263+
12421264
/* More cases here... */
12431265

12441266
default:
@@ -1677,6 +1699,64 @@ getsockaddrarg(PySocketSockObject *s, PyObject *args,
16771699
return 0;
16781700
}
16791701
#endif
1702+
1703+
#ifdef PF_SYSTEM
1704+
case PF_SYSTEM:
1705+
switch (s->sock_proto) {
1706+
#ifdef SYSPROTO_CONTROL
1707+
case SYSPROTO_CONTROL:
1708+
{
1709+
struct sockaddr_ctl *addr;
1710+
1711+
addr = (struct sockaddr_ctl *)addr_ret;
1712+
addr->sc_family = AF_SYSTEM;
1713+
addr->ss_sysaddr = AF_SYS_CONTROL;
1714+
1715+
if (PyUnicode_Check(args)) {
1716+
struct ctl_info info;
1717+
PyObject *ctl_name;
1718+
1719+
if (!PyArg_Parse(args, "O&",
1720+
PyUnicode_FSConverter, &ctl_name)) {
1721+
return 0;
1722+
}
1723+
1724+
if (PyBytes_GET_SIZE(ctl_name) > sizeof(info.ctl_name)) {
1725+
PyErr_SetString(PyExc_ValueError,
1726+
"provided string is too long");
1727+
Py_DECREF(ctl_name);
1728+
return 0;
1729+
}
1730+
strncpy(info.ctl_name, PyBytes_AS_STRING(ctl_name),
1731+
sizeof(info.ctl_name));
1732+
Py_DECREF(ctl_name);
1733+
1734+
if (ioctl(s->sock_fd, CTLIOCGINFO, &info)) {
1735+
PyErr_SetString(PyExc_OSError,
1736+
"cannot find kernel control with provided name");
1737+
return 0;
1738+
}
1739+
1740+
addr->sc_id = info.ctl_id;
1741+
addr->sc_unit = 0;
1742+
} else if (!PyArg_ParseTuple(args, "II",
1743+
&(addr->sc_id), &(addr->sc_unit))) {
1744+
PyErr_SetString(PyExc_TypeError, "getsockaddrarg: "
1745+
"expected str or tuple of two ints");
1746+
1747+
return 0;
1748+
}
1749+
1750+
*len_ret = sizeof(*addr);
1751+
return 1;
1752+
}
1753+
#endif
1754+
default:
1755+
PyErr_SetString(PyExc_OSError,
1756+
"getsockaddrarg: unsupported PF_SYSTEM protocol");
1757+
return 0;
1758+
}
1759+
#endif
16801760

16811761
/* More cases here... */
16821762

@@ -1783,6 +1863,21 @@ getsockaddrlen(PySocketSockObject *s, socklen_t *len_ret)
17831863
return 1;
17841864
}
17851865
#endif
1866+
1867+
#ifdef PF_SYSTEM
1868+
case PF_SYSTEM:
1869+
switch(s->sock_proto) {
1870+
#ifdef SYSPROTO_CONTROL
1871+
case SYSPROTO_CONTROL:
1872+
*len_ret = sizeof (struct sockaddr_ctl);
1873+
return 1;
1874+
#endif
1875+
default:
1876+
PyErr_SetString(PyExc_OSError, "getsockaddrlen: "
1877+
"unknown PF_SYSTEM protocol");
1878+
return 0;
1879+
}
1880+
#endif
17861881

17871882
/* More cases here... */
17881883

@@ -5660,6 +5755,14 @@ PyInit__socket(void)
56605755
PyModule_AddIntConstant(m, "PF_RDS", PF_RDS);
56615756
#endif
56625757

5758+
/* Kernel event messages */
5759+
#ifdef PF_SYSTEM
5760+
PyModule_AddIntConstant(m, "PF_SYSTEM", PF_SYSTEM);
5761+
#endif
5762+
#ifdef AF_SYSTEM
5763+
PyModule_AddIntConstant(m, "AF_SYSTEM", AF_SYSTEM);
5764+
#endif
5765+
56635766
#ifdef AF_PACKET
56645767
PyModule_AddIntMacro(m, AF_PACKET);
56655768
#endif
@@ -6096,6 +6199,10 @@ PyInit__socket(void)
60966199
PyModule_AddIntConstant(m, "IPPROTO_MAX", IPPROTO_MAX);
60976200
#endif
60986201

6202+
#ifdef SYSPROTO_CONTROL
6203+
PyModule_AddIntConstant(m, "SYSPROTO_CONTROL", SYSPROTO_CONTROL);
6204+
#endif
6205+
60996206
/* Some port configuration */
61006207
#ifdef IPPORT_RESERVED
61016208
PyModule_AddIntConstant(m, "IPPORT_RESERVED", IPPORT_RESERVED);

Modules/socketmodule.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,13 @@ typedef int socklen_t;
8080
#include <linux/can/raw.h>
8181
#endif
8282

83+
#ifdef HAVE_SYS_SYS_DOMAIN_H
84+
#include <sys/sys_domain.h>
85+
#endif
86+
#ifdef HAVE_SYS_KERN_CONTROL_H
87+
#include <sys/kern_control.h>
88+
#endif
89+
8390
#ifndef Py__SOCKET_H
8491
#define Py__SOCKET_H
8592
#ifdef __cplusplus
@@ -138,6 +145,9 @@ typedef union sock_addr {
138145
#ifdef HAVE_LINUX_CAN_H
139146
struct sockaddr_can can;
140147
#endif
148+
#ifdef HAVE_SYS_KERN_CONTROL_H
149+
struct sockaddr_ctl ctl;
150+
#endif
141151
} sock_addr_t;
142152

143153
/* The object holding a socket. It holds some extra information,

configure

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6144,10 +6144,10 @@ ieeefp.h io.h langinfo.h libintl.h ncurses.h process.h pthread.h \
61446144
sched.h shadow.h signal.h stdint.h stropts.h termios.h \
61456145
unistd.h utime.h \
61466146
poll.h sys/devpoll.h sys/epoll.h sys/poll.h \
6147-
sys/audioio.h sys/xattr.h sys/bsdtty.h sys/event.h sys/file.h sys/loadavg.h \
6148-
sys/lock.h sys/mkdev.h sys/modem.h \
6147+
sys/audioio.h sys/xattr.h sys/bsdtty.h sys/event.h sys/file.h \
6148+
sys/kern_control.h sys/loadavg.h sys/lock.h sys/mkdev.h sys/modem.h \
61496149
sys/param.h sys/select.h sys/sendfile.h sys/socket.h sys/statvfs.h \
6150-
sys/stat.h sys/syscall.h sys/termio.h sys/time.h \
6150+
sys/stat.h sys/syscall.h sys/sys_domain.h sys/termio.h sys/time.h \
61516151
sys/times.h sys/types.h sys/uio.h sys/un.h sys/utsname.h sys/wait.h pty.h \
61526152
libutil.h sys/resource.h netpacket/packet.h sysexits.h bluetooth.h \
61536153
bluetooth/bluetooth.h linux/tipc.h spawn.h util.h

configure.in

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1334,10 +1334,10 @@ ieeefp.h io.h langinfo.h libintl.h ncurses.h process.h pthread.h \
13341334
sched.h shadow.h signal.h stdint.h stropts.h termios.h \
13351335
unistd.h utime.h \
13361336
poll.h sys/devpoll.h sys/epoll.h sys/poll.h \
1337-
sys/audioio.h sys/xattr.h sys/bsdtty.h sys/event.h sys/file.h sys/loadavg.h \
1338-
sys/lock.h sys/mkdev.h sys/modem.h \
1337+
sys/audioio.h sys/xattr.h sys/bsdtty.h sys/event.h sys/file.h \
1338+
sys/kern_control.h sys/loadavg.h sys/lock.h sys/mkdev.h sys/modem.h \
13391339
sys/param.h sys/select.h sys/sendfile.h sys/socket.h sys/statvfs.h \
1340-
sys/stat.h sys/syscall.h sys/termio.h sys/time.h \
1340+
sys/stat.h sys/syscall.h sys/sys_domain.h sys/termio.h sys/time.h \
13411341
sys/times.h sys/types.h sys/uio.h sys/un.h sys/utsname.h sys/wait.h pty.h \
13421342
libutil.h sys/resource.h netpacket/packet.h sysexits.h bluetooth.h \
13431343
bluetooth/bluetooth.h linux/tipc.h spawn.h util.h)

pyconfig.h.in

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -908,6 +908,9 @@
908908
/* Define to 1 if you have the <sys/file.h> header file. */
909909
#undef HAVE_SYS_FILE_H
910910

911+
/* Define to 1 if you have the <sys/kern_control.h> header file. */
912+
#undef HAVE_SYS_KERN_CONTROL_H
913+
911914
/* Define to 1 if you have the <sys/loadavg.h> header file. */
912915
#undef HAVE_SYS_LOADAVG_H
913916

@@ -951,6 +954,9 @@
951954
/* Define to 1 if you have the <sys/syscall.h> header file. */
952955
#undef HAVE_SYS_SYSCALL_H
953956

957+
/* Define to 1 if you have the <sys/sys_domain.h> header file. */
958+
#undef HAVE_SYS_SYS_DOMAIN_H
959+
954960
/* Define to 1 if you have the <sys/termio.h> header file. */
955961
#undef HAVE_SYS_TERMIO_H
956962

0 commit comments

Comments
 (0)