Repository navigation
gh-159136: Avoid stop-the-world when setting function name attributes - #159269
Conversation
…ibutes Setting __name__, __qualname__, __doc__ or __module__ on a function stopped the world in the free-threaded build since pythongh-154826 and pythongh-154851, making functools.wraps() orders of magnitude slower with multiple threads. Use the per-object critical section and _PyObject_XSetRefDelayed() instead, as gen_set_name() already does. Use acquire loads in the readers and hold strong references across error reporting, tracing, and eval-frame recording that may execute Python or detach the thread. The __code__, __defaults__, __kwdefaults__ and __closure__ setters still stop the world to clear func_version. Document synchronization requirements for direct field access and the lifetime of borrowed function attributes.
Documentation build overview
79 files changed ·
|
Windows uses uppercase letters for hex addresses.
|
When you're done making the requested changes, leave the comment: |
Store func_annotations and func_annotate together before releasing the old values. Take the function's critical section in PyFunction_GetAnnotations(). Use an acquire load in PyFunction_GET_ANNOTATIONS().
|
Thanks @nascheme for the PR 🌮🎉.. I'm working now to backport this PR to: 3.15. |
|
Thanks @nascheme for the PR 🌮🎉.. I'm working now to backport this PR to: 3.14. |
|
Sorry, @nascheme, I could not cleanly backport this to Please backport manually with cherry_picker, see the devguide for more information. |
|
Sorry, @nascheme, I could not cleanly backport this to Please backport manually with cherry_picker, see the devguide for more information. |
…me attributes (pythongh-159269) Setting __name__, __qualname__, __doc__ or __module__ on a function stopped the world in the free-threaded build since pythongh-154826 and pythongh-154851, making functools.wraps() orders of magnitude slower with multiple threads. Use the per-object critical section and _PyObject_XSetRefDelayed() instead, as gen_set_name() already does. Use acquire loads in the readers and hold strong references across error reporting, tracing, and eval-frame recording that may execute Python or detach the thread. The __code__, __defaults__, __kwdefaults__ and __closure__ setters still stop the world to clear func_version. Document synchronization requirements for direct field access and the lifetime of borrowed function attributes. (cherry picked from commit 010bebb) Co-authored-by: Neil Schemenauer <nas-github@arctrix.com>
|
GH-159725 is a backport of this pull request to the 3.15 branch. |
|
GH-159726 is a backport of this pull request to the 3.14 branch. |
Setting
__name__,__qualname__,__doc__or__module__on a function stopped the world in the free-threaded build since gh-154826 and gh-154851, making functools.wraps() orders of magnitude slower with multiple threads.Use the per-object critical section and
_PyObject_XSetRefDelayed()instead, asgen_set_name()already does. Use acquire loads in the readers and hold strong references across error reporting, tracing, and eval-frame recording that may execute Python or detach the thread. The__code__,__defaults__,__kwdefaults__and__closure__setters still stop the world to clear func_version.Document synchronization requirements for direct field access and the lifetime of borrowed function attributes.
Benchmark results (release free-threaded build, each thread creates its own function, 5000 iterations, time in seconds):
__name____name____name__+__doc____name__+__doc__Note: this PR was created with assistance from LLM agents (Claude Fable and GPT 6.1 Sol).
__name__/__doc__stops the world;functools.wrapsfrom multiple threads is orders of magnitude slower since 3.14.7 #159136