gh-90872: Fix subprocess.Popen.wait() for negative timeout (#116989)

On Windows, subprocess.Popen.wait() no longer calls
WaitForSingleObject() with a negative timeout: pass 0 ms if the
timeout is negative.
This commit is contained in:
Victor Stinner 2024-03-19 14:42:44 +01:00 committed by GitHub
parent 408e127159
commit 27cf3ed00c
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 21 additions and 0 deletions

View File

@ -1586,6 +1586,8 @@ class Popen:
"""Internal implementation of wait() on Windows.""" """Internal implementation of wait() on Windows."""
if timeout is None: if timeout is None:
timeout_millis = _winapi.INFINITE timeout_millis = _winapi.INFINITE
elif timeout <= 0:
timeout_millis = 0
else: else:
timeout_millis = int(timeout * 1000) timeout_millis = int(timeout * 1000)
if self.returncode is None: if self.returncode is None:

View File

@ -1607,6 +1607,22 @@ class ProcessTestCase(BaseTestCase):
self.assertIsInstance(subprocess.Popen[bytes], types.GenericAlias) self.assertIsInstance(subprocess.Popen[bytes], types.GenericAlias)
self.assertIsInstance(subprocess.CompletedProcess[str], types.GenericAlias) self.assertIsInstance(subprocess.CompletedProcess[str], types.GenericAlias)
@unittest.skipUnless(hasattr(subprocess, '_winapi'),
'need subprocess._winapi')
def test_wait_negative_timeout(self):
proc = subprocess.Popen(ZERO_RETURN_CMD)
with proc:
patch = mock.patch.object(
subprocess._winapi,
'WaitForSingleObject',
return_value=subprocess._winapi.WAIT_OBJECT_0)
with patch as mock_wait:
proc.wait(-1) # negative timeout
mock_wait.assert_called_once_with(proc._handle, 0)
proc.returncode = None
self.assertEqual(proc.wait(), 0)
class RunFuncTestCase(BaseTestCase): class RunFuncTestCase(BaseTestCase):
def run_python(self, code, **kwargs): def run_python(self, code, **kwargs):

View File

@ -0,0 +1,3 @@
On Windows, :meth:`subprocess.Popen.wait` no longer calls
``WaitForSingleObject()`` with a negative timeout: pass ``0`` ms if the
timeout is negative. Patch by Victor Stinner.