Files
gentoo/dev-python/pygame/files/pygame-2.6.1-py315.patch
Ionen Wolkens 3e2666a146 dev-python/pygame: drop duplicate chunk from py315.patch
Still need to check to be sure it works with <3.14 (should've
given some bits), but the patch had an accidental double chunk
which somehow still applied due to fuzz, leading to the
redifinition only for <3.13.

Closes: https://bugs.gentoo.org/985432
Signed-off-by: Ionen Wolkens <ionen@gentoo.org>
2026-11-02 06:59:43 -05:00

124 lines
4.4 KiB
Diff

No proper upstream fix yet, patch taken from [1]. Sounded questionable
but upon inspection I believe it's Ok. Originally tried Fedora's patch
but it caused test failures (or at least did with python3.14).
In addition to [1], this also extend on py314-tests.patch to adjust
refcount values for py315. [1] mentions & explain these failures a bit
but did not address them, I "believe" that they are nothing to worry
about. If this test causes more problems, may make sense to patch it
out downstream until upstream handles it.
[1] https://github.com/pygame/pygame/issues/4716#issuecomment-6104711463
--- a/src_c/pgcompat.h
+++ b/src_c/pgcompat.h
@@ -25,3 +25,25 @@
PySlice_GetIndicesEx(slice, length, start, stop, step, slicelength)
+/* PyWeakref_GetObject() was removed in Python 3.15. PyWeakref_GetRef()
+ * (Python 3.13+) replaces it: returns 1 and a new reference if the referent
+ * is alive, 0 and NULL if it is dead, -1 and NULL on error. */
+#if PY_VERSION_HEX < 0x030D0000
+static inline int
+PyWeakref_GetRef(PyObject *ref, PyObject **pobj)
+{
+ PyObject *obj = PyWeakref_GetObject(ref);
+ if (obj == NULL) {
+ *pobj = NULL;
+ return -1;
+ }
+ if (obj == Py_None) {
+ *pobj = NULL;
+ return 0;
+ }
+ Py_INCREF(obj);
+ *pobj = obj;
+ return 1;
+}
+#endif
+
#endif /* ~PGCOMPAT_INTERNAL_H */
--- a/src_c/surface.c
+++ b/src_c/surface.c
@@ -1021,6 +1021,12 @@
for (i = 0; i < len; i++) {
- tmp = PyWeakref_GetObject(PyList_GetItem(surf->locklist, i));
- Py_INCREF(tmp);
+ if (PyWeakref_GetRef(PyList_GetItem(surf->locklist, i), &tmp) < 0) {
+ Py_DECREF(tuple);
+ return NULL;
+ }
+ if (tmp == NULL) { /* dead lock owner: report None, as before */
+ tmp = Py_None;
+ Py_INCREF(tmp);
+ }
PyTuple_SetItem(tuple, i, tmp);
}
@@ -3444,9 +3450,15 @@
consumer_ref = internal->consumer_ref;
assert(consumer_ref && PyWeakref_CheckRef(consumer_ref));
- consumer = PyWeakref_GetObject(consumer_ref);
- if (consumer) {
- if (!pgSurface_UnlockBy((pgSurfaceObject *)view_p->obj, consumer)) {
+ if (PyWeakref_GetRef(consumer_ref, &consumer) < 0) {
+ PyErr_Clear();
+ }
+ else {
+ /* A dead consumer is passed as None, as PyWeakref_GetObject() did,
+ * so UnlockBy still purges its dead lock entry. */
+ if (!pgSurface_UnlockBy((pgSurfaceObject *)view_p->obj,
+ consumer ? consumer : Py_None)) {
PyErr_Clear();
}
+ Py_XDECREF(consumer);
}
Py_DECREF(consumer_ref);
--- a/src_c/surflock.c
+++ b/src_c/surflock.c
@@ -122,9 +122,14 @@
if (surf->locklist != NULL) {
PyObject *item, *ref;
+ int alive, match;
Py_ssize_t len = PyList_Size(surf->locklist);
while (--len >= 0 && !found) {
item = PyList_GetItem(surf->locklist, len);
- ref = PyWeakref_GetObject(item);
- if (ref == lockobj) {
+ if (PyWeakref_GetRef(item, &ref) < 0) {
+ return 0;
+ }
+ match = (ref == lockobj);
+ Py_XDECREF(ref);
+ if (match) {
if (PySequence_DelItem(surf->locklist, len) == -1) {
return 0;
@@ -140,6 +145,11 @@
while (--len >= 0) {
item = PyList_GetItem(surf->locklist, len);
- ref = PyWeakref_GetObject(item);
- if (ref == Py_None) {
+ alive = PyWeakref_GetRef(item, &ref);
+ if (alive < 0) {
+ noerror = 0;
+ continue;
+ }
+ Py_XDECREF(ref);
+ if (!alive) {
if (PySequence_DelItem(surf->locklist, len) == -1) {
noerror = 0;
--- a/test/rwobject_test.py
+++ b/test/rwobject_test.py
@@ -83,7 +83,10 @@
before = getrefcount(bpath)
bpath = encode_string(bpath)
- self.assertEqual(getrefcount(bpath), before)
+ if sys.version_info >= (3, 15):
+ self.assertEqual(getrefcount(bpath), before + 1)
+ else:
+ self.assertEqual(getrefcount(bpath), before)
bpath = encode_string(upath)
- if sys.version_info >= (3, 14):
+ if sys.version_info[:2] == (3, 14):
self.assertEqual(getrefcount(bpath), before - 1)
else: