diff -r 3d726dbfca31 Doc/library/socket.rst
--- a/Doc/library/socket.rst Wed Jun 15 17:16:16 2016 -0500
+++ b/Doc/library/socket.rst Thu Jul 21 10:53:53 2016 -0400
@@ -131,6 +131,33 @@
string format. (ex. ``b'12:23:34:45:56:67'``) This protocol is not
supported under FreeBSD.
+ .. versionadded:: 3.4
+
+- :const:`AF_VSOCK` sockets are represented as a (CID, port) tuple
+ where the context ID or CID and port are integers.
+
+ - :const:`VMADDR_CID_ANY` will bind to any CID. Equivalent of INADDR_ANY.
+
+ - :const:`VMADDR_CID_HOST` is the destination CID in an address when
+ referring to the host.
+
+ - :const:`VMADDR_PORT_ANY` will bind to any available port.
+
+ - :const:`IOCTL_VM_SOCKETS_GET_LOCAL_CID` an IOCTL available to discover
+ the local CID address.
+
+ - :const:`SO_VM_SOCKETS_BUFFER_SIZE` is used as the option name in
+ setsockopt or getsockopt to set or get an unsigned long long that
+ specifies the size of the underlying stream socket buffer.
+
+ - :const:`SO_VM_SOCKETS_BUFFER_MIN_SIZE` is used as the option name in
+ setsockopt or getsockopt to set or get an unsigned long long that
+ specifies the minimum size allowed for the underying stream socket buffer.
+
+ - :const:`SO_VM_SOCKETS_BUFFER_MAX_SIZE` is used as the option name in
+ setsockopt or getsockopt to set or get an unsigned long long that
+ specifies the maximum size allowed for the underying socket buffer.
+
- Certain other address families (:const:`AF_PACKET`, :const:`AF_CAN`)
support specific representations.
diff -r 3d726dbfca31 Modules/socketmodule.c
--- a/Modules/socketmodule.c Wed Jun 15 17:16:16 2016 -0500
+++ b/Modules/socketmodule.c Thu Jul 21 10:53:53 2016 -0400
@@ -7,7 +7,8 @@
Limitations:
- Only AF_INET, AF_INET6 and AF_UNIX address families are supported in a
- portable manner, though AF_PACKET, AF_NETLINK and AF_TIPC are supported
+ portable manner, though AF_PACKET, AF_NETLINK, AF_VSOCK and AF_TIPCi
+ are supported
under Linux.
- No read/write operations (use sendall/recv or makefile instead).
- Additional restrictions apply on some non-Unix platforms (compensated
@@ -183,6 +184,7 @@
# endif
#endif
+
#if !defined(HAVE_GETHOSTBYNAME_R) && defined(WITH_THREAD) && \
!defined(MS_WINDOWS)
# define USE_GETHOSTBYNAME_LOCK
@@ -1206,6 +1208,14 @@
}
#endif /* AF_NETLINK */
+#if defined(AF_VSOCK)
+ case AF_VSOCK:
+ {
+ struct sockaddr_vm *a = (struct sockaddr_vm *) addr;
+ return Py_BuildValue("II", a->svm_cid, a->svm_port);
+ }
+#endif /* AF_VSOCK */
+
#ifdef ENABLE_IPV6
case AF_INET6:
{
@@ -1538,6 +1548,32 @@
}
#endif
+#if defined(AF_VSOCK)
+ case AF_VSOCK:
+ {
+ struct sockaddr_vm* addr;
+ int port, cid;
+ addr = (struct sockaddr_vm *)addr_ret;
+ memset(addr, 0, sizeof(struct sockaddr_vm));
+ if (!PyTuple_Check(args)) {
+ PyErr_Format(
+ PyExc_TypeError,
+ "getsockaddrarg: "
+ "AF_VSOCK address must be tuple, not %.500s",
+ Py_TYPE(args)->tp_name);
+ return 0;
+ }
+ if (!PyArg_ParseTuple(args, "II:getsockaddrarg", &cid, &port))
+ return 0;
+ addr->svm_family = s->sock_family;
+ addr->svm_port = port;
+ addr->svm_cid = cid;
+ *len_ret = sizeof(*addr);
+ return 1;
+ }
+#endif
+
+
#ifdef AF_RDS
case AF_RDS:
/* RDS sockets use sockaddr_in: fall-through */
@@ -1975,6 +2011,14 @@
}
#endif
+#if defined(AF_VSOCK)
+ case AF_VSOCK:
+ {
+ *len_ret = sizeof (struct sockaddr_vm);
+ return 1;
+ }
+#endif
+
#ifdef AF_RDS
case AF_RDS:
/* RDS sockets use sockaddr_in: fall-through */
@@ -2448,6 +2492,19 @@
Py_buffer optval;
int flag;
+#ifdef AF_VSOCK
+ if (s->sock_family == AF_VSOCK) {
+ uint64_t vflag;
+ if (PyArg_ParseTuple(args, "iiK:setsockopt",
+ &level, &optname, &vflag)) {
+ // level should always be set to AF_VSOCK
+ res = setsockopt(s->sock_fd, level, optname,
+ (void*)&vflag, sizeof vflag);
+ goto finally;
+ }
+ }
+#endif
+
if (PyArg_ParseTuple(args, "iii:setsockopt",
&level, &optname, &flag)) {
res = setsockopt(s->sock_fd, level, optname,
@@ -2473,6 +2530,11 @@
#endif
PyBuffer_Release(&optval);
}
+
+#ifdef AF_VSOCK
+finally:
+#endif
+
if (res < 0) {
return s->errorhandler();
}
@@ -2500,20 +2562,39 @@
int res;
PyObject *buf;
socklen_t buflen = 0;
+ int flag = 0;
+ socklen_t flagsize;
if (!PyArg_ParseTuple(args, "ii|i:getsockopt",
&level, &optname, &buflen))
return NULL;
if (buflen == 0) {
- int flag = 0;
- socklen_t flagsize = sizeof flag;
+#ifdef AF_VSOCK
+ if (s->sock_family == AF_VSOCK) {
+ uint64_t vflag = 0;
+ flagsize = sizeof vflag;
+ res = getsockopt(s->sock_fd, level, optname,
+ (void *)&vflag, &flagsize);
+ if (res < 0)
+ return s->errorhandler();
+ return PyLong_FromLong(vflag);
+ }
+#endif
+ flagsize = sizeof flag;
res = getsockopt(s->sock_fd, level, optname,
(void *)&flag, &flagsize);
if (res < 0)
return s->errorhandler();
return PyLong_FromLong(flag);
}
+#ifdef AF_VSOCK
+ if (s->sock_family == AF_VSOCK) {
+ PyErr_SetString(PyExc_OSError,
+ "getsockopt string buffer not allowed");
+ return NULL;
+ }
+#endif
if (buflen <= 0 || buflen > 1024) {
PyErr_SetString(PyExc_OSError,
"getsockopt buflen out of range");
@@ -6330,6 +6411,19 @@
PyModule_AddIntMacro(m, NETLINK_TAPBASE);
#endif
#endif /* AF_NETLINK */
+
+#ifdef AF_VSOCK
+ PyModule_AddIntConstant(m, "AF_VSOCK", AF_VSOCK);
+ PyModule_AddIntConstant(m, "SO_VM_SOCKETS_BUFFER_SIZE", 0);
+ PyModule_AddIntConstant(m, "SO_VM_SOCKETS_BUFFER_MIN_SIZE", 1);
+ PyModule_AddIntConstant(m, "SO_VM_SOCKETS_BUFFER_MAX_SIZE", 2);
+ PyModule_AddIntConstant(m, "VMADDR_CID_ANY", 0xffffffff);
+ PyModule_AddIntConstant(m, "VMADDR_PORT_ANY", 0xffffffff);
+ PyModule_AddIntConstant(m, "VMADDR_CID_HOST", 2);
+ PyModule_AddIntConstant(m, "VM_SOCKETS_INVALID_VERSION", 0xffffffff);
+ PyModule_AddIntConstant(m, "IOCTL_VM_SOCKETS_GET_LOCAL_CID", _IO(7, 0xb9));
+#endif
+
#ifdef AF_ROUTE
/* Alias to emulate 4.4BSD */
PyModule_AddIntMacro(m, AF_ROUTE);
diff -r 3d726dbfca31 Modules/socketmodule.h
--- a/Modules/socketmodule.h Wed Jun 15 17:16:16 2016 -0500
+++ b/Modules/socketmodule.h Thu Jul 21 10:53:53 2016 -0400
@@ -54,6 +54,12 @@
# undef AF_NETLINK
#endif
+#ifdef HAVE_LINUX_VM_SOCKETS_H
+# include
+#else
+# undef AF_VSOCK
+#endif
+
#ifdef HAVE_BLUETOOTH_BLUETOOTH_H
#include
#include
diff -r 3d726dbfca31 configure.ac
--- a/configure.ac Wed Jun 15 17:16:16 2016 -0500
+++ b/configure.ac Thu Jul 21 10:53:53 2016 -0400
@@ -1919,6 +1919,13 @@
#endif
])
+AC_CHECK_HEADERS(linux/vm_sockets.h,,,[
+#ifdef HAVE_SYS_SOCKET_H
+#include
+#endif
+])
+
+
# On Linux, can.h and can/raw.h require sys/socket.h
AC_CHECK_HEADERS(linux/can.h linux/can/raw.h linux/can/bcm.h,,,[
#ifdef HAVE_SYS_SOCKET_H