On 2025-11-16, Pokemon Chw via Python-list <[email protected]> wrote:
> On Linux AF_UNIX + SOCK_STREAM sockets, there is a quirk in how the
> kernel handles control messages with SCM_RIGHTS:
>
> To successfully pass file descriptors via SCM_RIGHTS, you must send
> at least one byte of normal data in the same sendmsg()
> call. Otherwise, the control message (i.e., the file descriptors)
> will not actually be transmitted.
Very interesting! If I ever knew that I had completely forgotten it.
Apparently that's not true on Mac OS-X where there must be at least
one iovec entry, but that entry can contain zero bytes.
FWIW, here is the relevent portion of the Linux man page Unix(7):
Ancillary messages
Ancillary data is sent and received using sendmsg(2) and
recvmsg(2). For historical reasons, the ancillary message types
listed below are specified with a SOL_SOCKET type even though they
are AF_UNIX specific. To send them, set the cmsg_level field of
the struct cmsghdr to SOL_SOCKET and the cmsg_type field to the
type. For more information, see cmsg(3).
SCM_RIGHTS
Send or receive a set of open file descriptors from another
process. The data portion contains an integer array of the file
descriptors.
Commonly, this operation is referred to as "passing a file
descriptor" to another process. However, more accurately, what
is being passed is a reference to an open file description (see
open(2)), and in the receiving process it is likely that a
different file descriptor number will be used. Semantically,
this operation is equivalent to duplicating (dup(2)) a file
descriptor into the file descriptor table of another process.
If the buffer used to receive the ancillary data containing file
de‐ scriptors is too small (or is absent), then the ancillary
data is truncated (or discarded) and the excess file descriptors
are automati‐ cally closed in the receiving process.
If the number of file descriptors received in the ancillary data
would cause the process to exceed its RLIMIT_NOFILE resource
limit (see getrlimit(2)), the excess file descriptors are
automatically closed in the receiving process.
The kernel constant SCM_MAX_FD defines a limit on the number of
file descriptors in the array. Attempting to send an array
larger than this limit causes sendmsg(2) to fail with the error
EINVAL. SCM_MAX_FD has the value 253 (or 255 before Linux
2.6.38).
[...]
At least one byte of real data should be sent when sending
ancillary data. On Linux, this is required to successfully send
ancillary data over a UNIX domain stream socket. When sending
ancillary data over a UNIX domain datagram socket, it is not
necessary on Linux to send any accompanying real data. However,
portable applications should also include at least one byte of real
data when sending ancillary data over a datagram socket.
--
https://mail.python.org/mailman3//lists/python-list.python.org