[Python-Dev] Tackling circular dependencies in 2.0?

M.-A. Lemburg mal@lemburg.com
Tue, 21 Sep 1999 18:23:53 +0200


Skip Montanaro wrote:
> 
>     Marc> BTW, I usually use an instrumented Python interpreter to track
>     Marc> down circular references: ...
> 
>     Marc> If anyone is interested I can post the patch (against Python 1.5).
> 
> That would be interesting to look at.  I found my latest circular reference
> by building Python with Py_DEBUG defined and trudging through the output at
> the end.

Here it is:

--- Objects/orig/classobject.c	Thu Jan  1 20:39:04 1998
+++ Objects/classobject.c	Sat Aug  8 21:38:57 1998
@@ -403,10 +588,37 @@ PyInstance_New(class, arg, kw)
 				inst = NULL;
 			}
 			Py_DECREF(res);
 		}
 	}
+	/* sys.traceinstances hook */
+	if (Py_DebugFlag && inst) {
+		PyObject *fct;
+		
+		fct = PySys_GetObject("traceinstances");
+		if (fct) {
+			PyObject *v,*arg;
+			PyObject *error_type, *error_value, *error_traceback;
+
+			/* Save and clear any exception */
+			PyErr_Fetch(&error_type,&error_value, 
+				    &error_traceback);
+			PyErr_Clear();
+			arg = Py_BuildValue("(sO)","create",(PyObject *)inst);
+			v = PyEval_CallObject(fct,arg);
+			Py_DECREF(arg);
+			if (!v) {
+				PyErr_Print();
+				PyErr_Clear();
+			}
+			else
+				Py_DECREF(v);
+			/* Restore exception state */
+			PyErr_Restore(error_type,error_value,
+				      error_traceback);
+		}
+	}
 	return (PyObject *)inst;
 }
 
 /* Instance methods */
 
@@ -460,10 +672,31 @@ instance_dealloc(inst)
 		}
 		else
 			Py_DECREF(res);
 		Py_DECREF(del);
 	}
+	/* sys.traceinstances hook */
+	if (Py_DebugFlag) {
+		PyObject *fct;
+		
+		fct = PySys_GetObject("traceinstances");
+		if (fct) {
+			PyObject *v,*arg;
+
+			/* Clear any previous exception */
+			PyErr_Clear();
+			arg = Py_BuildValue("(sO)","delete",(PyObject *)inst);
+			v = PyEval_CallObject(fct,arg);
+			Py_DECREF(arg);
+			if (!v) {
+				PyErr_Print();
+				PyErr_Clear();
+			}
+			else
+				Py_DECREF(v);
+		}
+	}
 	/* Restore the saved exception and undo the temporary revival */
 	PyErr_Restore(error_type, error_value, error_traceback);
 	/* Can't use DECREF here, it would cause a recursive call */
 	if (--inst->ob_refcnt > 0) {
 #ifdef COUNT_ALLOCS


-- 
Marc-Andre Lemburg
______________________________________________________________________
Y2000:                                                   101 days left
Business:                                      http://www.lemburg.com/
Python Pages:                           http://www.lemburg.com/python/