]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-105927: _ctypes use PyWeakref_GetRef() (#105964)
authorVictor Stinner <vstinner@python.org>
Wed, 21 Jun 2023 14:34:27 +0000 (16:34 +0200)
committerGitHub <noreply@github.com>
Wed, 21 Jun 2023 14:34:27 +0000 (16:34 +0200)
Rename PyDict_GetItemProxy() to _PyDict_GetItemProxy() and mark it as
static. _PyDict_GetItemProxy() now returns a strong reference,
instead of a borrowed reference: replace PyWeakref_GET_OBJECT() with
_PyWeakref_GET_REF().

Modules/_ctypes/_ctypes.c

index 534ef8c1d6cf8f4b9e4bc027c09036d266006baf..840d0df85e9c87e85de8b56f90449651868c6e93 100644 (file)
@@ -238,20 +238,29 @@ PyDict_SetItemProxy(PyObject *dict, PyObject *key, PyObject *item)
     return result;
 }
 
-PyObject *
-PyDict_GetItemProxy(PyObject *dict, PyObject *key)
+static int
+_PyDict_GetItemProxy(PyObject *dict, PyObject *key, PyObject **presult)
 {
-    PyObject *result;
     PyObject *item = PyDict_GetItemWithError(dict, key);
+    if (item == NULL) {
+        if (PyErr_Occurred()) {
+            return -1;
+        }
+        *presult = NULL;
+        return 0;
+    }
 
-    if (item == NULL)
-        return NULL;
-    if (!PyWeakref_CheckProxy(item))
-        return item;
-    result = PyWeakref_GET_OBJECT(item);
-    if (result == Py_None)
-        return NULL;
-    return result;
+    if (!PyWeakref_CheckProxy(item)) {
+        *presult = Py_NewRef(item);
+        return 0;
+    }
+    PyObject *ref;
+    if (PyWeakref_GetRef(item, &ref) < 0) {
+        return -1;
+    }
+    // ref is NULL if the referenced object was destroyed
+    *presult = ref;
+    return 0;
 }
 
 /******************************************************************/
@@ -4832,7 +4841,6 @@ PyCArrayType_from_ctype(PyObject *itemtype, Py_ssize_t length)
 {
     static PyObject *cache;
     PyObject *key;
-    PyObject *result;
     char name[256];
     PyObject *len;
 
@@ -4848,15 +4856,15 @@ PyCArrayType_from_ctype(PyObject *itemtype, Py_ssize_t length)
     Py_DECREF(len);
     if (!key)
         return NULL;
-    result = PyDict_GetItemProxy(cache, key);
-    if (result) {
-        Py_INCREF(result);
+
+    PyObject *result;
+    if (_PyDict_GetItemProxy(cache, key, &result) < 0) {
         Py_DECREF(key);
-        return result;
+        return NULL;
     }
-    else if (PyErr_Occurred()) {
+    if (result) {
         Py_DECREF(key);
-        return NULL;
+        return result;
     }
 
     if (!PyType_Check(itemtype)) {