bpo-45274: Fix Thread._wait_for_tstate_lock() race condition (GH-28532) · python/cpython@1ecb641

Original file line numberDiff line numberDiff line change

@@ -1064,11 +1064,24 @@ def _wait_for_tstate_lock(self, block=True, timeout=-1):

10641064

# If the lock is acquired, the C code is done, and self._stop() is

10651065

# called. That sets ._is_stopped to True, and ._tstate_lock to None.

10661066

lock = self._tstate_lock

1067-

if lock is None: # already determined that the C code is done

1067+

if lock is None:

1068+

# already determined that the C code is done

10681069

assert self._is_stopped

1069-

elif lock.acquire(block, timeout):

1070-

lock.release()

1071-

self._stop()

1070+

return

1071+
1072+

try:

1073+

if lock.acquire(block, timeout):

1074+

lock.release()

1075+

self._stop()

1076+

except:

1077+

if lock.locked():

1078+

# bpo-45274: lock.acquire() acquired the lock, but the function

1079+

# was interrupted with an exception before reaching the

1080+

# lock.release(). It can happen if a signal handler raises an

1081+

# exception, like CTRL+C which raises KeyboardInterrupt.

1082+

lock.release()

1083+

self._stop()

1084+

raise

10721085
10731086

@property

10741087

def name(self):