diff options
author | Noam Cohen <noam@noam.me> | 2022-10-20 09:08:54 (GMT) |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-10-20 09:08:54 (GMT) |
commit | a371a7e03e43e08cae70235a71904989c0f57a5e (patch) | |
tree | 40b9d4b13ec579ae370760e2dafd888e32f2b06f /Lib/test/test_posix.py | |
parent | c1e02d4e4e09dfc9d57c4d36eca1bbf312d4162d (diff) | |
download | cpython-a371a7e03e43e08cae70235a71904989c0f57a5e.zip cpython-a371a7e03e43e08cae70235a71904989c0f57a5e.tar.gz cpython-a371a7e03e43e08cae70235a71904989c0f57a5e.tar.bz2 |
gh-95023: Added os.setns and os.unshare functions (#95046)
Added os.setns and os.unshare to easily switch between namespaces
on Linux.
Co-authored-by: Christian Heimes <christian@python.org>
Co-authored-by: CAM Gerlach <CAM.Gerlach@Gerlach.CAM>
Co-authored-by: Victor Stinner <vstinner@python.org>
Diffstat (limited to 'Lib/test/test_posix.py')
-rw-r--r-- | Lib/test/test_posix.py | 47 |
1 files changed, 47 insertions, 0 deletions
diff --git a/Lib/test/test_posix.py b/Lib/test/test_posix.py index be561af..442dec8 100644 --- a/Lib/test/test_posix.py +++ b/Lib/test/test_posix.py @@ -2191,6 +2191,53 @@ class TestPosixWeaklinking(unittest.TestCase): os.utime("path", dir_fd=0) +class NamespacesTests(unittest.TestCase): + """Tests for os.unshare() and os.setns().""" + + @unittest.skipUnless(hasattr(os, 'unshare'), 'needs os.unshare()') + @unittest.skipUnless(hasattr(os, 'setns'), 'needs os.setns()') + @unittest.skipUnless(os.path.exists('/proc/self/ns/uts'), 'need /proc/self/ns/uts') + @support.requires_linux_version(3, 0, 0) + def test_unshare_setns(self): + code = """if 1: + import errno + import os + import sys + fd = os.open('/proc/self/ns/uts', os.O_RDONLY) + try: + original = os.readlink('/proc/self/ns/uts') + try: + os.unshare(os.CLONE_NEWUTS) + except OSError as e: + if e.errno == errno.ENOSPC: + # skip test if limit is exceeded + sys.exit() + raise + new = os.readlink('/proc/self/ns/uts') + if original == new: + raise Exception('os.unshare failed') + os.setns(fd, os.CLONE_NEWUTS) + restored = os.readlink('/proc/self/ns/uts') + if original != restored: + raise Exception('os.setns failed') + except PermissionError: + # The calling process did not have the required privileges + # for this operation + pass + except OSError as e: + # Skip the test on these errors: + # - ENOSYS: syscall not available + # - EINVAL: kernel was not configured with the CONFIG_UTS_NS option + # - ENOMEM: not enough memory + if e.errno not in (errno.ENOSYS, errno.EINVAL, errno.ENOMEM): + raise + finally: + os.close(fd) + """ + + assert_python_ok("-c", code) + + def tearDownModule(): support.reap_children() |