mirror of
https://github.com/python/cpython.git
synced 2025-09-19 15:10:58 +00:00
bpo-36046: posix_spawn() doesn't support uid/gid (GH-16384)
* subprocess.Popen now longer uses posix_spawn() if uid, gid or gids are set. * test_subprocess: add "nobody" and "nfsnobody" group names for test_group(). * test_subprocess: test_user() and test_group() are now also tested with close_fds=False.
This commit is contained in:
parent
1dc1acbd73
commit
faca855342
2 changed files with 42 additions and 34 deletions
|
@ -1681,7 +1681,10 @@ class Popen(object):
|
||||||
and (p2cread == -1 or p2cread > 2)
|
and (p2cread == -1 or p2cread > 2)
|
||||||
and (c2pwrite == -1 or c2pwrite > 2)
|
and (c2pwrite == -1 or c2pwrite > 2)
|
||||||
and (errwrite == -1 or errwrite > 2)
|
and (errwrite == -1 or errwrite > 2)
|
||||||
and not start_new_session):
|
and not start_new_session
|
||||||
|
and gid is None
|
||||||
|
and gids is None
|
||||||
|
and uid is None):
|
||||||
self._posix_spawn(args, executable, env, restore_signals,
|
self._posix_spawn(args, executable, env, restore_signals,
|
||||||
p2cread, p2cwrite,
|
p2cread, p2cwrite,
|
||||||
c2pread, c2pwrite,
|
c2pread, c2pwrite,
|
||||||
|
|
|
@ -1589,7 +1589,7 @@ class RunFuncTestCase(BaseTestCase):
|
||||||
|
|
||||||
|
|
||||||
def _get_test_grp_name():
|
def _get_test_grp_name():
|
||||||
for name_group in ('staff', 'nogroup', 'grp'):
|
for name_group in ('staff', 'nogroup', 'grp', 'nobody', 'nfsnobody'):
|
||||||
if grp:
|
if grp:
|
||||||
try:
|
try:
|
||||||
grp.getgrnam(name_group)
|
grp.getgrnam(name_group)
|
||||||
|
@ -1768,24 +1768,27 @@ class POSIXProcessTestCase(BaseTestCase):
|
||||||
test_users.append(name_uid)
|
test_users.append(name_uid)
|
||||||
|
|
||||||
for user in test_users:
|
for user in test_users:
|
||||||
with self.subTest(user=user):
|
# posix_spawn() may be used with close_fds=False
|
||||||
try:
|
for close_fds in (False, True):
|
||||||
output = subprocess.check_output(
|
with self.subTest(user=user, close_fds=close_fds):
|
||||||
[sys.executable, "-c",
|
try:
|
||||||
"import os; print(os.getuid())"],
|
output = subprocess.check_output(
|
||||||
user=user)
|
[sys.executable, "-c",
|
||||||
except PermissionError: # errno.EACCES
|
"import os; print(os.getuid())"],
|
||||||
pass
|
user=user,
|
||||||
except OSError as e:
|
close_fds=close_fds)
|
||||||
if e.errno not in (errno.EACCES, errno.EPERM):
|
except PermissionError: # (EACCES, EPERM)
|
||||||
raise
|
pass
|
||||||
else:
|
except OSError as e:
|
||||||
if isinstance(user, str):
|
if e.errno not in (errno.EACCES, errno.EPERM):
|
||||||
user_uid = pwd.getpwnam(user).pw_uid
|
raise
|
||||||
else:
|
else:
|
||||||
user_uid = user
|
if isinstance(user, str):
|
||||||
child_user = int(output)
|
user_uid = pwd.getpwnam(user).pw_uid
|
||||||
self.assertEqual(child_user, user_uid)
|
else:
|
||||||
|
user_uid = user
|
||||||
|
child_user = int(output)
|
||||||
|
self.assertEqual(child_user, user_uid)
|
||||||
|
|
||||||
with self.assertRaises(ValueError):
|
with self.assertRaises(ValueError):
|
||||||
subprocess.check_call([sys.executable, "-c", "pass"], user=-1)
|
subprocess.check_call([sys.executable, "-c", "pass"], user=-1)
|
||||||
|
@ -1809,23 +1812,25 @@ class POSIXProcessTestCase(BaseTestCase):
|
||||||
group_list.append(name_group)
|
group_list.append(name_group)
|
||||||
|
|
||||||
for group in group_list + [gid]:
|
for group in group_list + [gid]:
|
||||||
with self.subTest(group=group):
|
# posix_spawn() may be used with close_fds=False
|
||||||
try:
|
for close_fds in (False, True):
|
||||||
output = subprocess.check_output(
|
with self.subTest(group=group, close_fds=close_fds):
|
||||||
[sys.executable, "-c",
|
try:
|
||||||
"import os; print(os.getgid())"],
|
output = subprocess.check_output(
|
||||||
group=group)
|
[sys.executable, "-c",
|
||||||
except OSError as e:
|
"import os; print(os.getgid())"],
|
||||||
if e.errno != errno.EPERM:
|
group=group,
|
||||||
raise
|
close_fds=close_fds)
|
||||||
else:
|
except PermissionError: # (EACCES, EPERM)
|
||||||
if isinstance(group, str):
|
pass
|
||||||
group_gid = grp.getgrnam(group).gr_gid
|
|
||||||
else:
|
else:
|
||||||
group_gid = group
|
if isinstance(group, str):
|
||||||
|
group_gid = grp.getgrnam(group).gr_gid
|
||||||
|
else:
|
||||||
|
group_gid = group
|
||||||
|
|
||||||
child_group = int(output)
|
child_group = int(output)
|
||||||
self.assertEqual(child_group, group_gid)
|
self.assertEqual(child_group, group_gid)
|
||||||
|
|
||||||
# make sure we bomb on negative values
|
# make sure we bomb on negative values
|
||||||
with self.assertRaises(ValueError):
|
with self.assertRaises(ValueError):
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue