mirror of
https://github.com/python/cpython.git
synced 2025-08-24 18:55:00 +00:00
bpo-24484: Avoid race condition in multiprocessing cleanup (#2159)
* bpo-24484: Avoid race condition in multiprocessing cleanup The finalizer registry can be mutated while inspected by multiprocessing at process exit. * Use test.support.start_threads() * Add Misc/NEWS
This commit is contained in:
parent
8323189ff1
commit
1eb6c0074d
3 changed files with 84 additions and 11 deletions
|
@ -241,20 +241,28 @@ def _run_finalizers(minpriority=None):
|
|||
return
|
||||
|
||||
if minpriority is None:
|
||||
f = lambda p : p[0][0] is not None
|
||||
f = lambda p : p[0] is not None
|
||||
else:
|
||||
f = lambda p : p[0][0] is not None and p[0][0] >= minpriority
|
||||
f = lambda p : p[0] is not None and p[0] >= minpriority
|
||||
|
||||
items = [x for x in list(_finalizer_registry.items()) if f(x)]
|
||||
items.sort(reverse=True)
|
||||
# Careful: _finalizer_registry may be mutated while this function
|
||||
# is running (either by a GC run or by another thread).
|
||||
|
||||
for key, finalizer in items:
|
||||
sub_debug('calling %s', finalizer)
|
||||
try:
|
||||
finalizer()
|
||||
except Exception:
|
||||
import traceback
|
||||
traceback.print_exc()
|
||||
# list(_finalizer_registry) should be atomic, while
|
||||
# list(_finalizer_registry.items()) is not.
|
||||
keys = [key for key in list(_finalizer_registry) if f(key)]
|
||||
keys.sort(reverse=True)
|
||||
|
||||
for key in keys:
|
||||
finalizer = _finalizer_registry.get(key)
|
||||
# key may have been removed from the registry
|
||||
if finalizer is not None:
|
||||
sub_debug('calling %s', finalizer)
|
||||
try:
|
||||
finalizer()
|
||||
except Exception:
|
||||
import traceback
|
||||
traceback.print_exc()
|
||||
|
||||
if minpriority is None:
|
||||
_finalizer_registry.clear()
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue