Skip to content

Avoid the weakref list lock when dereferencing weakrefs #159564

Open

Description

@nascheme

Feature or enhancement

In the free-threaded build, dereferencing a live weakref takes a striped weakref-list lock. This affects PyWeakref_GetRef(), calls to weakref.ref objects, and weakref hashing and comparison.

The 127 locks are packed into a small per-interpreter array. Threads accessing unrelated weakrefs can therefore contend on the same locks or cache lines, limiting throughput.

I propose using an atomic pointer load followed by _Py_TryIncrefCompare() instead of taking the lock in _PyWeakref_GET_REF().

This uses the allocator and reference-counting guarantees already used for optimistic dict and list reads. QSBR keeps reference-count fields readable during concurrent deallocation, and weakref creation already sets _Py_REF_MAYBE_WEAKREF on the referent. The pointer validation handles memory reuse: a weakref's target can only change from its original referent to Py_None.

Weakref creation, clearing, and deallocation would retain their existing synchronization.

Has this already been discussed elsewhere?

This is a minor feature, which does not need previous discussion elsewhere

Links to previous discussion of this feature:

No response

Linked PRs

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions