]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-111789: Use PyDict_GetItemRef() in Objects/ (GH-111827)
authorSerhiy Storchaka <storchaka@gmail.com>
Tue, 14 Nov 2023 09:25:39 +0000 (11:25 +0200)
committerGitHub <noreply@github.com>
Tue, 14 Nov 2023 09:25:39 +0000 (11:25 +0200)
Objects/abstract.c
Objects/funcobject.c
Objects/moduleobject.c
Objects/object.c
Objects/typeobject.c

index b6762893b8fd5d213a1b53dc5fb457e6a918fe7d..43842fbdd6aeddff0f35650062fc747f69469ecf 100644 (file)
@@ -204,12 +204,7 @@ int
 PyMapping_GetOptionalItem(PyObject *obj, PyObject *key, PyObject **result)
 {
     if (PyDict_CheckExact(obj)) {
-        *result = PyDict_GetItemWithError(obj, key);  /* borrowed */
-        if (*result) {
-            Py_INCREF(*result);
-            return 1;
-        }
-        return PyErr_Occurred() ? -1 : 0;
+        return PyDict_GetItemRef(obj, key, result);
     }
 
     *result = PyObject_GetItem(obj, key);
index e2fd6f99e451b3e40ff0263dfab9a69596cd4403..4d88dd2229295dc5dc6fa2b81ceea36e01a55be7 100644 (file)
@@ -92,8 +92,8 @@ PyFunction_ClearWatcher(int watcher_id)
 PyFunctionObject *
 _PyFunction_FromConstructor(PyFrameConstructor *constr)
 {
-    PyObject *module = Py_XNewRef(PyDict_GetItemWithError(constr->fc_globals, &_Py_ID(__name__)));
-    if (!module && PyErr_Occurred()) {
+    PyObject *module;
+    if (PyDict_GetItemRef(constr->fc_globals, &_Py_ID(__name__), &module) < 0) {
         return NULL;
     }
 
@@ -158,12 +158,11 @@ PyFunction_NewWithQualName(PyObject *code, PyObject *globals, PyObject *qualname
     Py_INCREF(doc);
 
     // __module__: Use globals['__name__'] if it exists, or NULL.
-    PyObject *module = PyDict_GetItemWithError(globals, &_Py_ID(__name__));
+    PyObject *module;
     PyObject *builtins = NULL;
-    if (module == NULL && _PyErr_Occurred(tstate)) {
+    if (PyDict_GetItemRef(globals, &_Py_ID(__name__), &module) < 0) {
         goto error;
     }
-    Py_XINCREF(module);
 
     builtins = _PyEval_BuiltinsFromGlobals(tstate, globals); // borrowed ref
     if (builtins == NULL) {
index a3d55b76aa10127ce8b57e87e49d89bef2136abd..bba77ce8ab7e7b1f64489b99e8bea0bb0acd649c 100644 (file)
@@ -522,6 +522,7 @@ PyModule_GetNameObject(PyObject *mod)
     }
     PyObject *name;
     if (PyDict_GetItemRef(dict, &_Py_ID(__name__), &name) <= 0) {
+        // error or not found
         goto error;
     }
     if (!PyUnicode_Check(name)) {
@@ -562,6 +563,7 @@ PyModule_GetFilenameObject(PyObject *mod)
     }
     PyObject *fileobj;
     if (PyDict_GetItemRef(dict, &_Py_ID(__file__), &fileobj) <= 0) {
+        // error or not found
         goto error;
     }
     if (!PyUnicode_Check(fileobj)) {
@@ -816,28 +818,28 @@ _Py_module_getattro_impl(PyModuleObject *m, PyObject *name, int suppress)
         PyErr_Clear();
     }
     assert(m->md_dict != NULL);
-    getattr = PyDict_GetItemWithError(m->md_dict, &_Py_ID(__getattr__));
+    if (PyDict_GetItemRef(m->md_dict, &_Py_ID(__getattr__), &getattr) < 0) {
+        return NULL;
+    }
     if (getattr) {
         PyObject *result = PyObject_CallOneArg(getattr, name);
         if (result == NULL && suppress == 1 && PyErr_ExceptionMatches(PyExc_AttributeError)) {
             // suppress AttributeError
             PyErr_Clear();
         }
+        Py_DECREF(getattr);
         return result;
     }
-    if (PyErr_Occurred()) {
+    if (PyDict_GetItemRef(m->md_dict, &_Py_ID(__name__), &mod_name) < 0) {
         return NULL;
     }
-    mod_name = PyDict_GetItemWithError(m->md_dict, &_Py_ID(__name__));
     if (mod_name && PyUnicode_Check(mod_name)) {
-        Py_INCREF(mod_name);
-        PyObject *spec = PyDict_GetItemWithError(m->md_dict, &_Py_ID(__spec__));
-        if (spec == NULL && PyErr_Occurred()) {
+        PyObject *spec;
+        if (PyDict_GetItemRef(m->md_dict, &_Py_ID(__spec__), &spec) < 0) {
             Py_DECREF(mod_name);
             return NULL;
         }
         if (suppress != 1) {
-            Py_XINCREF(spec);
             if (_PyModuleSpec_IsInitializing(spec)) {
                 PyErr_Format(PyExc_AttributeError,
                                 "partially initialized "
@@ -856,14 +858,12 @@ _Py_module_getattro_impl(PyModuleObject *m, PyObject *name, int suppress)
                                 "module '%U' has no attribute '%U'",
                                 mod_name, name);
             }
-            Py_XDECREF(spec);
         }
+        Py_XDECREF(spec);
         Py_DECREF(mod_name);
         return NULL;
     }
-    else if (PyErr_Occurred()) {
-        return NULL;
-    }
+    Py_XDECREF(mod_name);
     if (suppress != 1) {
         PyErr_Format(PyExc_AttributeError,
                     "module has no attribute '%U'", name);
@@ -957,11 +957,8 @@ module_get_annotations(PyModuleObject *m, void *Py_UNUSED(ignored))
         return NULL;
     }
 
-    PyObject *annotations = PyDict_GetItemWithError(dict, &_Py_ID(__annotations__));
-    if (annotations) {
-        Py_INCREF(annotations);
-    }
-    else if (!PyErr_Occurred()) {
+    PyObject *annotations;
+    if (PyDict_GetItemRef(dict, &_Py_ID(__annotations__), &annotations) == 0) {
         annotations = PyDict_New();
         if (annotations) {
             int result = PyDict_SetItem(
index 1003029f0ed722168e695f749f831e9e1fb7eb4f..1f5b2b4f79e5fa91f2b2eb8d8ce6572d6a3bd915 100644 (file)
@@ -1490,19 +1490,14 @@ _PyObject_GetMethod(PyObject *obj, PyObject *name, PyObject **method)
     }
     if (dict != NULL) {
         Py_INCREF(dict);
-        PyObject *attr = PyDict_GetItemWithError(dict, name);
-        if (attr != NULL) {
-            *method = Py_NewRef(attr);
+        if (PyDict_GetItemRef(dict, name, method) != 0) {
+            // found or error
             Py_DECREF(dict);
             Py_XDECREF(descr);
             return 0;
         }
+        // not found
         Py_DECREF(dict);
-
-        if (PyErr_Occurred()) {
-            Py_XDECREF(descr);
-            return 0;
-        }
     }
 
     if (meth_found) {
@@ -1607,21 +1602,17 @@ _PyObject_GenericGetAttrWithDict(PyObject *obj, PyObject *name,
     }
     if (dict != NULL) {
         Py_INCREF(dict);
-        res = PyDict_GetItemWithError(dict, name);
+        int rc = PyDict_GetItemRef(dict, name, &res);
+        Py_DECREF(dict);
         if (res != NULL) {
-            Py_INCREF(res);
-            Py_DECREF(dict);
             goto done;
         }
-        else {
-            Py_DECREF(dict);
-            if (PyErr_Occurred()) {
-                if (suppress && PyErr_ExceptionMatches(PyExc_AttributeError)) {
-                    PyErr_Clear();
-                }
-                else {
-                    goto done;
-                }
+        else if (rc < 0) {
+            if (suppress && PyErr_ExceptionMatches(PyExc_AttributeError)) {
+                PyErr_Clear();
+            }
+            else {
+                goto done;
             }
         }
     }
index c1a4cb9aaeacfd08cd2e19182c1a30b84607aabf..4464b5af8cd15be1b3d5153f97a81a30ac974946 100644 (file)
@@ -1092,14 +1092,9 @@ type_module(PyTypeObject *type, void *context)
 
     if (type->tp_flags & Py_TPFLAGS_HEAPTYPE) {
         PyObject *dict = lookup_tp_dict(type);
-        mod = PyDict_GetItemWithError(dict, &_Py_ID(__module__));
-        if (mod == NULL) {
-            if (!PyErr_Occurred()) {
-                PyErr_Format(PyExc_AttributeError, "__module__");
-            }
-            return NULL;
+        if (PyDict_GetItemRef(dict, &_Py_ID(__module__), &mod) == 0) {
+            PyErr_Format(PyExc_AttributeError, "__module__");
         }
-        Py_INCREF(mod);
     }
     else {
         const char *s = strrchr(type->tp_name, '.');
@@ -1134,17 +1129,16 @@ type_abstractmethods(PyTypeObject *type, void *context)
     PyObject *mod = NULL;
     /* type itself has an __abstractmethods__ descriptor (this). Don't return
        that. */
-    if (type != &PyType_Type) {
-        PyObject *dict = lookup_tp_dict(type);
-        mod = PyDict_GetItemWithError(dict, &_Py_ID(__abstractmethods__));
+    if (type == &PyType_Type) {
+        PyErr_SetObject(PyExc_AttributeError, &_Py_ID(__abstractmethods__));
     }
-    if (!mod) {
-        if (!PyErr_Occurred()) {
+    else {
+        PyObject *dict = lookup_tp_dict(type);
+        if (PyDict_GetItemRef(dict, &_Py_ID(__abstractmethods__), &mod) == 0) {
             PyErr_SetObject(PyExc_AttributeError, &_Py_ID(__abstractmethods__));
         }
-        return NULL;
     }
-    return Py_NewRef(mod);
+    return mod;
 }
 
 static int
@@ -1435,18 +1429,14 @@ type_get_doc(PyTypeObject *type, void *context)
         return _PyType_GetDocFromInternalDoc(type->tp_name, type->tp_doc);
     }
     PyObject *dict = lookup_tp_dict(type);
-    result = PyDict_GetItemWithError(dict, &_Py_ID(__doc__));
-    if (result == NULL) {
-        if (!PyErr_Occurred()) {
-            result = Py_NewRef(Py_None);
-        }
-    }
-    else if (Py_TYPE(result)->tp_descr_get) {
-        result = Py_TYPE(result)->tp_descr_get(result, NULL,
-                                               (PyObject *)type);
+    if (PyDict_GetItemRef(dict, &_Py_ID(__doc__), &result) == 0) {
+        result = Py_NewRef(Py_None);
     }
-    else {
-        Py_INCREF(result);
+    else if (result) {
+        descrgetfunc descr_get = Py_TYPE(result)->tp_descr_get;
+        if (descr_get) {
+            Py_SETREF(result, descr_get(result, NULL, (PyObject *)type));
+        }
     }
     return result;
 }
@@ -1477,16 +1467,16 @@ type_get_annotations(PyTypeObject *type, void *context)
 
     PyObject *annotations;
     PyObject *dict = lookup_tp_dict(type);
-    annotations = PyDict_GetItemWithError(dict, &_Py_ID(__annotations__));
+    if (PyDict_GetItemRef(dict, &_Py_ID(__annotations__), &annotations) < 0) {
+        return NULL;
+    }
     if (annotations) {
-        if (Py_TYPE(annotations)->tp_descr_get) {
-            annotations = Py_TYPE(annotations)->tp_descr_get(
-                    annotations, NULL, (PyObject *)type);
-        } else {
-            Py_INCREF(annotations);
+        descrgetfunc get = Py_TYPE(annotations)->tp_descr_get;
+        if (get) {
+            Py_SETREF(annotations, get(annotations, NULL, (PyObject *)type));
         }
     }
-    else if (!PyErr_Occurred()) {
+    else {
         annotations = PyDict_New();
         if (annotations) {
             int result = PyDict_SetItem(
@@ -1533,16 +1523,11 @@ type_set_annotations(PyTypeObject *type, PyObject *value, void *context)
 static PyObject *
 type_get_type_params(PyTypeObject *type, void *context)
 {
-    PyObject *params = PyDict_GetItemWithError(lookup_tp_dict(type), &_Py_ID(__type_params__));
-
-    if (params) {
-        return Py_NewRef(params);
-    }
-    if (PyErr_Occurred()) {
-        return NULL;
+    PyObject *params;
+    if (PyDict_GetItemRef(lookup_tp_dict(type), &_Py_ID(__type_params__), &params) == 0) {
+        return PyTuple_New(0);
     }
-
-    return PyTuple_New(0);
+    return params;
 }
 
 static int
@@ -3436,18 +3421,13 @@ type_new_set_module(PyTypeObject *type)
         return 0;
     }
 
-    PyObject *module = PyDict_GetItemWithError(globals, &_Py_ID(__name__));
-    if (module == NULL) {
-        if (PyErr_Occurred()) {
-            return -1;
-        }
-        return 0;
-    }
-
-    if (PyDict_SetItem(dict, &_Py_ID(__module__), module) < 0) {
-        return -1;
+    PyObject *module;
+    r = PyDict_GetItemRef(globals, &_Py_ID(__name__), &module);
+    if (module) {
+        r = PyDict_SetItem(dict, &_Py_ID(__module__), module);
+        Py_DECREF(module);
     }
-    return 0;
+    return r;
 }
 
 
@@ -3458,23 +3438,24 @@ type_new_set_ht_name(PyTypeObject *type)
 {
     PyHeapTypeObject *et = (PyHeapTypeObject *)type;
     PyObject *dict = lookup_tp_dict(type);
-    PyObject *qualname = PyDict_GetItemWithError(dict, &_Py_ID(__qualname__));
+    PyObject *qualname;
+    if (PyDict_GetItemRef(dict, &_Py_ID(__qualname__), &qualname) < 0) {
+        return -1;
+    }
     if (qualname != NULL) {
         if (!PyUnicode_Check(qualname)) {
             PyErr_Format(PyExc_TypeError,
                     "type __qualname__ must be a str, not %s",
                     Py_TYPE(qualname)->tp_name);
+            Py_DECREF(qualname);
             return -1;
         }
-        et->ht_qualname = Py_NewRef(qualname);
+        et->ht_qualname = qualname;
         if (PyDict_DelItem(dict, &_Py_ID(__qualname__)) < 0) {
             return -1;
         }
     }
     else {
-        if (PyErr_Occurred()) {
-            return -1;
-        }
         et->ht_qualname = Py_NewRef(et->ht_name);
     }
     return 0;
@@ -5888,24 +5869,22 @@ _PyType_GetSlotNames(PyTypeObject *cls)
 
     /* Get the slot names from the cache in the class if possible. */
     PyObject *dict = lookup_tp_dict(cls);
-    slotnames = PyDict_GetItemWithError(dict, &_Py_ID(__slotnames__));
+    if (PyDict_GetItemRef(dict, &_Py_ID(__slotnames__), &slotnames) < 0) {
+        return NULL;
+    }
     if (slotnames != NULL) {
         if (slotnames != Py_None && !PyList_Check(slotnames)) {
             PyErr_Format(PyExc_TypeError,
                          "%.200s.__slotnames__ should be a list or None, "
                          "not %.200s",
                          cls->tp_name, Py_TYPE(slotnames)->tp_name);
+            Py_DECREF(slotnames);
             return NULL;
         }
-        return Py_NewRef(slotnames);
-    }
-    else {
-        if (PyErr_Occurred()) {
-            return NULL;
-        }
-        /* The class does not have the slot names cached yet. */
+        return slotnames;
     }
 
+    /* The class does not have the slot names cached yet. */
     copyreg = import_copyreg();
     if (copyreg == NULL)
         return NULL;
@@ -10264,23 +10243,18 @@ _super_lookup_descr(PyTypeObject *su_type, PyTypeObject *su_obj_type, PyObject *
         return NULL;
 
     /* keep a strong reference to mro because su_obj_type->tp_mro can be
-       replaced during PyDict_GetItemWithError(dict, name)  */
+       replaced during PyDict_GetItemRef(dict, name, &res)  */
     Py_INCREF(mro);
     do {
         PyObject *obj = PyTuple_GET_ITEM(mro, i);
         PyObject *dict = lookup_tp_dict(_PyType_CAST(obj));
         assert(dict != NULL && PyDict_Check(dict));
 
-        res = PyDict_GetItemWithError(dict, name);
-        if (res != NULL) {
-            Py_INCREF(res);
+        if (PyDict_GetItemRef(dict, name, &res) != 0) {
+            // found or error
             Py_DECREF(mro);
             return res;
         }
-        else if (PyErr_Occurred()) {
-            Py_DECREF(mro);
-            return NULL;
-        }
 
         i++;
     } while (i < n);