bpo-38692: Add os.pidfd_open. (GH-17063)
This commit is contained in:
parent
56698d5769
commit
6c4c45efae
@ -3539,6 +3539,19 @@ written in Python, such as a mail server's external command delivery program.
|
|||||||
.. availability:: Unix.
|
.. availability:: Unix.
|
||||||
|
|
||||||
|
|
||||||
|
.. function:: pidfd_open(pid, flags=0)
|
||||||
|
|
||||||
|
Return a file descriptor referring to the process *pid*. This descriptor can
|
||||||
|
be used to perform process management without races and signals. The *flags*
|
||||||
|
argument is provided for future extensions; no flag values are currently
|
||||||
|
defined.
|
||||||
|
|
||||||
|
See the :manpage:`pidfd_open(2)` man page for more details.
|
||||||
|
|
||||||
|
.. availability:: Linux 5.3+
|
||||||
|
.. versionadded:: 3.9
|
||||||
|
|
||||||
|
|
||||||
.. function:: plock(op)
|
.. function:: plock(op)
|
||||||
|
|
||||||
Lock program segments into memory. The value of *op* (defined in
|
Lock program segments into memory. The value of *op* (defined in
|
||||||
|
@ -150,6 +150,9 @@ os
|
|||||||
Added :data:`~os.CLD_KILLED` and :data:`~os.CLD_STOPPED` for :attr:`si_code`.
|
Added :data:`~os.CLD_KILLED` and :data:`~os.CLD_STOPPED` for :attr:`si_code`.
|
||||||
(Contributed by Dong-hee Na in :issue:`38493`.)
|
(Contributed by Dong-hee Na in :issue:`38493`.)
|
||||||
|
|
||||||
|
Exposed the Linux-specific :func:`os.pidfd_open` for process management with
|
||||||
|
file descriptors. (:issue:`38692`)
|
||||||
|
|
||||||
threading
|
threading
|
||||||
---------
|
---------
|
||||||
|
|
||||||
|
@ -1470,6 +1470,15 @@ class PosixTester(unittest.TestCase):
|
|||||||
open(fn, 'wb').close()
|
open(fn, 'wb').close()
|
||||||
self.assertRaises(ValueError, os.stat, fn_with_NUL)
|
self.assertRaises(ValueError, os.stat, fn_with_NUL)
|
||||||
|
|
||||||
|
@unittest.skipUnless(hasattr(os, "pidfd_open"), "pidfd_open unavailable")
|
||||||
|
def test_pidfd_open(self):
|
||||||
|
with self.assertRaises(OSError) as cm:
|
||||||
|
os.pidfd_open(-1)
|
||||||
|
if cm.exception.errno == errno.ENOSYS:
|
||||||
|
self.skipTest("system does not support pidfd_open")
|
||||||
|
self.assertEqual(cm.exception.errno, errno.EINVAL)
|
||||||
|
os.close(os.pidfd_open(os.getpid(), 0))
|
||||||
|
|
||||||
class PosixGroupsTester(unittest.TestCase):
|
class PosixGroupsTester(unittest.TestCase):
|
||||||
|
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
|
@ -0,0 +1 @@
|
|||||||
|
Expose the Linux ``pidfd_open`` syscall as :func:`os.pidfd_open`.
|
44
Modules/clinic/posixmodule.c.h
generated
44
Modules/clinic/posixmodule.c.h
generated
@ -3963,6 +3963,44 @@ os_wait(PyObject *module, PyObject *Py_UNUSED(ignored))
|
|||||||
|
|
||||||
#endif /* defined(HAVE_WAIT) */
|
#endif /* defined(HAVE_WAIT) */
|
||||||
|
|
||||||
|
#if (defined(__linux__) && defined(__NR_pidfd_open))
|
||||||
|
|
||||||
|
PyDoc_STRVAR(os_pidfd_open__doc__,
|
||||||
|
"pidfd_open($module, /, pid, flags=0)\n"
|
||||||
|
"--\n"
|
||||||
|
"\n"
|
||||||
|
"Return a file descriptor referring to the process *pid*.\n"
|
||||||
|
"\n"
|
||||||
|
"The descriptor can be used to perform process management without races and\n"
|
||||||
|
"signals.");
|
||||||
|
|
||||||
|
#define OS_PIDFD_OPEN_METHODDEF \
|
||||||
|
{"pidfd_open", (PyCFunction)(void(*)(void))os_pidfd_open, METH_FASTCALL|METH_KEYWORDS, os_pidfd_open__doc__},
|
||||||
|
|
||||||
|
static PyObject *
|
||||||
|
os_pidfd_open_impl(PyObject *module, pid_t pid, unsigned int flags);
|
||||||
|
|
||||||
|
static PyObject *
|
||||||
|
os_pidfd_open(PyObject *module, PyObject *const *args, Py_ssize_t nargs, PyObject *kwnames)
|
||||||
|
{
|
||||||
|
PyObject *return_value = NULL;
|
||||||
|
static const char * const _keywords[] = {"pid", "flags", NULL};
|
||||||
|
static _PyArg_Parser _parser = {"" _Py_PARSE_PID "|O&:pidfd_open", _keywords, 0};
|
||||||
|
pid_t pid;
|
||||||
|
unsigned int flags = 0;
|
||||||
|
|
||||||
|
if (!_PyArg_ParseStackAndKeywords(args, nargs, kwnames, &_parser,
|
||||||
|
&pid, _PyLong_UnsignedInt_Converter, &flags)) {
|
||||||
|
goto exit;
|
||||||
|
}
|
||||||
|
return_value = os_pidfd_open_impl(module, pid, flags);
|
||||||
|
|
||||||
|
exit:
|
||||||
|
return return_value;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* (defined(__linux__) && defined(__NR_pidfd_open)) */
|
||||||
|
|
||||||
#if (defined(HAVE_READLINK) || defined(MS_WINDOWS))
|
#if (defined(HAVE_READLINK) || defined(MS_WINDOWS))
|
||||||
|
|
||||||
PyDoc_STRVAR(os_readlink__doc__,
|
PyDoc_STRVAR(os_readlink__doc__,
|
||||||
@ -8480,6 +8518,10 @@ exit:
|
|||||||
#define OS_WAIT_METHODDEF
|
#define OS_WAIT_METHODDEF
|
||||||
#endif /* !defined(OS_WAIT_METHODDEF) */
|
#endif /* !defined(OS_WAIT_METHODDEF) */
|
||||||
|
|
||||||
|
#ifndef OS_PIDFD_OPEN_METHODDEF
|
||||||
|
#define OS_PIDFD_OPEN_METHODDEF
|
||||||
|
#endif /* !defined(OS_PIDFD_OPEN_METHODDEF) */
|
||||||
|
|
||||||
#ifndef OS_READLINK_METHODDEF
|
#ifndef OS_READLINK_METHODDEF
|
||||||
#define OS_READLINK_METHODDEF
|
#define OS_READLINK_METHODDEF
|
||||||
#endif /* !defined(OS_READLINK_METHODDEF) */
|
#endif /* !defined(OS_READLINK_METHODDEF) */
|
||||||
@ -8731,4 +8773,4 @@ exit:
|
|||||||
#ifndef OS__REMOVE_DLL_DIRECTORY_METHODDEF
|
#ifndef OS__REMOVE_DLL_DIRECTORY_METHODDEF
|
||||||
#define OS__REMOVE_DLL_DIRECTORY_METHODDEF
|
#define OS__REMOVE_DLL_DIRECTORY_METHODDEF
|
||||||
#endif /* !defined(OS__REMOVE_DLL_DIRECTORY_METHODDEF) */
|
#endif /* !defined(OS__REMOVE_DLL_DIRECTORY_METHODDEF) */
|
||||||
/*[clinic end generated code: output=c6e67d475eef00c4 input=a9049054013a1b77]*/
|
/*[clinic end generated code: output=51ba5b9536420cea input=a9049054013a1b77]*/
|
||||||
|
@ -7861,6 +7861,30 @@ os_wait_impl(PyObject *module)
|
|||||||
}
|
}
|
||||||
#endif /* HAVE_WAIT */
|
#endif /* HAVE_WAIT */
|
||||||
|
|
||||||
|
#if defined(__linux__) && defined(__NR_pidfd_open)
|
||||||
|
/*[clinic input]
|
||||||
|
os.pidfd_open
|
||||||
|
pid: pid_t
|
||||||
|
flags: unsigned_int = 0
|
||||||
|
|
||||||
|
Return a file descriptor referring to the process *pid*.
|
||||||
|
|
||||||
|
The descriptor can be used to perform process management without races and
|
||||||
|
signals.
|
||||||
|
[clinic start generated code]*/
|
||||||
|
|
||||||
|
static PyObject *
|
||||||
|
os_pidfd_open_impl(PyObject *module, pid_t pid, unsigned int flags)
|
||||||
|
/*[clinic end generated code: output=5c7252698947dc41 input=c3fd99ce947ccfef]*/
|
||||||
|
{
|
||||||
|
int fd = syscall(__NR_pidfd_open, pid, flags);
|
||||||
|
if (fd < 0) {
|
||||||
|
return posix_error();
|
||||||
|
}
|
||||||
|
return PyLong_FromLong(fd);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
|
#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
|
||||||
/*[clinic input]
|
/*[clinic input]
|
||||||
@ -13671,6 +13695,7 @@ static PyMethodDef posix_methods[] = {
|
|||||||
OS_WAIT4_METHODDEF
|
OS_WAIT4_METHODDEF
|
||||||
OS_WAITID_METHODDEF
|
OS_WAITID_METHODDEF
|
||||||
OS_WAITPID_METHODDEF
|
OS_WAITPID_METHODDEF
|
||||||
|
OS_PIDFD_OPEN_METHODDEF
|
||||||
OS_GETSID_METHODDEF
|
OS_GETSID_METHODDEF
|
||||||
OS_SETSID_METHODDEF
|
OS_SETSID_METHODDEF
|
||||||
OS_SETPGID_METHODDEF
|
OS_SETPGID_METHODDEF
|
||||||
|
Loading…
x
Reference in New Issue
Block a user