mirror of
https://github.com/isar/libmdbx.git
synced 2024-12-30 01:34:14 +08:00
mdbx: adds signatures to detect ABI mixup.
This commit is contained in:
parent
68171d5f5d
commit
dc3256e91c
6
lmdb.h
6
lmdb.h
@ -774,7 +774,7 @@ int mdb_env_sync(MDB_env *env, int force);
|
|||||||
*/
|
*/
|
||||||
void mdb_env_close(MDB_env *env);
|
void mdb_env_close(MDB_env *env);
|
||||||
#if MDBX_MODE_ENABLED
|
#if MDBX_MODE_ENABLED
|
||||||
void mdbx_env_close_ex(MDB_env *env, int dont_sync);
|
int mdbx_env_close_ex(MDB_env *env, int dont_sync);
|
||||||
#endif /* MDBX_MODE_ENABLED */
|
#endif /* MDBX_MODE_ENABLED */
|
||||||
|
|
||||||
/** @brief Set environment flags.
|
/** @brief Set environment flags.
|
||||||
@ -1058,7 +1058,7 @@ int mdb_txn_commit(MDB_txn *txn);
|
|||||||
* Only write-transactions free cursors.
|
* Only write-transactions free cursors.
|
||||||
* @param[in] txn A transaction handle returned by #mdb_txn_begin()
|
* @param[in] txn A transaction handle returned by #mdb_txn_begin()
|
||||||
*/
|
*/
|
||||||
void mdb_txn_abort(MDB_txn *txn);
|
int mdb_txn_abort(MDB_txn *txn);
|
||||||
|
|
||||||
/** @brief Reset a read-only transaction.
|
/** @brief Reset a read-only transaction.
|
||||||
*
|
*
|
||||||
@ -1077,7 +1077,7 @@ void mdb_txn_abort(MDB_txn *txn);
|
|||||||
* the database size may grow much more rapidly than otherwise.
|
* the database size may grow much more rapidly than otherwise.
|
||||||
* @param[in] txn A transaction handle returned by #mdb_txn_begin()
|
* @param[in] txn A transaction handle returned by #mdb_txn_begin()
|
||||||
*/
|
*/
|
||||||
void mdb_txn_reset(MDB_txn *txn);
|
int mdb_txn_reset(MDB_txn *txn);
|
||||||
|
|
||||||
/** @brief Renew a read-only transaction.
|
/** @brief Renew a read-only transaction.
|
||||||
*
|
*
|
||||||
|
307
mdb.c
307
mdb.c
@ -737,6 +737,8 @@ typedef struct MDB_dbx {
|
|||||||
* Every operation requires a transaction handle.
|
* Every operation requires a transaction handle.
|
||||||
*/
|
*/
|
||||||
struct MDB_txn {
|
struct MDB_txn {
|
||||||
|
#define MDBX_MT_SIGNATURE 0x706C553B
|
||||||
|
unsigned mt_signature;
|
||||||
MDB_txn *mt_parent; /**< parent of a nested txn */
|
MDB_txn *mt_parent; /**< parent of a nested txn */
|
||||||
/** Nested txn under this txn, set together with flag #MDB_TXN_HAS_CHILD */
|
/** Nested txn under this txn, set together with flag #MDB_TXN_HAS_CHILD */
|
||||||
MDB_txn *mt_child;
|
MDB_txn *mt_child;
|
||||||
@ -840,6 +842,8 @@ struct MDB_xcursor;
|
|||||||
* (A node with #F_DUPDATA but no #F_SUBDATA contains a subpage).
|
* (A node with #F_DUPDATA but no #F_SUBDATA contains a subpage).
|
||||||
*/
|
*/
|
||||||
struct MDB_cursor {
|
struct MDB_cursor {
|
||||||
|
#define MDBX_MC_SIGNATURE 0xFE05D5B1
|
||||||
|
unsigned mc_signature;
|
||||||
/** Next cursor on this DB in this txn */
|
/** Next cursor on this DB in this txn */
|
||||||
MDB_cursor *mc_next;
|
MDB_cursor *mc_next;
|
||||||
/** Backup of the original cursor if this cursor is a shadow */
|
/** Backup of the original cursor if this cursor is a shadow */
|
||||||
@ -905,6 +909,8 @@ struct MDB_rthc {
|
|||||||
};
|
};
|
||||||
/** The database environment. */
|
/** The database environment. */
|
||||||
struct MDB_env {
|
struct MDB_env {
|
||||||
|
#define MDBX_ME_SIGNATURE 0x9A899641
|
||||||
|
unsigned me_signature;
|
||||||
HANDLE me_fd; /**< The main data file */
|
HANDLE me_fd; /**< The main data file */
|
||||||
HANDLE me_lfd; /**< The lock file */
|
HANDLE me_lfd; /**< The lock file */
|
||||||
/** Failed to update the meta page. Probably an I/O error. */
|
/** Failed to update the meta page. Probably an I/O error. */
|
||||||
@ -981,7 +987,7 @@ typedef struct MDB_ntxn {
|
|||||||
|
|
||||||
/** Check \b txn and \b dbi arguments to a function */
|
/** Check \b txn and \b dbi arguments to a function */
|
||||||
#define TXN_DBI_EXIST(txn, dbi, validity) \
|
#define TXN_DBI_EXIST(txn, dbi, validity) \
|
||||||
((txn) && (dbi)<(txn)->mt_numdbs && ((txn)->mt_dbflags[dbi] & (validity)))
|
((dbi)<(txn)->mt_numdbs && ((txn)->mt_dbflags[dbi] & (validity)))
|
||||||
|
|
||||||
/** Check for misused \b dbi handles */
|
/** Check for misused \b dbi handles */
|
||||||
#define TXN_DBI_CHANGED(txn, dbi) \
|
#define TXN_DBI_CHANGED(txn, dbi) \
|
||||||
@ -1447,12 +1453,14 @@ static void mdb_audit(MDB_txn *txn)
|
|||||||
int
|
int
|
||||||
mdb_cmp(MDB_txn *txn, MDB_dbi dbi, const MDB_val *a, const MDB_val *b)
|
mdb_cmp(MDB_txn *txn, MDB_dbi dbi, const MDB_val *a, const MDB_val *b)
|
||||||
{
|
{
|
||||||
|
mdb_ensure(NULL, txn->mt_signature == MDBX_MT_SIGNATURE);
|
||||||
return txn->mt_dbxs[dbi].md_cmp(a, b);
|
return txn->mt_dbxs[dbi].md_cmp(a, b);
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
mdb_dcmp(MDB_txn *txn, MDB_dbi dbi, const MDB_val *a, const MDB_val *b)
|
mdb_dcmp(MDB_txn *txn, MDB_dbi dbi, const MDB_val *a, const MDB_val *b)
|
||||||
{
|
{
|
||||||
|
mdb_ensure(NULL, txn->mt_signature == MDBX_MT_SIGNATURE);
|
||||||
return txn->mt_dbxs[dbi].md_dcmp(a, b);
|
return txn->mt_dbxs[dbi].md_dcmp(a, b);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2495,9 +2503,15 @@ mdb_env_sync(MDB_env *env, int force)
|
|||||||
MDB_meta *head;
|
MDB_meta *head;
|
||||||
unsigned flags;
|
unsigned flags;
|
||||||
|
|
||||||
if (unlikely(! env || ! env->me_txns))
|
if (unlikely(! env))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(! env->me_txns))
|
||||||
|
return MDB_PANIC;
|
||||||
|
|
||||||
flags = env->me_flags & ~MDB_NOMETASYNC;
|
flags = env->me_flags & ~MDB_NOMETASYNC;
|
||||||
if (unlikely(flags & (MDB_RDONLY | MDB_FATAL_ERROR)))
|
if (unlikely(flags & (MDB_RDONLY | MDB_FATAL_ERROR)))
|
||||||
return EACCES;
|
return EACCES;
|
||||||
@ -2618,6 +2632,7 @@ mdb_cursors_close(MDB_txn *txn, unsigned merge)
|
|||||||
mc = bk;
|
mc = bk;
|
||||||
}
|
}
|
||||||
/* Only malloced cursors are permanently tracked. */
|
/* Only malloced cursors are permanently tracked. */
|
||||||
|
mc->mc_signature = 0;
|
||||||
free(mc);
|
free(mc);
|
||||||
}
|
}
|
||||||
cursors[i] = NULL;
|
cursors[i] = NULL;
|
||||||
@ -2820,7 +2835,13 @@ mdb_txn_renew(MDB_txn *txn)
|
|||||||
{
|
{
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
if (unlikely(!txn || !F_ISSET(txn->mt_flags, MDB_TXN_RDONLY|MDB_TXN_FINISHED)))
|
if (unlikely(!txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!F_ISSET(txn->mt_flags, MDB_TXN_RDONLY|MDB_TXN_FINISHED)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
rc = mdb_txn_renew0(txn);
|
rc = mdb_txn_renew0(txn);
|
||||||
@ -2839,6 +2860,12 @@ mdb_txn_begin(MDB_env *env, MDB_txn *parent, unsigned flags, MDB_txn **ret)
|
|||||||
MDB_ntxn *ntxn;
|
MDB_ntxn *ntxn;
|
||||||
int rc, size, tsize;
|
int rc, size, tsize;
|
||||||
|
|
||||||
|
if (unlikely(!env || !ret))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
flags &= MDB_TXN_BEGIN_FLAGS;
|
flags &= MDB_TXN_BEGIN_FLAGS;
|
||||||
flags |= env->me_flags & MDB_WRITEMAP;
|
flags |= env->me_flags & MDB_WRITEMAP;
|
||||||
|
|
||||||
@ -2846,6 +2873,9 @@ mdb_txn_begin(MDB_env *env, MDB_txn *parent, unsigned flags, MDB_txn **ret)
|
|||||||
return EACCES;
|
return EACCES;
|
||||||
|
|
||||||
if (parent) {
|
if (parent) {
|
||||||
|
if (unlikely(parent->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
/* Nested transactions: Max 1 child, write txns only, no writemap */
|
/* Nested transactions: Max 1 child, write txns only, no writemap */
|
||||||
flags |= parent->mt_flags;
|
flags |= parent->mt_flags;
|
||||||
if (unlikely(flags & (MDB_RDONLY|MDB_WRITEMAP|MDB_TXN_BLOCKED))) {
|
if (unlikely(flags & (MDB_RDONLY|MDB_WRITEMAP|MDB_TXN_BLOCKED))) {
|
||||||
@ -2924,6 +2954,7 @@ renew:
|
|||||||
free(txn);
|
free(txn);
|
||||||
} else {
|
} else {
|
||||||
txn->mt_flags |= flags; /* could not change txn=me_txn0 earlier */
|
txn->mt_flags |= flags; /* could not change txn=me_txn0 earlier */
|
||||||
|
txn->mt_signature = MDBX_MT_SIGNATURE;
|
||||||
*ret = txn;
|
*ret = txn;
|
||||||
mdb_debug("begin txn %zu%c %p on mdbenv %p, root page %zu",
|
mdb_debug("begin txn %zu%c %p on mdbenv %p, root page %zu",
|
||||||
txn->mt_txnid, (flags & MDB_RDONLY) ? 'r' : 'w',
|
txn->mt_txnid, (flags & MDB_RDONLY) ? 'r' : 'w',
|
||||||
@ -2936,14 +2967,16 @@ renew:
|
|||||||
MDB_env *
|
MDB_env *
|
||||||
mdb_txn_env(MDB_txn *txn)
|
mdb_txn_env(MDB_txn *txn)
|
||||||
{
|
{
|
||||||
if(unlikely(!txn)) return NULL;
|
if(unlikely(!txn || txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return NULL;
|
||||||
return txn->mt_env;
|
return txn->mt_env;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t
|
size_t
|
||||||
mdb_txn_id(MDB_txn *txn)
|
mdb_txn_id(MDB_txn *txn)
|
||||||
{
|
{
|
||||||
if(unlikely(!txn)) return 0;
|
if(unlikely(!txn || txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return 0;
|
||||||
return txn->mt_txnid;
|
return txn->mt_txnid;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2983,7 +3016,13 @@ mdbx_txn_straggler(MDB_txn *txn, int *percent)
|
|||||||
MDB_meta *meta;
|
MDB_meta *meta;
|
||||||
txnid_t lag;
|
txnid_t lag;
|
||||||
|
|
||||||
if (unlikely(! txn || ! txn->mt_u.reader))
|
if(unlikely(!txn))
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
if(unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(! txn->mt_u.reader))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
env = txn->mt_env;
|
env = txn->mt_env;
|
||||||
@ -3073,33 +3112,43 @@ mdb_txn_end(MDB_txn *txn, unsigned mode)
|
|||||||
mdb_midl_free(pghead);
|
mdb_midl_free(pghead);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mode & MDB_END_FREE)
|
if (mode & MDB_END_FREE) {
|
||||||
|
txn->mt_signature = 0;
|
||||||
free(txn);
|
free(txn);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
int
|
||||||
mdb_txn_reset(MDB_txn *txn)
|
mdb_txn_reset(MDB_txn *txn)
|
||||||
{
|
{
|
||||||
if (unlikely(txn == NULL))
|
if (unlikely(! txn))
|
||||||
return;
|
return EINVAL;
|
||||||
|
|
||||||
|
if(unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
/* This call is only valid for read-only txns */
|
/* This call is only valid for read-only txns */
|
||||||
if (unlikely(!(txn->mt_flags & MDB_TXN_RDONLY)))
|
if (unlikely(!(txn->mt_flags & MDB_TXN_RDONLY)))
|
||||||
return;
|
return EINVAL;
|
||||||
|
|
||||||
mdb_txn_end(txn, MDB_END_RESET);
|
mdb_txn_end(txn, MDB_END_RESET);
|
||||||
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
int
|
||||||
mdb_txn_abort(MDB_txn *txn)
|
mdb_txn_abort(MDB_txn *txn)
|
||||||
{
|
{
|
||||||
if (unlikely(txn == NULL))
|
if (unlikely(! txn))
|
||||||
return;
|
return EINVAL;
|
||||||
|
|
||||||
|
if(unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (txn->mt_child)
|
if (txn->mt_child)
|
||||||
mdb_txn_abort(txn->mt_child);
|
mdb_txn_abort(txn->mt_child);
|
||||||
|
|
||||||
mdb_txn_end(txn, MDB_END_ABORT|MDB_END_SLOT|MDB_END_FREE);
|
mdb_txn_end(txn, MDB_END_ABORT|MDB_END_SLOT|MDB_END_FREE);
|
||||||
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
@ -3574,6 +3623,9 @@ mdb_txn_commit(MDB_txn *txn)
|
|||||||
if (unlikely(txn == NULL))
|
if (unlikely(txn == NULL))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if(unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
/* mdb_txn_end() mode for a commit which writes nothing */
|
/* mdb_txn_end() mode for a commit which writes nothing */
|
||||||
end_mode = MDB_END_EMPTY_COMMIT|MDB_END_UPDATE|MDB_END_SLOT|MDB_END_FREE;
|
end_mode = MDB_END_EMPTY_COMMIT|MDB_END_UPDATE|MDB_END_SLOT|MDB_END_FREE;
|
||||||
|
|
||||||
@ -3718,6 +3770,7 @@ mdb_txn_commit(MDB_txn *txn)
|
|||||||
|
|
||||||
parent->mt_child = NULL;
|
parent->mt_child = NULL;
|
||||||
mdb_midl_free(((MDB_ntxn *)txn)->mnt_pgstate.mf_pghead);
|
mdb_midl_free(((MDB_ntxn *)txn)->mnt_pgstate.mf_pghead);
|
||||||
|
txn->mt_signature = 0;
|
||||||
free(txn);
|
free(txn);
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
@ -3797,7 +3850,14 @@ fail:
|
|||||||
}
|
}
|
||||||
|
|
||||||
int __cold
|
int __cold
|
||||||
mdb_env_set_syncbytes(MDB_env *env, size_t bytes) {
|
mdb_env_set_syncbytes(MDB_env *env, size_t bytes)
|
||||||
|
{
|
||||||
|
if (unlikely(!env))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if(unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
env->me_sync_threshold = bytes;
|
env->me_sync_threshold = bytes;
|
||||||
return env->me_map ? mdb_env_sync(env, 0) : 0;
|
return env->me_map ? mdb_env_sync(env, 0) : 0;
|
||||||
}
|
}
|
||||||
@ -4098,6 +4158,7 @@ mdb_env_create(MDB_env **env)
|
|||||||
e->me_pid = getpid();
|
e->me_pid = getpid();
|
||||||
GET_PAGESIZE(e->me_os_psize);
|
GET_PAGESIZE(e->me_os_psize);
|
||||||
VALGRIND_CREATE_MEMPOOL(e,0,0);
|
VALGRIND_CREATE_MEMPOOL(e,0,0);
|
||||||
|
e->me_signature = MDBX_ME_SIGNATURE;
|
||||||
*env = e;
|
*env = e;
|
||||||
return MDB_SUCCESS;
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -4155,6 +4216,15 @@ mdb_env_map(MDB_env *env, void *addr)
|
|||||||
int __cold
|
int __cold
|
||||||
mdb_env_set_mapsize(MDB_env *env, size_t size)
|
mdb_env_set_mapsize(MDB_env *env, size_t size)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!env))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(size < env->me_psize * 8))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
/* If env is already open, caller is responsible for making
|
/* If env is already open, caller is responsible for making
|
||||||
* sure there are no active txns.
|
* sure there are no active txns.
|
||||||
*/
|
*/
|
||||||
@ -4193,8 +4263,15 @@ mdb_env_set_mapsize(MDB_env *env, size_t size)
|
|||||||
int __cold
|
int __cold
|
||||||
mdb_env_set_maxdbs(MDB_env *env, MDB_dbi dbs)
|
mdb_env_set_maxdbs(MDB_env *env, MDB_dbi dbs)
|
||||||
{
|
{
|
||||||
if (env->me_map)
|
if (unlikely(!env))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(env->me_map))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
env->me_maxdbs = dbs + CORE_DBS;
|
env->me_maxdbs = dbs + CORE_DBS;
|
||||||
return MDB_SUCCESS;
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -4202,8 +4279,15 @@ mdb_env_set_maxdbs(MDB_env *env, MDB_dbi dbs)
|
|||||||
int __cold
|
int __cold
|
||||||
mdb_env_set_maxreaders(MDB_env *env, unsigned readers)
|
mdb_env_set_maxreaders(MDB_env *env, unsigned readers)
|
||||||
{
|
{
|
||||||
if (env->me_map || readers < 1)
|
if (unlikely(!env || readers < 1))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(env->me_map))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
env->me_maxreaders = readers;
|
env->me_maxreaders = readers;
|
||||||
return MDB_SUCCESS;
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -4213,6 +4297,10 @@ mdb_env_get_maxreaders(MDB_env *env, unsigned *readers)
|
|||||||
{
|
{
|
||||||
if (!env || !readers)
|
if (!env || !readers)
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
*readers = env->me_maxreaders;
|
*readers = env->me_maxreaders;
|
||||||
return MDB_SUCCESS;
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -4604,7 +4692,13 @@ mdbx_env_open_ex(MDB_env *env, const char *path, unsigned flags, mode_t mode, in
|
|||||||
int oflags, rc, len, excl = -1;
|
int oflags, rc, len, excl = -1;
|
||||||
char *lpath, *dpath;
|
char *lpath, *dpath;
|
||||||
|
|
||||||
if (env->me_fd!=INVALID_HANDLE_VALUE || (flags & ~(CHANGEABLE|CHANGELESS)))
|
if (unlikely(!env || !path))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (env->me_fd != INVALID_HANDLE_VALUE || (flags & ~(CHANGEABLE|CHANGELESS)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
len = strlen(path);
|
len = strlen(path);
|
||||||
@ -4816,16 +4910,19 @@ mdb_env_close0(MDB_env *env)
|
|||||||
#if !MDBX_MODE_ENABLED
|
#if !MDBX_MODE_ENABLED
|
||||||
static
|
static
|
||||||
#endif /* !MDBX_MODE_ENABLED*/
|
#endif /* !MDBX_MODE_ENABLED*/
|
||||||
void __cold
|
int __cold
|
||||||
mdbx_env_close_ex(MDB_env *env, int dont_sync)
|
mdbx_env_close_ex(MDB_env *env, int dont_sync)
|
||||||
{
|
{
|
||||||
MDB_page *dp;
|
MDB_page *dp;
|
||||||
|
int rc = MDB_SUCCESS;
|
||||||
|
|
||||||
if (env == NULL)
|
if (unlikely(!env))
|
||||||
return;
|
return EINVAL;
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (! dont_sync)
|
if (! dont_sync)
|
||||||
mdb_env_sync(env, 1);
|
rc = mdb_env_sync(env, 1);
|
||||||
|
|
||||||
VALGRIND_DESTROY_MEMPOOL(env);
|
VALGRIND_DESTROY_MEMPOOL(env);
|
||||||
while ((dp = env->me_dpages) != NULL) {
|
while ((dp = env->me_dpages) != NULL) {
|
||||||
@ -4835,7 +4932,10 @@ mdbx_env_close_ex(MDB_env *env, int dont_sync)
|
|||||||
}
|
}
|
||||||
|
|
||||||
mdb_env_close0(env);
|
mdb_env_close0(env);
|
||||||
|
env->me_signature = 0;
|
||||||
free(env);
|
free(env);
|
||||||
|
|
||||||
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __cold
|
void __cold
|
||||||
@ -5476,7 +5576,13 @@ mdb_get(MDB_txn *txn, MDB_dbi dbi,
|
|||||||
|
|
||||||
mdb_debug("===> get db %u key [%s]", dbi, DKEY(key));
|
mdb_debug("===> get db %u key [%s]", dbi, DKEY(key));
|
||||||
|
|
||||||
if (unlikely(!key || !data || !TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!key || !data || !txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(txn->mt_flags & MDB_TXN_BLOCKED))
|
if (unlikely(txn->mt_flags & MDB_TXN_BLOCKED))
|
||||||
@ -6001,6 +6107,9 @@ mdb_cursor_get(MDB_cursor *mc, MDB_val *key, MDB_val *data,
|
|||||||
if (unlikely(mc == NULL))
|
if (unlikely(mc == NULL))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(mc->mc_txn->mt_flags & MDB_TXN_BLOCKED))
|
if (unlikely(mc->mc_txn->mt_flags & MDB_TXN_BLOCKED))
|
||||||
return MDB_BAD_TXN;
|
return MDB_BAD_TXN;
|
||||||
|
|
||||||
@ -6216,6 +6325,9 @@ mdb_cursor_put(MDB_cursor *mc, MDB_val *key, MDB_val *data,
|
|||||||
if (unlikely(mc == NULL || key == NULL))
|
if (unlikely(mc == NULL || key == NULL))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
env = mc->mc_txn->mt_env;
|
env = mc->mc_txn->mt_env;
|
||||||
|
|
||||||
/* Check this first so counter will always be zero on any
|
/* Check this first so counter will always be zero on any
|
||||||
@ -6722,6 +6834,12 @@ mdb_cursor_del(MDB_cursor *mc, unsigned flags)
|
|||||||
MDB_page *mp;
|
MDB_page *mp;
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
|
if (unlikely(!mc))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(mc->mc_txn->mt_flags & (MDB_TXN_RDONLY|MDB_TXN_BLOCKED)))
|
if (unlikely(mc->mc_txn->mt_flags & (MDB_TXN_RDONLY|MDB_TXN_BLOCKED)))
|
||||||
return (mc->mc_txn->mt_flags & MDB_TXN_RDONLY) ? EACCES : MDB_BAD_TXN;
|
return (mc->mc_txn->mt_flags & MDB_TXN_RDONLY) ? EACCES : MDB_BAD_TXN;
|
||||||
|
|
||||||
@ -7213,6 +7331,7 @@ mdb_xcursor_init1(MDB_cursor *mc, MDB_node *node)
|
|||||||
if (mx->mx_dbx.md_cmp == mdb_cmp_int && mx->mx_db.md_pad == sizeof(size_t))
|
if (mx->mx_dbx.md_cmp == mdb_cmp_int && mx->mx_db.md_pad == sizeof(size_t))
|
||||||
mx->mx_dbx.md_cmp = mdb_cmp_clong;
|
mx->mx_dbx.md_cmp = mdb_cmp_clong;
|
||||||
#endif */
|
#endif */
|
||||||
|
mc->mc_signature = MDBX_MC_SIGNATURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Initialize a cursor for a given transaction and database. */
|
/** Initialize a cursor for a given transaction and database. */
|
||||||
@ -7233,6 +7352,7 @@ mdb_cursor_init(MDB_cursor *mc, MDB_txn *txn, MDB_dbi dbi, MDB_xcursor *mx)
|
|||||||
mc->mc_ki[0] = 0;
|
mc->mc_ki[0] = 0;
|
||||||
if (txn->mt_dbs[dbi].md_flags & MDB_DUPSORT) {
|
if (txn->mt_dbs[dbi].md_flags & MDB_DUPSORT) {
|
||||||
mdb_tassert(txn, mx != NULL);
|
mdb_tassert(txn, mx != NULL);
|
||||||
|
mx->mx_cursor.mc_signature = MDBX_MC_SIGNATURE;
|
||||||
mc->mc_xcursor = mx;
|
mc->mc_xcursor = mx;
|
||||||
mdb_xcursor_init0(mc);
|
mdb_xcursor_init0(mc);
|
||||||
} else {
|
} else {
|
||||||
@ -7241,6 +7361,7 @@ mdb_cursor_init(MDB_cursor *mc, MDB_txn *txn, MDB_dbi dbi, MDB_xcursor *mx)
|
|||||||
if (*mc->mc_dbflag & DB_STALE) {
|
if (*mc->mc_dbflag & DB_STALE) {
|
||||||
mdb_page_search(mc, NULL, MDB_PS_ROOTONLY);
|
mdb_page_search(mc, NULL, MDB_PS_ROOTONLY);
|
||||||
}
|
}
|
||||||
|
mc->mc_signature = MDBX_MC_SIGNATURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
@ -7249,7 +7370,13 @@ mdb_cursor_open(MDB_txn *txn, MDB_dbi dbi, MDB_cursor **ret)
|
|||||||
MDB_cursor *mc;
|
MDB_cursor *mc;
|
||||||
size_t size = sizeof(MDB_cursor);
|
size_t size = sizeof(MDB_cursor);
|
||||||
|
|
||||||
if (unlikely(!ret || !TXN_DBI_EXIST(txn, dbi, DB_VALID)))
|
if (unlikely(!ret || !txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_VALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(txn->mt_flags & MDB_TXN_BLOCKED))
|
if (unlikely(txn->mt_flags & MDB_TXN_BLOCKED))
|
||||||
@ -7280,7 +7407,14 @@ mdb_cursor_open(MDB_txn *txn, MDB_dbi dbi, MDB_cursor **ret)
|
|||||||
int
|
int
|
||||||
mdb_cursor_renew(MDB_txn *txn, MDB_cursor *mc)
|
mdb_cursor_renew(MDB_txn *txn, MDB_cursor *mc)
|
||||||
{
|
{
|
||||||
if (unlikely(!mc || !TXN_DBI_EXIST(txn, mc->mc_dbi, DB_VALID)))
|
if (unlikely(!mc || !txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE
|
||||||
|
|| mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, mc->mc_dbi, DB_VALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely((mc->mc_flags & C_UNTRACK) || txn->mt_cursors))
|
if (unlikely((mc->mc_flags & C_UNTRACK) || txn->mt_cursors))
|
||||||
@ -7302,6 +7436,9 @@ mdb_cursor_count(MDB_cursor *mc, size_t *countp)
|
|||||||
if (unlikely(mc == NULL || countp == NULL))
|
if (unlikely(mc == NULL || countp == NULL))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(mc->mc_xcursor == NULL))
|
if (unlikely(mc->mc_xcursor == NULL))
|
||||||
return MDB_INCOMPATIBLE;
|
return MDB_INCOMPATIBLE;
|
||||||
|
|
||||||
@ -7329,28 +7466,35 @@ mdb_cursor_count(MDB_cursor *mc, size_t *countp)
|
|||||||
void
|
void
|
||||||
mdb_cursor_close(MDB_cursor *mc)
|
mdb_cursor_close(MDB_cursor *mc)
|
||||||
{
|
{
|
||||||
if (mc && !mc->mc_backup) {
|
if (mc) {
|
||||||
/* remove from txn, if tracked */
|
mdb_ensure(NULL, mc->mc_signature == MDBX_MC_SIGNATURE);
|
||||||
if ((mc->mc_flags & C_UNTRACK) && mc->mc_txn->mt_cursors) {
|
if (!mc->mc_backup) {
|
||||||
MDB_cursor **prev = &mc->mc_txn->mt_cursors[mc->mc_dbi];
|
/* remove from txn, if tracked */
|
||||||
while (*prev && *prev != mc) prev = &(*prev)->mc_next;
|
if ((mc->mc_flags & C_UNTRACK) && mc->mc_txn->mt_cursors) {
|
||||||
if (*prev == mc)
|
MDB_cursor **prev = &mc->mc_txn->mt_cursors[mc->mc_dbi];
|
||||||
*prev = mc->mc_next;
|
while (*prev && *prev != mc) prev = &(*prev)->mc_next;
|
||||||
|
if (*prev == mc)
|
||||||
|
*prev = mc->mc_next;
|
||||||
|
}
|
||||||
|
mc->mc_signature = 0;
|
||||||
|
free(mc);
|
||||||
}
|
}
|
||||||
free(mc);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
MDB_txn *
|
MDB_txn *
|
||||||
mdb_cursor_txn(MDB_cursor *mc)
|
mdb_cursor_txn(MDB_cursor *mc)
|
||||||
{
|
{
|
||||||
if (unlikely(!mc)) return NULL;
|
if (unlikely(!mc || mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return NULL;
|
||||||
return mc->mc_txn;
|
return mc->mc_txn;
|
||||||
}
|
}
|
||||||
|
|
||||||
MDB_dbi
|
MDB_dbi
|
||||||
mdb_cursor_dbi(MDB_cursor *mc)
|
mdb_cursor_dbi(MDB_cursor *mc)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!mc || mc->mc_signature != MDBX_MC_SIGNATURE))
|
||||||
|
return INT_MIN;
|
||||||
return mc->mc_dbi;
|
return mc->mc_dbi;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -8050,7 +8194,13 @@ int
|
|||||||
mdb_del(MDB_txn *txn, MDB_dbi dbi,
|
mdb_del(MDB_txn *txn, MDB_dbi dbi,
|
||||||
MDB_val *key, MDB_val *data)
|
MDB_val *key, MDB_val *data)
|
||||||
{
|
{
|
||||||
if (unlikely(!key || !TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!key || !txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(txn->mt_flags & (MDB_TXN_RDONLY|MDB_TXN_BLOCKED)))
|
if (unlikely(txn->mt_flags & (MDB_TXN_RDONLY|MDB_TXN_BLOCKED)))
|
||||||
@ -8516,7 +8666,13 @@ mdb_put(MDB_txn *txn, MDB_dbi dbi,
|
|||||||
MDB_cursor mc;
|
MDB_cursor mc;
|
||||||
MDB_xcursor mx;
|
MDB_xcursor mx;
|
||||||
|
|
||||||
if (unlikely(!key || !data || !TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!key || !data || !txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(flags & ~(MDB_NOOVERWRITE|MDB_NODUPDATA|MDB_RESERVE|MDB_APPEND|MDB_APPENDDUP)))
|
if (unlikely(flags & ~(MDB_NOOVERWRITE|MDB_NODUPDATA|MDB_RESERVE|MDB_APPEND|MDB_APPENDDUP)))
|
||||||
@ -9262,8 +9418,15 @@ int mdb_dbi_open(MDB_txn *txn, const char *name, unsigned flags, MDB_dbi *dbi)
|
|||||||
unsigned unused = 0, seq;
|
unsigned unused = 0, seq;
|
||||||
size_t len;
|
size_t len;
|
||||||
|
|
||||||
|
if (unlikely(!txn || !dbi))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(flags & ~VALID_FLAGS))
|
if (unlikely(flags & ~VALID_FLAGS))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(txn->mt_flags & MDB_TXN_BLOCKED))
|
if (unlikely(txn->mt_flags & MDB_TXN_BLOCKED))
|
||||||
return MDB_BAD_TXN;
|
return MDB_BAD_TXN;
|
||||||
|
|
||||||
@ -9362,7 +9525,13 @@ static
|
|||||||
int __cold
|
int __cold
|
||||||
mdbx_stat(MDB_txn *txn, MDB_dbi dbi, MDBX_stat *arg, size_t bytes)
|
mdbx_stat(MDB_txn *txn, MDB_dbi dbi, MDBX_stat *arg, size_t bytes)
|
||||||
{
|
{
|
||||||
if (!arg || unlikely(!TXN_DBI_EXIST(txn, dbi, DB_VALID)))
|
if (unlikely(!arg || !txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_VALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(bytes != sizeof(MDBX_stat)))
|
if (unlikely(bytes != sizeof(MDBX_stat)))
|
||||||
@ -9404,8 +9573,15 @@ void mdb_dbi_close(MDB_env *env, MDB_dbi dbi)
|
|||||||
|
|
||||||
int mdb_dbi_flags(MDB_txn *txn, MDB_dbi dbi, unsigned *flags)
|
int mdb_dbi_flags(MDB_txn *txn, MDB_dbi dbi, unsigned *flags)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!txn || !flags))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_VALID)))
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_VALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
*flags = txn->mt_dbs[dbi].md_flags & PERSISTENT_FLAGS;
|
*flags = txn->mt_dbs[dbi].md_flags & PERSISTENT_FLAGS;
|
||||||
return MDB_SUCCESS;
|
return MDB_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -9504,15 +9680,21 @@ int mdb_drop(MDB_txn *txn, MDB_dbi dbi, int del)
|
|||||||
MDB_cursor *mc, *m2;
|
MDB_cursor *mc, *m2;
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
if ((unsigned)del > 1 || unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(1 < (unsigned) del || !txn))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(F_ISSET(txn->mt_flags, MDB_TXN_RDONLY)))
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
return EACCES;
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
if (unlikely(TXN_DBI_CHANGED(txn, dbi)))
|
if (unlikely(TXN_DBI_CHANGED(txn, dbi)))
|
||||||
return MDB_BAD_DBI;
|
return MDB_BAD_DBI;
|
||||||
|
|
||||||
|
if (unlikely(F_ISSET(txn->mt_flags, MDB_TXN_RDONLY)))
|
||||||
|
return EACCES;
|
||||||
|
|
||||||
rc = mdb_cursor_open(txn, dbi, &mc);
|
rc = mdb_cursor_open(txn, dbi, &mc);
|
||||||
if (unlikely(rc))
|
if (unlikely(rc))
|
||||||
return rc;
|
return rc;
|
||||||
@ -9552,6 +9734,12 @@ leave:
|
|||||||
|
|
||||||
int mdb_set_compare(MDB_txn *txn, MDB_dbi dbi, MDB_cmp_func *cmp)
|
int mdb_set_compare(MDB_txn *txn, MDB_dbi dbi, MDB_cmp_func *cmp)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
@ -9561,6 +9749,12 @@ int mdb_set_compare(MDB_txn *txn, MDB_dbi dbi, MDB_cmp_func *cmp)
|
|||||||
|
|
||||||
int mdb_set_dupsort(MDB_txn *txn, MDB_dbi dbi, MDB_cmp_func *cmp)
|
int mdb_set_dupsort(MDB_txn *txn, MDB_dbi dbi, MDB_cmp_func *cmp)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
@ -9570,6 +9764,12 @@ int mdb_set_dupsort(MDB_txn *txn, MDB_dbi dbi, MDB_cmp_func *cmp)
|
|||||||
|
|
||||||
int mdb_set_relfunc(MDB_txn *txn, MDB_dbi dbi, MDB_rel_func *rel)
|
int mdb_set_relfunc(MDB_txn *txn, MDB_dbi dbi, MDB_rel_func *rel)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
@ -9579,6 +9779,12 @@ int mdb_set_relfunc(MDB_txn *txn, MDB_dbi dbi, MDB_rel_func *rel)
|
|||||||
|
|
||||||
int mdb_set_relctx(MDB_txn *txn, MDB_dbi dbi, void *ctx)
|
int mdb_set_relctx(MDB_txn *txn, MDB_dbi dbi, void *ctx)
|
||||||
{
|
{
|
||||||
|
if (unlikely(!txn))
|
||||||
|
return EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
if (unlikely(!TXN_DBI_EXIST(txn, dbi, DB_USRVALID)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
|
||||||
@ -9589,6 +9795,8 @@ int mdb_set_relctx(MDB_txn *txn, MDB_dbi dbi, void *ctx)
|
|||||||
int __cold
|
int __cold
|
||||||
mdb_env_get_maxkeysize(MDB_env *env)
|
mdb_env_get_maxkeysize(MDB_env *env)
|
||||||
{
|
{
|
||||||
|
if (!env || env->me_signature != MDBX_ME_SIGNATURE)
|
||||||
|
return EINVAL;
|
||||||
return ENV_MAXKEY(env);
|
return ENV_MAXKEY(env);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -9600,8 +9808,11 @@ mdb_reader_list(MDB_env *env, MDB_msg_func *func, void *ctx)
|
|||||||
char buf[64];
|
char buf[64];
|
||||||
int rc = 0, first = 1;
|
int rc = 0, first = 1;
|
||||||
|
|
||||||
if (!env || !func)
|
if (unlikely(!env || !func))
|
||||||
return -1;
|
return -EINVAL;
|
||||||
|
|
||||||
|
if (unlikely(env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
rdrs = env->me_txns->mti_numreaders;
|
rdrs = env->me_txns->mti_numreaders;
|
||||||
mr = env->me_txns->mti_readers;
|
mr = env->me_txns->mti_readers;
|
||||||
@ -9675,7 +9886,7 @@ mdb_pid_insert(pid_t *ids, pid_t pid)
|
|||||||
int __cold
|
int __cold
|
||||||
mdb_reader_check(MDB_env *env, int *dead)
|
mdb_reader_check(MDB_env *env, int *dead)
|
||||||
{
|
{
|
||||||
if (!env)
|
if (unlikely(!env || env->me_signature != MDBX_ME_SIGNATURE))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
if (dead)
|
if (dead)
|
||||||
*dead = 0;
|
*dead = 0;
|
||||||
@ -9804,14 +10015,15 @@ static void mdb_mutex_unlock(MDB_env *env, pthread_mutex_t *mutex) {
|
|||||||
void __cold
|
void __cold
|
||||||
mdbx_env_set_oomfunc(MDB_env *env, MDB_oom_func *oomfunc)
|
mdbx_env_set_oomfunc(MDB_env *env, MDB_oom_func *oomfunc)
|
||||||
{
|
{
|
||||||
if (env)
|
if (likely(env && env->me_signature == MDBX_ME_SIGNATURE))
|
||||||
env->me_oom_func = oomfunc;
|
env->me_oom_func = oomfunc;
|
||||||
}
|
}
|
||||||
|
|
||||||
MDB_oom_func* __cold
|
MDB_oom_func* __cold
|
||||||
mdbx_env_get_oomfunc(MDB_env *env)
|
mdbx_env_get_oomfunc(MDB_env *env)
|
||||||
{
|
{
|
||||||
return env ? env->me_oom_func : NULL;
|
return likely(env && env->me_signature == MDBX_ME_SIGNATURE)
|
||||||
|
? env->me_oom_func : NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct mdb_walk_ctx {
|
struct mdb_walk_ctx {
|
||||||
@ -9954,6 +10166,11 @@ mdbx_env_pgwalk(MDB_txn *txn, MDB_pgvisitor_func* visitor, void* user)
|
|||||||
mdb_walk_ctx_t ctx;
|
mdb_walk_ctx_t ctx;
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
|
if (unlikely(!txn))
|
||||||
|
return MDB_BAD_TXN;
|
||||||
|
if (unlikely(txn->mt_signature != MDBX_MT_SIGNATURE))
|
||||||
|
return MDB_VERSION_MISMATCH;
|
||||||
|
|
||||||
ctx.mw_txn = txn;
|
ctx.mw_txn = txn;
|
||||||
ctx.mw_user = user;
|
ctx.mw_user = user;
|
||||||
ctx.mw_visitor = visitor;
|
ctx.mw_visitor = visitor;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user