From d4e412ba723df41344676f1c902172814141ab62 Mon Sep 17 00:00:00 2001 From: jg Date: Wed, 14 Oct 2026 23:00:15 +0100 Subject: [PATCH 1/2] Avoid re-locking both sets in set.issuperset() on the free-threaded build `set_issuperset_impl()` is already locked but calls `set_issubset` which just wraps a lock to `set_issubset_impl` --- Objects/setobject.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Objects/setobject.c b/Objects/setobject.c index 8fdd1eb26118c0a..7b31acf132a7639 100644 --- a/Objects/setobject.c +++ b/Objects/setobject.c @@ -2418,6 +2418,9 @@ set_issubset_impl(PySetObject *so, PyObject *other) Py_ssize_t pos = 0; int rv; + _Py_CRITICAL_SECTION_ASSERT_OBJECT_LOCKED(so); + _Py_CRITICAL_SECTION_ASSERT_OBJECT_LOCKED(other); + if (!PyAnySet_Check(other)) { PyObject *tmp = set_intersection(so, other); if (tmp == NULL) { @@ -2460,7 +2463,7 @@ set_issuperset_impl(PySetObject *so, PyObject *other) /*[clinic end generated code: output=ecf00ce552c09461 input=5f2e1f262e6e4ccc]*/ { if (PyAnySet_Check(other)) { - return set_issubset(other, (PyObject *)so); + return set_issubset_impl((PySetObject *)other, (PyObject *)so); } PyObject *key, *it = PyObject_GetIter(other); From 5867c21909b3181e9fd9c59f0a0ce4b564e7d470 Mon Sep 17 00:00:00 2001 From: jg Date: Thu, 15 Oct 2026 21:44:28 +0100 Subject: [PATCH 2/2] News entry --- .../2026-10-15-21-44-08.gh-issue-159486.2yJkXO.rst | 1 + 1 file changed, 1 insertion(+) create mode 100644 Misc/NEWS.d/next/Core_and_Builtins/2026-10-15-21-44-08.gh-issue-159486.2yJkXO.rst diff --git a/Misc/NEWS.d/next/Core_and_Builtins/2026-10-15-21-44-08.gh-issue-159486.2yJkXO.rst b/Misc/NEWS.d/next/Core_and_Builtins/2026-10-15-21-44-08.gh-issue-159486.2yJkXO.rst new file mode 100644 index 000000000000000..d493998dbef9dd9 --- /dev/null +++ b/Misc/NEWS.d/next/Core_and_Builtins/2026-10-15-21-44-08.gh-issue-159486.2yJkXO.rst @@ -0,0 +1 @@ +Speed up ``set >= set``, ``set > set`` and ``set.issuperset()`` on the free-threaded build.