Add free function for sudo Python module.
This reduces the amount of memory leaked on unload.
This commit is contained in:
@@ -23,7 +23,7 @@
|
|||||||
|
|
||||||
#include "sudo_python_module.h"
|
#include "sudo_python_module.h"
|
||||||
|
|
||||||
static PyTypeObject *sudo_type_ConvMessage;
|
PyTypeObject *sudo_type_ConvMessage;
|
||||||
|
|
||||||
static PyObject *
|
static PyObject *
|
||||||
_sudo_ConvMessage__Init(PyObject *py_self, PyObject *py_args, PyObject *py_kwargs)
|
_sudo_ConvMessage__Init(PyObject *py_self, PyObject *py_args, PyObject *py_kwargs)
|
||||||
|
@@ -130,7 +130,7 @@ static PyMethodDef _sudo_LogHandler_class_methods[] =
|
|||||||
int
|
int
|
||||||
sudo_module_set_default_loghandler()
|
sudo_module_set_default_loghandler()
|
||||||
{
|
{
|
||||||
debug_decl(sudo_module_register_loghandler, PYTHON_DEBUG_INTERNAL);
|
debug_decl(sudo_module_set_default_loghandler, PYTHON_DEBUG_INTERNAL);
|
||||||
|
|
||||||
PyObject *py_sudo, *py_logging_module = NULL, *py_logger = NULL,
|
PyObject *py_sudo, *py_logging_module = NULL, *py_logger = NULL,
|
||||||
*py_streamhandler = NULL, *py_class = NULL,
|
*py_streamhandler = NULL, *py_class = NULL,
|
||||||
|
@@ -64,7 +64,7 @@ _append_python_path(const char *module_dir)
|
|||||||
{
|
{
|
||||||
debug_decl(_append_python_path, PYTHON_DEBUG_PLUGIN_LOAD);
|
debug_decl(_append_python_path, PYTHON_DEBUG_PLUGIN_LOAD);
|
||||||
int rc = -1;
|
int rc = -1;
|
||||||
PyObject *py_sys_path = PySys_GetObject("path");
|
PyObject *py_sys_path = PySys_GetObject("path"); // borrowed
|
||||||
if (py_sys_path == NULL) {
|
if (py_sys_path == NULL) {
|
||||||
PyErr_Format(sudo_exc_SudoException, "Failed to get python 'path'");
|
PyErr_Format(sudo_exc_SudoException, "Failed to get python 'path'");
|
||||||
debug_return_int(rc);
|
debug_return_int(rc);
|
||||||
@@ -77,7 +77,7 @@ _append_python_path(const char *module_dir)
|
|||||||
Py_XDECREF(py_module_dir);
|
Py_XDECREF(py_module_dir);
|
||||||
debug_return_int(rc);
|
debug_return_int(rc);
|
||||||
}
|
}
|
||||||
Py_XDECREF(py_module_dir);
|
Py_DECREF(py_module_dir);
|
||||||
|
|
||||||
if (sudo_debug_needed(SUDO_DEBUG_INFO)) {
|
if (sudo_debug_needed(SUDO_DEBUG_INFO)) {
|
||||||
char *path = py_join_str_list(py_sys_path, ":");
|
char *path = py_join_str_list(py_sys_path, ":");
|
||||||
|
@@ -42,6 +42,9 @@ static PyObject *python_sudo_conversation(PyObject *py_self, PyObject *py_args,
|
|||||||
static PyObject *python_sudo_options_as_dict(PyObject *py_self, PyObject *py_args);
|
static PyObject *python_sudo_options_as_dict(PyObject *py_self, PyObject *py_args);
|
||||||
static PyObject *python_sudo_options_from_dict(PyObject *py_self, PyObject *py_args);
|
static PyObject *python_sudo_options_from_dict(PyObject *py_self, PyObject *py_args);
|
||||||
|
|
||||||
|
// Called on module teardown.
|
||||||
|
static void sudo_module_free(void *self);
|
||||||
|
|
||||||
static PyMethodDef sudo_methods[] = {
|
static PyMethodDef sudo_methods[] = {
|
||||||
{"debug", (PyCFunction)python_sudo_debug, METH_VARARGS, "Debug messages which can be saved to file in sudo.conf."},
|
{"debug", (PyCFunction)python_sudo_debug, METH_VARARGS, "Debug messages which can be saved to file in sudo.conf."},
|
||||||
{"log_info", (PyCFunction)python_sudo_log_info, METH_VARARGS | METH_KEYWORDS, "Display informational messages."},
|
{"log_info", (PyCFunction)python_sudo_log_info, METH_VARARGS | METH_KEYWORDS, "Display informational messages."},
|
||||||
@@ -62,7 +65,7 @@ static struct PyModuleDef sudo_module = {
|
|||||||
NULL, /* slots */
|
NULL, /* slots */
|
||||||
NULL, /* traverse */
|
NULL, /* traverse */
|
||||||
NULL, /* clear */
|
NULL, /* clear */
|
||||||
NULL /* free */
|
sudo_module_free
|
||||||
};
|
};
|
||||||
|
|
||||||
CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION
|
CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION
|
||||||
@@ -600,8 +603,29 @@ cleanup:
|
|||||||
Py_CLEAR(py_module);
|
Py_CLEAR(py_module);
|
||||||
Py_CLEAR(sudo_exc_SudoException);
|
Py_CLEAR(sudo_exc_SudoException);
|
||||||
Py_CLEAR(sudo_exc_PluginError);
|
Py_CLEAR(sudo_exc_PluginError);
|
||||||
|
Py_CLEAR(sudo_exc_PluginReject);
|
||||||
Py_CLEAR(sudo_exc_ConversationInterrupted);
|
Py_CLEAR(sudo_exc_ConversationInterrupted);
|
||||||
}
|
}
|
||||||
|
|
||||||
debug_return_ptr(py_module);
|
debug_return_ptr(py_module);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
sudo_module_free(void *self)
|
||||||
|
{
|
||||||
|
debug_decl(sudo_module_free, PYTHON_DEBUG_C_CALLS);
|
||||||
|
|
||||||
|
// Free exceptions
|
||||||
|
Py_CLEAR(sudo_exc_SudoException);
|
||||||
|
Py_CLEAR(sudo_exc_PluginError);
|
||||||
|
Py_CLEAR(sudo_exc_PluginReject);
|
||||||
|
Py_CLEAR(sudo_exc_ConversationInterrupted);
|
||||||
|
|
||||||
|
// Free base plugin
|
||||||
|
Py_CLEAR(sudo_type_Plugin);
|
||||||
|
|
||||||
|
// Free conversation message type
|
||||||
|
Py_CLEAR(sudo_type_ConvMessage);
|
||||||
|
|
||||||
|
debug_return;
|
||||||
|
}
|
||||||
|
@@ -29,6 +29,7 @@ extern PyObject *sudo_exc_PluginReject; // a reject with message
|
|||||||
extern PyObject *sudo_exc_PluginError; // an error with message
|
extern PyObject *sudo_exc_PluginError; // an error with message
|
||||||
|
|
||||||
extern PyTypeObject *sudo_type_Plugin;
|
extern PyTypeObject *sudo_type_Plugin;
|
||||||
|
extern PyTypeObject *sudo_type_ConvMessage;
|
||||||
|
|
||||||
PyObject *sudo_module_create_class(const char *class_name, PyMethodDef *class_methods,
|
PyObject *sudo_module_create_class(const char *class_name, PyMethodDef *class_methods,
|
||||||
PyObject *base_class);
|
PyObject *base_class);
|
||||||
|
Reference in New Issue
Block a user