mirror of
https://github.com/python/cpython.git
synced 2025-09-26 18:29:57 +00:00
(merge 3.2) Issue #12493: subprocess: communicate() handles EINTR
subprocess.Popen.communicate() now also handles EINTR errors if the process has only one pipe.
This commit is contained in:
commit
5b1261d750
3 changed files with 22 additions and 3 deletions
|
@ -446,7 +446,7 @@ def _eintr_retry_call(func, *args):
|
||||||
while True:
|
while True:
|
||||||
try:
|
try:
|
||||||
return func(*args)
|
return func(*args)
|
||||||
except OSError as e:
|
except (OSError, IOError) as e:
|
||||||
if e.errno == errno.EINTR:
|
if e.errno == errno.EINTR:
|
||||||
continue
|
continue
|
||||||
raise
|
raise
|
||||||
|
@ -820,10 +820,10 @@ class Popen(object):
|
||||||
raise
|
raise
|
||||||
self.stdin.close()
|
self.stdin.close()
|
||||||
elif self.stdout:
|
elif self.stdout:
|
||||||
stdout = self.stdout.read()
|
stdout = _eintr_retry_call(self.stdout.read)
|
||||||
self.stdout.close()
|
self.stdout.close()
|
||||||
elif self.stderr:
|
elif self.stderr:
|
||||||
stderr = self.stderr.read()
|
stderr = _eintr_retry_call(self.stderr.read)
|
||||||
self.stderr.close()
|
self.stderr.close()
|
||||||
self.wait()
|
self.wait()
|
||||||
else:
|
else:
|
||||||
|
|
|
@ -767,6 +767,22 @@ class ProcessTestCase(BaseTestCase):
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
p.communicate(b"x" * 2**20)
|
p.communicate(b"x" * 2**20)
|
||||||
|
|
||||||
|
def test_communicate_eintr(self):
|
||||||
|
# Issue #12493: communicate() should handle EINTR
|
||||||
|
def handler(signum, frame):
|
||||||
|
pass
|
||||||
|
old_handler = signal.signal(signal.SIGALRM, handler)
|
||||||
|
self.addCleanup(signal.signal, signal.SIGALRM, old_handler)
|
||||||
|
|
||||||
|
# the process is running for 2 seconds
|
||||||
|
args = [sys.executable, "-c", 'import time; time.sleep(2)']
|
||||||
|
for stream in ('stdout', 'stderr'):
|
||||||
|
kw = {stream: subprocess.PIPE}
|
||||||
|
with subprocess.Popen(args, **kw) as process:
|
||||||
|
signal.alarm(1)
|
||||||
|
# communicate() will be interrupted by SIGALRM
|
||||||
|
process.communicate()
|
||||||
|
|
||||||
|
|
||||||
# context manager
|
# context manager
|
||||||
class _SuppressCoreFiles(object):
|
class _SuppressCoreFiles(object):
|
||||||
|
|
|
@ -219,6 +219,9 @@ Core and Builtins
|
||||||
Library
|
Library
|
||||||
-------
|
-------
|
||||||
|
|
||||||
|
- Issue #12493: subprocess: Popen.communicate() now also handles EINTR errors
|
||||||
|
if the process has only one pipe.
|
||||||
|
|
||||||
- Issue #12467: warnings: fix a race condition if a warning is emitted at
|
- Issue #12467: warnings: fix a race condition if a warning is emitted at
|
||||||
shutdown, if globals()['__file__'] is None.
|
shutdown, if globals()['__file__'] is None.
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue