diff options
author | Gregory P. Smith <greg@mad-scientist.com> | 2003-11-02 08:06:29 (GMT) |
---|---|---|
committer | Gregory P. Smith <greg@mad-scientist.com> | 2003-11-02 08:06:29 (GMT) |
commit | e2767171133ead86ec3aacc205d1d8365a0a2d07 (patch) | |
tree | 8bbf6e6a28584dc14d3165ab23e1c8c71072fd1e /Modules | |
parent | 54a831bef74fc2213dc2a8467236a5f481957d5c (diff) | |
download | cpython-e2767171133ead86ec3aacc205d1d8365a0a2d07.zip cpython-e2767171133ead86ec3aacc205d1d8365a0a2d07.tar.gz cpython-e2767171133ead86ec3aacc205d1d8365a0a2d07.tar.bz2 |
Fix a tuple memory leak when raising DB, DBEnv and DBCursor "object
has been closed" exceptions.
Adds a DBCursorClosedError exception in the closed cursor case for
future use in fixing the legacy bsddb interface deadlock problems
due to its use of cursors with DB_INIT_LOCK | DB_THREAD support
enabled.
Diffstat (limited to 'Modules')
-rw-r--r-- | Modules/_bsddb.c | 32 |
1 files changed, 15 insertions, 17 deletions
diff --git a/Modules/_bsddb.c b/Modules/_bsddb.c index e705526..6cf733f 100644 --- a/Modules/_bsddb.c +++ b/Modules/_bsddb.c @@ -148,6 +148,7 @@ static PyInterpreterState* _db_interpreterState = NULL; /* Exceptions */ static PyObject* DBError; /* Base class, all others derive from this */ +static PyObject* DBCursorClosedError; /* raised when trying to use a closed cursor object */ static PyObject* DBKeyEmptyError; /* DB_KEYEMPTY */ static PyObject* DBKeyExistError; /* DB_KEYEXIST */ static PyObject* DBLockDeadlockError; /* DB_LOCK_DEADLOCK */ @@ -258,27 +259,23 @@ staticforward PyTypeObject DB_Type, DBCursor_Type, DBEnv_Type, DBTxn_Type, DBLoc #define RETURN_NONE() Py_INCREF(Py_None); return Py_None; -#define CHECK_DB_NOT_CLOSED(dbobj) \ - if (dbobj->db == NULL) { \ - PyErr_SetObject(DBError, Py_BuildValue("(is)", 0, \ - "DB object has been closed")); \ - return NULL; \ +#define _CHECK_OBJECT_NOT_CLOSED(nonNull, pyErrObj, name) \ + if ((nonNull) == NULL) { \ + PyObject *errTuple = NULL; \ + errTuple = Py_BuildValue("(is)", 0, #name " object has been closed"); \ + PyErr_SetObject((pyErrObj), errTuple); \ + Py_DECREF(errTuple); \ + return NULL; \ } -#define CHECK_ENV_NOT_CLOSED(env) \ - if (env->db_env == NULL) { \ - PyErr_SetObject(DBError, Py_BuildValue("(is)", 0, \ - "DBEnv object has been closed"));\ - return NULL; \ - } +#define CHECK_DB_NOT_CLOSED(dbobj) \ + _CHECK_OBJECT_NOT_CLOSED(dbobj->db, DBError, DB) -#define CHECK_CURSOR_NOT_CLOSED(curs) \ - if (curs->dbc == NULL) { \ - PyErr_SetObject(DBError, Py_BuildValue("(is)", 0, \ - "DBCursor object has been closed"));\ - return NULL; \ - } +#define CHECK_ENV_NOT_CLOSED(env) \ + _CHECK_OBJECT_NOT_CLOSED(env->db_env, DBError, DBEnv) +#define CHECK_CURSOR_NOT_CLOSED(curs) \ + _CHECK_OBJECT_NOT_CLOSED(curs->dbc, DBCursorClosedError, DBCursor) #define CHECK_DBFLAG(mydb, flag) (((mydb)->flags & (flag)) || \ @@ -4717,6 +4714,7 @@ DL_EXPORT(void) init_bsddb(void) #if !INCOMPLETE_IS_WARNING MAKE_EX(DBIncompleteError); #endif + MAKE_EX(DBCursorClosedError); MAKE_EX(DBKeyEmptyError); MAKE_EX(DBKeyExistError); MAKE_EX(DBLockDeadlockError); |