summaryrefslogtreecommitdiff
path: root/Modules/_tracemalloc.c
diff options
context:
space:
mode:
authorVictor Stinner <victor.stinner@gmail.com>2013-12-01 10:03:26 +0100
committerVictor Stinner <victor.stinner@gmail.com>2013-12-01 10:03:26 +0100
commit7049e92e939bfdb1d9e34a8d3a5d1611d8fd1a4a (patch)
tree616d8d2a4ca7e0f8742d4cf8f17150bce9eb816e /Modules/_tracemalloc.c
parente90b63bb003a4339ac5243d7728fbd2792d4fe8f (diff)
downloadcpython-7049e92e939bfdb1d9e34a8d3a5d1611d8fd1a4a.tar.gz
Closes #19831: Stop tracemalloc later at Python shutdown to be able to use
tracemalloc in objects destructor Replace atexit handler with an harcoded C function _PyTraceMalloc_Fini().
Diffstat (limited to 'Modules/_tracemalloc.c')
-rw-r--r--Modules/_tracemalloc.c77
1 files changed, 10 insertions, 67 deletions
diff --git a/Modules/_tracemalloc.c b/Modules/_tracemalloc.c
index 2b2222ea87..7b88a74594 100644
--- a/Modules/_tracemalloc.c
+++ b/Modules/_tracemalloc.c
@@ -9,7 +9,6 @@
/* Forward declaration */
static void tracemalloc_stop(void);
-static int tracemalloc_atexit_register(void);
static void* raw_malloc(size_t size);
static void raw_free(void *ptr);
@@ -36,9 +35,6 @@ static struct {
TRACEMALLOC_FINALIZED
} initialized;
- /* atexit handler registered? */
- int atexit_registered;
-
/* Is tracemalloc tracing memory allocations?
Variable protected by the GIL */
int tracing;
@@ -46,7 +42,7 @@ static struct {
/* limit of the number of frames in a traceback, 1 by default.
Variable protected by the GIL. */
int max_nframe;
-} tracemalloc_config = {TRACEMALLOC_NOT_INITIALIZED, 0, 0, 1};
+} tracemalloc_config = {TRACEMALLOC_NOT_INITIALIZED, 0, 1};
#if defined(TRACE_RAW_MALLOC) && defined(WITH_THREAD)
/* This lock is needed because tracemalloc_free() is called without
@@ -802,9 +798,6 @@ tracemalloc_start(int max_nframe)
return 0;
}
- if (tracemalloc_atexit_register() < 0)
- return -1;
-
assert(1 <= max_nframe && max_nframe <= MAX_NFRAME);
tracemalloc_config.max_nframe = max_nframe;
@@ -1140,65 +1133,6 @@ py_tracemalloc_get_object_traceback(PyObject *self, PyObject *obj)
return traceback_to_pyobject(trace.traceback, NULL);
}
-static PyObject*
-tracemalloc_atexit(PyObject *self)
-{
-#ifdef WITH_THREAD
- assert(PyGILState_Check());
-#endif
- tracemalloc_deinit();
- Py_RETURN_NONE;
-}
-
-static PyMethodDef atexit_method = {
- "_atexit", (PyCFunction)tracemalloc_atexit, METH_NOARGS, NULL};
-
-static int
-tracemalloc_atexit_register(void)
-{
- PyObject *method = NULL, *atexit = NULL, *func = NULL;
- PyObject *result;
- int ret = -1;
-
- if (tracemalloc_config.atexit_registered)
- return 0;
- tracemalloc_config.atexit_registered = 1;
-
- /* private functions */
- method = PyCFunction_New(&atexit_method, NULL);
- if (method == NULL)
- goto done;
-
- atexit = PyImport_ImportModule("atexit");
- if (atexit == NULL) {
- if (!PyErr_Warn(PyExc_ImportWarning,
- "atexit module is missing: "
- "cannot automatically disable tracemalloc at exit"))
- {
- PyErr_Clear();
- return 0;
- }
- goto done;
- }
-
- func = PyObject_GetAttrString(atexit, "register");
- if (func == NULL)
- goto done;
-
- result = PyObject_CallFunction(func, "O", method);
- if (result == NULL)
- goto done;
- Py_DECREF(result);
-
- ret = 0;
-
-done:
- Py_XDECREF(method);
- Py_XDECREF(func);
- Py_XDECREF(atexit);
- return ret;
-}
-
PyDoc_STRVAR(tracemalloc_start_doc,
"start(nframe: int=1)\n"
"\n"
@@ -1439,3 +1373,12 @@ _PyTraceMalloc_Init(void)
return tracemalloc_start(nframe);
}
+void
+_PyTraceMalloc_Fini(void)
+{
+#ifdef WITH_THREAD
+ assert(PyGILState_Check());
+#endif
+ tracemalloc_deinit();
+}
+