summaryrefslogtreecommitdiffstats
path: root/Objects/object.c
diff options
context:
space:
mode:
authorVictor Stinner <vstinner@redhat.com>2019-04-12 19:51:34 (GMT)
committerGitHub <noreply@github.com>2019-04-12 19:51:34 (GMT)
commit0fc91eef34a1d9194904fa093c9fbd711af0f26c (patch)
treebeec907827203135c5c5baa9303fcb27776088a3 /Objects/object.c
parent23a683adf803eef405d248cc9c2a7eb08a7300e2 (diff)
downloadcpython-0fc91eef34a1d9194904fa093c9fbd711af0f26c.zip
cpython-0fc91eef34a1d9194904fa093c9fbd711af0f26c.tar.gz
cpython-0fc91eef34a1d9194904fa093c9fbd711af0f26c.tar.bz2
bpo-36389: Add _PyObject_CheckConsistency() function (GH-12803)
Add a new _PyObject_CheckConsistency() function which can be used to help debugging. The function is available in release mode. Add a 'check_content' parameter to _PyDict_CheckConsistency().
Diffstat (limited to 'Objects/object.c')
-rw-r--r--Objects/object.c31
1 files changed, 30 insertions, 1 deletions
diff --git a/Objects/object.c b/Objects/object.c
index 3fad73c..e7ec7ae 100644
--- a/Objects/object.c
+++ b/Objects/object.c
@@ -2,6 +2,7 @@
/* Generic object operations; and implementation of None */
#include "Python.h"
+#include "pycore_object.h"
#include "pycore_pystate.h"
#include "pycore_context.h"
#include "frameobject.h"
@@ -19,6 +20,28 @@ _Py_IDENTIFIER(__bytes__);
_Py_IDENTIFIER(__dir__);
_Py_IDENTIFIER(__isabstractmethod__);
+
+int
+_PyObject_CheckConsistency(PyObject *op, int check_content)
+{
+ _PyObject_ASSERT(op, op != NULL);
+ _PyObject_ASSERT(op, !_PyObject_IsFreed(op));
+ _PyObject_ASSERT(op, Py_REFCNT(op) >= 1);
+
+ PyTypeObject *type = op->ob_type;
+ _PyObject_ASSERT(op, type != NULL);
+ _PyType_CheckConsistency(type);
+
+ if (PyUnicode_Check(op)) {
+ _PyUnicode_CheckConsistency(op, check_content);
+ }
+ else if (PyDict_Check(op)) {
+ _PyDict_CheckConsistency(op, check_content);
+ }
+ return 1;
+}
+
+
#ifdef Py_REF_DEBUG
Py_ssize_t _Py_RefTotal;
@@ -2136,7 +2159,13 @@ _PyObject_AssertFailed(PyObject *obj, const char *expr, const char *msg,
else if (_PyObject_IsFreed(obj)) {
/* It seems like the object memory has been freed:
don't access it to prevent a segmentation fault. */
- fprintf(stderr, "<Freed object>\n");
+ fprintf(stderr, "<object: freed>\n");
+ }
+ else if (Py_TYPE(obj) == NULL) {
+ fprintf(stderr, "<object: ob_type=NULL>\n");
+ }
+ else if (_PyObject_IsFreed((PyObject *)Py_TYPE(obj))) {
+ fprintf(stderr, "<object: freed type %p>\n", Py_TYPE(obj));
}
else {
/* Diplay the traceback where the object has been allocated.