mirror of
https://github.com/isar/libmdbx.git
synced 2025-01-04 17:34:14 +08:00
mdbx: split MDB_ID into pgno_t and txnid_t.
This commit is contained in:
parent
5c2042c466
commit
0cd30792bb
40
src/bits.h
40
src/bits.h
@ -152,37 +152,27 @@
|
||||
/* Number of meta pages - also hardcoded elsewhere */
|
||||
#define NUM_METAS 2
|
||||
|
||||
/* A generic unsigned ID number. These were entryIDs in back-bdb.
|
||||
* Preferably it should have the same size as a pointer.
|
||||
*/
|
||||
typedef size_t MDB_ID;
|
||||
/* A page number in the database.
|
||||
*
|
||||
* MDBX uses 32 bit for page numbers. This limits database
|
||||
* size up to 2^44 bytes, in case of 4K pages. */
|
||||
typedef uint32_t pgno_t;
|
||||
#define PRIaPGNO PRIu32
|
||||
|
||||
/** A page number in the database.
|
||||
* Note that 64 bit page numbers are overkill, since pages themselves
|
||||
* already represent 12-13 bits of addressable memory, and the OS will
|
||||
* always limit applications to a maximum of 63 bits of address space.
|
||||
*
|
||||
* @note In the #MDB_node structure, we only store 48 bits of this value,
|
||||
* which thus limits us to only 60 bits of addressable data.
|
||||
*/
|
||||
typedef MDB_ID pgno_t;
|
||||
|
||||
/** A transaction ID.
|
||||
* See struct MDB_txn.mt_txnid for details.
|
||||
*/
|
||||
typedef MDB_ID txnid_t;
|
||||
/* A transaction ID. */
|
||||
typedef uint64_t txnid_t;
|
||||
#define PRIaTXN PRIi64
|
||||
|
||||
/* An IDL is an ID List, a sorted array of IDs. The first
|
||||
* element of the array is a counter for how many actual
|
||||
* IDs are in the list. In the original back-bdb code, IDLs are
|
||||
* sorted in ascending order. For libmdb IDLs are sorted in
|
||||
* descending order.
|
||||
*/
|
||||
typedef MDB_ID *MDB_IDL;
|
||||
* element of the array is a counter for how many actual
|
||||
* IDs are in the list. In the original back-bdb code, IDLs are
|
||||
* sorted in ascending order. For libmdb IDLs are sorted in
|
||||
* descending order. */
|
||||
typedef pgno_t *MDB_IDL;
|
||||
|
||||
/* An ID2 is an ID/pointer pair. */
|
||||
typedef struct MDB_ID2 {
|
||||
MDB_ID mid; /* The ID */
|
||||
pgno_t mid; /* The ID */
|
||||
void *mptr; /* The pointer */
|
||||
} MDB_ID2;
|
||||
|
||||
|
258
src/mdbx.c
258
src/mdbx.c
@ -506,25 +506,21 @@ static __inline MDB_node *NODEPTR(MDB_page *p, unsigned i) {
|
||||
|
||||
/* Copy a page number from src to dst */
|
||||
#if UNALIGNED_OK
|
||||
#define COPY_PGNO(dst, src) dst = src
|
||||
#elif SIZE_MAX > 4294967295UL
|
||||
#define COPY_PGNO(dst, src) \
|
||||
do { \
|
||||
uint16_t *s, *d; \
|
||||
s = (uint16_t *)&(src); \
|
||||
d = (uint16_t *)&(dst); \
|
||||
*d++ = *s++; \
|
||||
*d++ = *s++; \
|
||||
*d++ = *s++; \
|
||||
*d = *s; \
|
||||
} while (0)
|
||||
#define COPY_PGNO(dst, src) (dst) = (src)
|
||||
#elif defined(__GNUC__) || __has_builtin(__built_memcmp)
|
||||
#define COPY_PGNO(dst, src) __built_memcmp(&(dst), &(src), sizeof(pgno_t));
|
||||
#else
|
||||
#define COPY_PGNO(dst, src) \
|
||||
do { \
|
||||
uint16_t *s, *d; \
|
||||
s = (uint16_t *)&(src); \
|
||||
d = (uint16_t *)&(dst); \
|
||||
*d++ = *s++; \
|
||||
if (sizeof(pgno_t) > 6) \
|
||||
*d++ = *s++; \
|
||||
if (sizeof(pgno_t) > 4) \
|
||||
*d++ = *s++; \
|
||||
if (sizeof(pgno_t) > 2) \
|
||||
*d++ = *s++; \
|
||||
*d = *s; \
|
||||
} while (0)
|
||||
#endif /* UNALIGNED_OK */
|
||||
@ -952,14 +948,14 @@ static void mdbx_cursor_chk(MDB_cursor *mc) {
|
||||
static void mdbx_audit(MDB_txn *txn) {
|
||||
MDB_cursor mc;
|
||||
MDB_val key, data;
|
||||
MDB_ID freecount, count;
|
||||
pgno_t freecount, count;
|
||||
MDB_dbi i;
|
||||
int rc;
|
||||
|
||||
freecount = 0;
|
||||
mdbx_cursor_init(&mc, txn, FREE_DBI, NULL);
|
||||
while ((rc = mdbx_cursor_get(&mc, &key, &data, MDB_NEXT)) == 0)
|
||||
freecount += *(MDB_ID *)data.mv_data;
|
||||
freecount += *(pgno_t *)data.mv_data;
|
||||
mdbx_tassert(txn, rc == MDB_NOTFOUND);
|
||||
|
||||
count = 0;
|
||||
@ -992,10 +988,10 @@ static void mdbx_audit(MDB_txn *txn) {
|
||||
}
|
||||
}
|
||||
if (freecount + count + NUM_METAS != txn->mt_next_pgno) {
|
||||
mdbx_print(
|
||||
"audit: %lu freecount: %lu count: %lu total: %lu next_pgno: %lu\n",
|
||||
txn->mt_txnid, freecount, count + NUM_METAS,
|
||||
freecount + count + NUM_METAS, txn->mt_next_pgno);
|
||||
mdbx_print("audit: %" PRIaTXN " freecount: %" PRIaPGNO " count: %" PRIaPGNO
|
||||
" total: %" PRIaPGNO " next_pgno: %" PRIaPGNO "\n",
|
||||
txn->mt_txnid, freecount, count + NUM_METAS,
|
||||
freecount + count + NUM_METAS, txn->mt_next_pgno);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1133,7 +1129,7 @@ static int mdbx_page_loose(MDB_cursor *mc, MDB_page *mp) {
|
||||
}
|
||||
}
|
||||
if (loose) {
|
||||
mdbx_debug("loosen db %d page %" PRIuPTR "", DDBI(mc), mp->mp_pgno);
|
||||
mdbx_debug("loosen db %d page %" PRIaPGNO, DDBI(mc), mp->mp_pgno);
|
||||
MDB_page **link = &NEXT_LOOSE_PAGE(mp);
|
||||
if (unlikely(txn->mt_env->me_flags & MDBX_PAGEPERTURB)) {
|
||||
mdbx_kill_page(txn->mt_env, pgno);
|
||||
@ -1312,7 +1308,7 @@ static int mdbx_page_spill(MDB_cursor *m0, MDB_val *key, MDB_val *data) {
|
||||
/* Save the page IDs of all the pages we're flushing */
|
||||
/* flush from the tail forward, this saves a lot of shifting later on. */
|
||||
for (i = dl[0].mid; i && need; i--) {
|
||||
MDB_ID pn = dl[i].mid << 1;
|
||||
pgno_t pn = dl[i].mid << 1;
|
||||
dp = dl[i].mptr;
|
||||
if (dp->mp_flags & (P_LOOSE | P_KEEP))
|
||||
continue;
|
||||
@ -1470,7 +1466,7 @@ static int mdbx_page_alloc(MDB_cursor *mc, int num, MDB_page **mp, int flags) {
|
||||
np = txn->mt_loose_pgs;
|
||||
txn->mt_loose_pgs = NEXT_LOOSE_PAGE(np);
|
||||
txn->mt_loose_count--;
|
||||
mdbx_debug("db %d use loose page %" PRIuPTR "", DDBI(mc), np->mp_pgno);
|
||||
mdbx_debug("db %d use loose page %" PRIaPGNO, DDBI(mc), np->mp_pgno);
|
||||
ASAN_UNPOISON_MEMORY_REGION(np, env->me_psize);
|
||||
*mp = np;
|
||||
return MDB_SUCCESS;
|
||||
@ -1597,9 +1593,9 @@ static int mdbx_page_alloc(MDB_cursor *mc, int num, MDB_page **mp, int flags) {
|
||||
}
|
||||
}
|
||||
|
||||
idl = (MDB_ID *)data.mv_data;
|
||||
idl = (pgno_t *)data.mv_data;
|
||||
mdbx_tassert(txn, idl[0] == 0 ||
|
||||
data.mv_size == (idl[0] + 1) * sizeof(MDB_ID));
|
||||
data.mv_size == (idl[0] + 1) * sizeof(pgno_t));
|
||||
i = idl[0];
|
||||
if (!mop) {
|
||||
if (unlikely(!(env->me_pghead = mop = mdbx_midl_alloc(i)))) {
|
||||
@ -1618,11 +1614,11 @@ static int mdbx_page_alloc(MDB_cursor *mc, int num, MDB_page **mp, int flags) {
|
||||
env->me_pglast = last;
|
||||
|
||||
if (mdbx_debug_enabled(MDBX_DBG_EXTRA)) {
|
||||
mdbx_debug_extra("IDL read txn %" PRIuPTR " root %" PRIuPTR
|
||||
mdbx_debug_extra("IDL read txn %" PRIaTXN " root %" PRIaPGNO
|
||||
" num %u, IDL",
|
||||
last, txn->mt_dbs[FREE_DBI].md_root, i);
|
||||
for (j = i; j; j--)
|
||||
mdbx_debug_extra_print(" %" PRIuPTR "", idl[j]);
|
||||
mdbx_debug_extra_print(" %" PRIaPGNO "", idl[j]);
|
||||
mdbx_debug_extra_print("\n");
|
||||
}
|
||||
|
||||
@ -1684,8 +1680,8 @@ static int mdbx_page_alloc(MDB_cursor *mc, int num, MDB_page **mp, int flags) {
|
||||
* don't make a steady-sync, but only a legacy-mode checkpoint,
|
||||
* just for resume reclaiming only, not for data consistency. */
|
||||
|
||||
mdbx_debug("kick-gc: head %" PRIuPTR "/%c, tail %" PRIuPTR
|
||||
"/%c, oldest %" PRIuPTR "",
|
||||
mdbx_debug("kick-gc: head %" PRIaTXN "/%c, tail %" PRIaTXN
|
||||
"/%c, oldest %" PRIaTXN "",
|
||||
head->mm_txnid, META_IS_WEAK(head) ? 'W' : 'N',
|
||||
tail->mm_txnid, META_IS_WEAK(tail) ? 'W' : 'N', oldest);
|
||||
|
||||
@ -1862,7 +1858,7 @@ static int mdbx_page_touch(MDB_cursor *mc) {
|
||||
(rc = mdbx_page_alloc(mc, 1, &np, MDBX_ALLOC_ALL))))
|
||||
goto fail;
|
||||
pgno = np->mp_pgno;
|
||||
mdbx_debug("touched db %d page %" PRIuPTR " -> %" PRIuPTR "", DDBI(mc),
|
||||
mdbx_debug("touched db %d page %" PRIaPGNO " -> %" PRIaPGNO, DDBI(mc),
|
||||
mp->mp_pgno, pgno);
|
||||
mdbx_cassert(mc, mp->mp_pgno != pgno);
|
||||
mdbx_midl_xappend(txn->mt_free_pgs, mp->mp_pgno);
|
||||
@ -2217,7 +2213,7 @@ static int mdbx_txn_renew0(MDB_txn *txn, unsigned flags) {
|
||||
mdbx_runtime_flags |=
|
||||
MDBX_DBG_TRACE | MDBX_DBG_EXTRA | MDBX_DBG_AUDIT | MDBX_DBG_ASSERT;
|
||||
mdbx_debug_log(MDBX_DBG_EDGE, __FUNCTION__, __LINE__,
|
||||
"on/off edge (txn %" PRIuPTR ")", txn->mt_txnid);
|
||||
"on/off edge (txn %" PRIaTXN ")", txn->mt_txnid);
|
||||
}
|
||||
#endif
|
||||
if (unlikely(txn->mt_txnid < meta->mm_txnid)) {
|
||||
@ -2285,8 +2281,7 @@ int mdbx_txn_renew(MDB_txn *txn) {
|
||||
|
||||
rc = mdbx_txn_renew0(txn, MDB_TXN_RDONLY);
|
||||
if (rc == MDB_SUCCESS) {
|
||||
mdbx_debug("renew txn %" PRIuPTR "%c %p on mdbenv %p, root page %" PRIuPTR
|
||||
"",
|
||||
mdbx_debug("renew txn %" PRIaTXN "%c %p on env %p, root page %" PRIaPGNO "",
|
||||
txn->mt_txnid, (txn->mt_flags & MDB_TXN_RDONLY) ? 'r' : 'w',
|
||||
(void *)txn, (void *)txn->mt_env, txn->mt_dbs[MAIN_DBI].md_root);
|
||||
}
|
||||
@ -2399,8 +2394,7 @@ int mdbx_txn_begin(MDB_env *env, MDB_txn *parent, unsigned flags,
|
||||
} else {
|
||||
txn->mt_signature = MDBX_MT_SIGNATURE;
|
||||
*ret = txn;
|
||||
mdbx_debug("begin txn %" PRIuPTR "%c %p on mdbenv %p, root page %" PRIuPTR
|
||||
"",
|
||||
mdbx_debug("begin txn %" PRIaTXN "%c %p on env %p, root page %" PRIaPGNO "",
|
||||
txn->mt_txnid, (flags & MDB_RDONLY) ? 'r' : 'w', (void *)txn,
|
||||
(void *)env, txn->mt_dbs[MAIN_DBI].md_root);
|
||||
}
|
||||
@ -2462,7 +2456,7 @@ static int mdbx_txn_end(MDB_txn *txn, unsigned mode) {
|
||||
/* Export or close DBI handles opened in this txn */
|
||||
mdbx_dbis_update(txn, mode & MDB_END_UPDATE);
|
||||
|
||||
mdbx_debug("%s txn %" PRIuPTR "%c %p on mdbenv %p, root page %" PRIuPTR "",
|
||||
mdbx_debug("%s txn %" PRIaTXN "%c %p on mdbenv %p, root page %" PRIaPGNO "",
|
||||
names[mode & MDB_END_OPMASK], txn->mt_txnid,
|
||||
(txn->mt_flags & MDB_TXN_RDONLY) ? 'r' : 'w', (void *)txn,
|
||||
(void *)env, txn->mt_dbs[MAIN_DBI].md_root);
|
||||
@ -2705,11 +2699,11 @@ again:
|
||||
|
||||
if (mdbx_debug_enabled(MDBX_DBG_EXTRA)) {
|
||||
unsigned i = free_pgs[0];
|
||||
mdbx_debug_extra("IDL write txn %" PRIuPTR " root %" PRIuPTR
|
||||
mdbx_debug_extra("IDL write txn %" PRIaTXN " root %" PRIaPGNO
|
||||
" num %u, IDL",
|
||||
txn->mt_txnid, txn->mt_dbs[FREE_DBI].md_root, i);
|
||||
for (; i; i--)
|
||||
mdbx_debug_extra_print(" %" PRIuPTR "", free_pgs[i]);
|
||||
mdbx_debug_extra_print(" %" PRIaPGNO "", free_pgs[i]);
|
||||
mdbx_debug_extra_print("\n");
|
||||
}
|
||||
continue;
|
||||
@ -2840,7 +2834,7 @@ again:
|
||||
for (;;) {
|
||||
txnid_t id;
|
||||
ssize_t len;
|
||||
MDB_ID save;
|
||||
pgno_t save;
|
||||
|
||||
if (!lifo) {
|
||||
id = *(txnid_t *)key.mv_data;
|
||||
@ -2859,11 +2853,11 @@ again:
|
||||
txn, cleanup_idx ==
|
||||
(txn->mt_lifo_reclaimed ? txn->mt_lifo_reclaimed[0] : 0));
|
||||
|
||||
len = (ssize_t)(data.mv_size / sizeof(MDB_ID)) - 1;
|
||||
len = (ssize_t)(data.mv_size / sizeof(pgno_t)) - 1;
|
||||
mdbx_tassert(txn, len >= 0);
|
||||
if (len > mop_len)
|
||||
len = mop_len;
|
||||
data.mv_size = (len + 1) * sizeof(MDB_ID);
|
||||
data.mv_size = (len + 1) * sizeof(pgno_t);
|
||||
key.mv_data = &id;
|
||||
key.mv_size = sizeof(id);
|
||||
data.mv_data = mop -= len;
|
||||
@ -2979,7 +2973,7 @@ static int mdbx_page_flush(MDB_txn *txn, int keep) {
|
||||
wpos = pos;
|
||||
wsize = 0;
|
||||
}
|
||||
mdbx_debug("committing page %" PRIuPTR "", pgno);
|
||||
mdbx_debug("committing page %" PRIaPGNO "", pgno);
|
||||
next_pos = pos + size;
|
||||
iov[n].iov_len = size;
|
||||
iov[n].iov_base = (char *)dp;
|
||||
@ -3096,7 +3090,7 @@ int mdbx_txn_commit(MDB_txn *txn) {
|
||||
pspill[0] = (pgno_t)-1;
|
||||
/* Mark our dirty pages as deleted in parent spill list */
|
||||
for (i = 0, len = src[0].mid; ++i <= len;) {
|
||||
MDB_ID pn = src[i].mid << 1;
|
||||
pgno_t pn = src[i].mid << 1;
|
||||
while (pn > pspill[x])
|
||||
x--;
|
||||
if (pn == pspill[x]) {
|
||||
@ -3114,7 +3108,7 @@ int mdbx_txn_commit(MDB_txn *txn) {
|
||||
/* Remove anything in our spill list from parent's dirty list */
|
||||
if (txn->mt_spill_pgs && txn->mt_spill_pgs[0]) {
|
||||
for (i = 1; i <= txn->mt_spill_pgs[0]; i++) {
|
||||
MDB_ID pn = txn->mt_spill_pgs[i];
|
||||
pgno_t pn = txn->mt_spill_pgs[i];
|
||||
if (pn & 1)
|
||||
continue; /* deleted spillpg */
|
||||
pn >>= 1;
|
||||
@ -3201,7 +3195,7 @@ int mdbx_txn_commit(MDB_txn *txn) {
|
||||
goto done;
|
||||
|
||||
mdbx_debug(
|
||||
"committing txn %" PRIuPTR " %p on mdbenv %p, root page %" PRIuPTR "",
|
||||
"committing txn %" PRIaTXN " %p on mdbenv %p, root page %" PRIaPGNO "",
|
||||
txn->mt_txnid, (void *)txn, (void *)env, txn->mt_dbs[MAIN_DBI].md_root);
|
||||
|
||||
/* Update DB root pointers */
|
||||
@ -3283,7 +3277,7 @@ static int __cold mdbx_read_header(MDB_env *env, MDB_meta *meta) {
|
||||
|
||||
MDB_page *p = (MDB_page *)&buf;
|
||||
if (!F_ISSET(p->mp_flags, P_META)) {
|
||||
mdbx_debug("page %" PRIuPTR " not a meta-page", p->mp_pgno);
|
||||
mdbx_debug("page %" PRIaPGNO " not a meta-page", p->mp_pgno);
|
||||
return MDB_INVALID;
|
||||
}
|
||||
|
||||
@ -3448,9 +3442,9 @@ static int mdbx_env_sync_locked(MDB_env *env, unsigned flags,
|
||||
|
||||
MDB_meta *stay = mdbx_env_meta_flipflop(env, (MDB_meta *)target);
|
||||
mdbx_debug(
|
||||
"writing meta %d (%s, was %" PRIuPTR "/%s, stay %s %" PRIuPTR
|
||||
"/%s), root %" PRIuPTR ", "
|
||||
"txn_id %" PRIuPTR ", %s",
|
||||
"writing meta %d (%s, was %" PRIaTXN "/%s, stay %s %" PRIaTXN
|
||||
"/%s), root %" PRIaPGNO ", "
|
||||
"txn_id %" PRIaTXN ", %s",
|
||||
offset >= (off_t)env->me_psize, target == head ? "head" : "tail",
|
||||
target->mm_txnid,
|
||||
META_IS_WEAK(target) ? "Weak" : META_IS_STEADY(target) ? "Steady"
|
||||
@ -3815,7 +3809,7 @@ static int __cold mdbx_setup_dxb(MDB_env *env, MDB_meta *meta, int lck_rc) {
|
||||
|
||||
MDB_meta *const head = mdbx_meta_head(env);
|
||||
if (head->mm_txnid != meta->mm_txnid) {
|
||||
mdbx_trace("head->mm_txnid (%" PRIuPTR ") != (%" PRIuPTR ") meta->mm_txnid",
|
||||
mdbx_trace("head->mm_txnid (%" PRIaTXN ") != (%" PRIaTXN ") meta->mm_txnid",
|
||||
head->mm_txnid, meta->mm_txnid);
|
||||
if (lck_rc == /* lck exclusive */ MDBX_RESULT_TRUE) {
|
||||
assert(META_IS_STEADY(meta) && !META_IS_STEADY(head));
|
||||
@ -4111,13 +4105,13 @@ int __cold mdbx_env_open_ex(MDB_env *env, const char *path, unsigned flags,
|
||||
|
||||
mdbx_debug("opened database version %u, pagesize %u", meta->mm_version,
|
||||
env->me_psize);
|
||||
mdbx_debug("using meta page %d, txn %" PRIuPTR "", toggle, meta->mm_txnid);
|
||||
mdbx_debug("using meta page %d, txn %" PRIaTXN "", toggle, meta->mm_txnid);
|
||||
mdbx_debug("depth: %u", db->md_depth);
|
||||
mdbx_debug("entries: %" PRIuPTR "", db->md_entries);
|
||||
mdbx_debug("branch pages: %" PRIuPTR "", db->md_branch_pages);
|
||||
mdbx_debug("leaf pages: %" PRIuPTR "", db->md_leaf_pages);
|
||||
mdbx_debug("overflow pages: %" PRIuPTR "", db->md_overflow_pages);
|
||||
mdbx_debug("root: %" PRIuPTR "", db->md_root);
|
||||
mdbx_debug("entries: %" PRIu64 "", db->md_entries);
|
||||
mdbx_debug("branch pages: %" PRIaPGNO "", db->md_branch_pages);
|
||||
mdbx_debug("leaf pages: %" PRIaPGNO "", db->md_leaf_pages);
|
||||
mdbx_debug("overflow pages: %" PRIaPGNO "", db->md_overflow_pages);
|
||||
mdbx_debug("root: %" PRIaPGNO "", db->md_root);
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -4384,7 +4378,7 @@ static MDB_node *__hot mdbx_node_search(MDB_cursor *mc, MDB_val *key,
|
||||
|
||||
nkeys = NUMKEYS(mp);
|
||||
|
||||
mdbx_debug("searching %u keys in %s %spage %" PRIuPTR "", nkeys,
|
||||
mdbx_debug("searching %u keys in %s %spage %" PRIaPGNO "", nkeys,
|
||||
IS_LEAF(mp) ? "leaf" : "branch", IS_SUBP(mp) ? "sub-" : "",
|
||||
mdbx_dbg_pgno(mp));
|
||||
|
||||
@ -4425,7 +4419,7 @@ static MDB_node *__hot mdbx_node_search(MDB_cursor *mc, MDB_val *key,
|
||||
if (IS_LEAF(mp))
|
||||
mdbx_debug("found leaf index %u [%s], rc = %i", i, DKEY(&nodekey), rc);
|
||||
else
|
||||
mdbx_debug("found branch index %u [%s -> %" PRIuPTR "], rc = %i", i,
|
||||
mdbx_debug("found branch index %u [%s -> %" PRIaPGNO "], rc = %i", i,
|
||||
DKEY(&nodekey), NODEPGNO(node), rc);
|
||||
if (rc == 0)
|
||||
break;
|
||||
@ -4466,7 +4460,7 @@ static void mdbx_cursor_adjust(MDB_cursor *mc, func) {
|
||||
/* Pop a page off the top of the cursor's stack. */
|
||||
static void mdbx_cursor_pop(MDB_cursor *mc) {
|
||||
if (mc->mc_snum) {
|
||||
mdbx_debug("popped page %" PRIuPTR " off db %d cursor %p",
|
||||
mdbx_debug("popped page %" PRIaPGNO " off db %d cursor %p",
|
||||
mc->mc_pg[mc->mc_top]->mp_pgno, DDBI(mc), (void *)mc);
|
||||
|
||||
mc->mc_snum--;
|
||||
@ -4481,7 +4475,7 @@ static void mdbx_cursor_pop(MDB_cursor *mc) {
|
||||
/* Push a page onto the top of the cursor's stack.
|
||||
* Set MDB_TXN_ERROR on failure. */
|
||||
static int mdbx_cursor_push(MDB_cursor *mc, MDB_page *mp) {
|
||||
mdbx_debug("pushing page %" PRIuPTR " on db %d cursor %p", mp->mp_pgno,
|
||||
mdbx_debug("pushing page %" PRIaPGNO " on db %d cursor %p", mp->mp_pgno,
|
||||
DDBI(mc), (void *)mc);
|
||||
|
||||
if (unlikely(mc->mc_snum >= CURSOR_STACK)) {
|
||||
@ -4525,7 +4519,7 @@ static int mdbx_page_get(MDB_cursor *mc, pgno_t pgno, MDB_page **ret,
|
||||
* back in from the map (but don't unspill it here,
|
||||
* leave that unless page_touch happens again). */
|
||||
if (tx2->mt_spill_pgs) {
|
||||
MDB_ID pn = pgno << 1;
|
||||
pgno_t pn = pgno << 1;
|
||||
x = mdbx_midl_search(tx2->mt_spill_pgs, pn);
|
||||
if (x <= tx2->mt_spill_pgs[0] && tx2->mt_spill_pgs[x] == pn)
|
||||
goto mapped;
|
||||
@ -4542,7 +4536,7 @@ static int mdbx_page_get(MDB_cursor *mc, pgno_t pgno, MDB_page **ret,
|
||||
}
|
||||
|
||||
if (unlikely(pgno >= txn->mt_next_pgno)) {
|
||||
mdbx_debug("page %" PRIuPTR " not found", pgno);
|
||||
mdbx_debug("page %" PRIaPGNO " not found", pgno);
|
||||
txn->mt_flags |= MDB_TXN_ERROR;
|
||||
return MDB_PAGE_NOTFOUND;
|
||||
}
|
||||
@ -4569,13 +4563,13 @@ static int mdbx_page_search_root(MDB_cursor *mc, MDB_val *key, int flags) {
|
||||
MDB_node *node;
|
||||
indx_t i;
|
||||
|
||||
mdbx_debug("branch page %" PRIuPTR " has %u keys", mp->mp_pgno,
|
||||
mdbx_debug("branch page %" PRIaPGNO " has %u keys", mp->mp_pgno,
|
||||
NUMKEYS(mp));
|
||||
/* Don't assert on branch pages in the FreeDB. We can get here
|
||||
* while in the process of rebalancing a FreeDB branch page; we must
|
||||
* let that proceed. ITS#8336 */
|
||||
mdbx_cassert(mc, !mc->mc_dbi || NUMKEYS(mp) > 1);
|
||||
mdbx_debug("found index 0 to page %" PRIuPTR "", NODEPGNO(NODEPTR(mp, 0)));
|
||||
mdbx_debug("found index 0 to page %" PRIaPGNO "", NODEPGNO(NODEPTR(mp, 0)));
|
||||
|
||||
if (flags & (MDB_PS_FIRST | MDB_PS_LAST)) {
|
||||
i = 0;
|
||||
@ -4630,7 +4624,7 @@ static int mdbx_page_search_root(MDB_cursor *mc, MDB_val *key, int flags) {
|
||||
return MDB_CORRUPTED;
|
||||
}
|
||||
|
||||
mdbx_debug("found leaf page %" PRIuPTR " for key [%s]", mp->mp_pgno,
|
||||
mdbx_debug("found leaf page %" PRIaPGNO " for key [%s]", mp->mp_pgno,
|
||||
DKEY(key));
|
||||
mc->mc_flags |= C_INITIALIZED;
|
||||
mc->mc_flags &= ~C_EOF;
|
||||
@ -4728,7 +4722,7 @@ static int mdbx_page_search(MDB_cursor *mc, MDB_val *key, int flags) {
|
||||
mc->mc_snum = 1;
|
||||
mc->mc_top = 0;
|
||||
|
||||
mdbx_debug("db %d root page %" PRIuPTR " has flags 0x%X", DDBI(mc), root,
|
||||
mdbx_debug("db %d root page %" PRIaPGNO " has flags 0x%X", DDBI(mc), root,
|
||||
mc->mc_pg[0]->mp_flags);
|
||||
|
||||
if (flags & MDB_PS_MODIFY) {
|
||||
@ -4748,10 +4742,10 @@ static int mdbx_ovpage_free(MDB_cursor *mc, MDB_page *mp) {
|
||||
unsigned x = 0, ovpages = mp->mp_pages;
|
||||
MDB_env *env = txn->mt_env;
|
||||
MDB_IDL sl = txn->mt_spill_pgs;
|
||||
MDB_ID pn = pg << 1;
|
||||
pgno_t pn = pg << 1;
|
||||
int rc;
|
||||
|
||||
mdbx_debug("free ov page %" PRIuPTR " (%u)", pg, ovpages);
|
||||
mdbx_debug("free ov page %" PRIaPGNO " (%u)", pg, ovpages);
|
||||
/* If the page is dirty or on the spill list we just acquired it,
|
||||
* so we should give it back to our current free list, if any.
|
||||
* Otherwise put it onto the list of pages we freed in this txn.
|
||||
@ -4836,7 +4830,7 @@ static __inline int mdbx_node_read(MDB_cursor *mc, MDB_node *leaf,
|
||||
data->mv_size = NODEDSZ(leaf);
|
||||
memcpy(&pgno, NODEDATA(leaf), sizeof(pgno));
|
||||
if (unlikely((rc = mdbx_page_get(mc, pgno, &omp, NULL)) != 0)) {
|
||||
mdbx_debug("read overflow page %" PRIuPTR " failed", pgno);
|
||||
mdbx_debug("read overflow page %" PRIaPGNO " failed", pgno);
|
||||
return rc;
|
||||
}
|
||||
data->mv_data = PAGEDATA(omp);
|
||||
@ -4887,7 +4881,7 @@ static int mdbx_cursor_sibling(MDB_cursor *mc, int move_right) {
|
||||
}
|
||||
|
||||
mdbx_cursor_pop(mc);
|
||||
mdbx_debug("parent page is page %" PRIuPTR ", index %u",
|
||||
mdbx_debug("parent page is page %" PRIaPGNO ", index %u",
|
||||
mc->mc_pg[mc->mc_top]->mp_pgno, mc->mc_ki[mc->mc_top]);
|
||||
|
||||
if (move_right
|
||||
@ -4963,7 +4957,7 @@ static int mdbx_cursor_next(MDB_cursor *mc, MDB_val *key, MDB_val *data,
|
||||
}
|
||||
}
|
||||
|
||||
mdbx_debug("cursor_next: top page is %" PRIuPTR " in cursor %p",
|
||||
mdbx_debug("cursor_next: top page is %" PRIaPGNO " in cursor %p",
|
||||
mdbx_dbg_pgno(mp), (void *)mc);
|
||||
if (mc->mc_flags & C_DEL) {
|
||||
mc->mc_flags ^= C_DEL;
|
||||
@ -4977,13 +4971,13 @@ static int mdbx_cursor_next(MDB_cursor *mc, MDB_val *key, MDB_val *data,
|
||||
return rc;
|
||||
}
|
||||
mp = mc->mc_pg[mc->mc_top];
|
||||
mdbx_debug("next page is %" PRIuPTR ", key index %u", mp->mp_pgno,
|
||||
mdbx_debug("next page is %" PRIaPGNO ", key index %u", mp->mp_pgno,
|
||||
mc->mc_ki[mc->mc_top]);
|
||||
} else
|
||||
mc->mc_ki[mc->mc_top]++;
|
||||
|
||||
skip:
|
||||
mdbx_debug("==> cursor points to page %" PRIuPTR
|
||||
mdbx_debug("==> cursor points to page %" PRIaPGNO
|
||||
" with %u keys, key index %u",
|
||||
mdbx_dbg_pgno(mp), NUMKEYS(mp), mc->mc_ki[mc->mc_top]);
|
||||
|
||||
@ -5053,7 +5047,7 @@ static int mdbx_cursor_prev(MDB_cursor *mc, MDB_val *key, MDB_val *data,
|
||||
}
|
||||
}
|
||||
|
||||
mdbx_debug("cursor_prev: top page is %" PRIuPTR " in cursor %p",
|
||||
mdbx_debug("cursor_prev: top page is %" PRIaPGNO " in cursor %p",
|
||||
mdbx_dbg_pgno(mp), (void *)mc);
|
||||
|
||||
mc->mc_flags &= ~(C_EOF | C_DEL);
|
||||
@ -5065,12 +5059,12 @@ static int mdbx_cursor_prev(MDB_cursor *mc, MDB_val *key, MDB_val *data,
|
||||
}
|
||||
mp = mc->mc_pg[mc->mc_top];
|
||||
mc->mc_ki[mc->mc_top] = NUMKEYS(mp) - 1;
|
||||
mdbx_debug("prev page is %" PRIuPTR ", key index %u", mp->mp_pgno,
|
||||
mdbx_debug("prev page is %" PRIaPGNO ", key index %u", mp->mp_pgno,
|
||||
mc->mc_ki[mc->mc_top]);
|
||||
} else
|
||||
mc->mc_ki[mc->mc_top]--;
|
||||
|
||||
mdbx_debug("==> cursor points to page %" PRIuPTR
|
||||
mdbx_debug("==> cursor points to page %" PRIaPGNO
|
||||
" with %u keys, key index %u",
|
||||
mdbx_dbg_pgno(mp), NUMKEYS(mp), mc->mc_ki[mc->mc_top]);
|
||||
|
||||
@ -6279,7 +6273,7 @@ static int mdbx_page_new(MDB_cursor *mc, uint32_t flags, int num,
|
||||
|
||||
if (unlikely((rc = mdbx_page_alloc(mc, num, &np, MDBX_ALLOC_ALL))))
|
||||
return rc;
|
||||
mdbx_debug("allocated new page #%" PRIuPTR ", size %u", np->mp_pgno,
|
||||
mdbx_debug("allocated new page #%" PRIaPGNO ", size %u", np->mp_pgno,
|
||||
mc->mc_txn->mt_env->me_psize);
|
||||
np->mp_flags = flags | P_DIRTY;
|
||||
np->mp_lower = (PAGEHDRSZ - PAGEBASE);
|
||||
@ -6381,7 +6375,7 @@ static int mdbx_node_add(MDB_cursor *mc, indx_t indx, MDB_val *key,
|
||||
|
||||
mdbx_cassert(mc, mp->mp_upper >= mp->mp_lower);
|
||||
|
||||
mdbx_debug("add to %s %spage %" PRIuPTR " index %i, data size %" PRIuPTR
|
||||
mdbx_debug("add to %s %spage %" PRIaPGNO " index %i, data size %" PRIuPTR
|
||||
" key size %" PRIuPTR " [%s]",
|
||||
IS_LEAF(mp) ? "leaf" : "branch", IS_SUBP(mp) ? "sub-" : "",
|
||||
mdbx_dbg_pgno(mp), indx, data ? data->mv_size : 0,
|
||||
@ -6425,7 +6419,7 @@ static int mdbx_node_add(MDB_cursor *mc, indx_t indx, MDB_val *key,
|
||||
goto full;
|
||||
if ((rc = mdbx_page_new(mc, P_OVERFLOW, ovpages, &ofp)))
|
||||
return rc;
|
||||
mdbx_debug("allocated overflow page %" PRIuPTR "", ofp->mp_pgno);
|
||||
mdbx_debug("allocated overflow page %" PRIaPGNO "", ofp->mp_pgno);
|
||||
flags |= F_BIGDATA;
|
||||
goto update;
|
||||
} else {
|
||||
@ -6482,7 +6476,7 @@ update:
|
||||
return MDB_SUCCESS;
|
||||
|
||||
full:
|
||||
mdbx_debug("not enough room in page %" PRIuPTR ", got %u ptrs",
|
||||
mdbx_debug("not enough room in page %" PRIaPGNO ", got %u ptrs",
|
||||
mdbx_dbg_pgno(mp), NUMKEYS(mp));
|
||||
mdbx_debug("upper-lower = %u - %u = %" PRIiPTR "", mp->mp_upper, mp->mp_lower,
|
||||
room);
|
||||
@ -6503,7 +6497,7 @@ static void mdbx_node_del(MDB_cursor *mc, int ksize) {
|
||||
MDB_node *node;
|
||||
char *base;
|
||||
|
||||
mdbx_debug("delete node %u on %s page %" PRIuPTR "", indx,
|
||||
mdbx_debug("delete node %u on %s page %" PRIaPGNO "", indx,
|
||||
IS_LEAF(mp) ? "leaf" : "branch", mdbx_dbg_pgno(mp));
|
||||
numkeys = NUMKEYS(mp);
|
||||
mdbx_cassert(mc, indx < numkeys);
|
||||
@ -6651,7 +6645,7 @@ static void mdbx_xcursor_init1(MDB_cursor *mc, MDB_node *node) {
|
||||
mx->mx_db.md_flags |= MDB_INTEGERKEY;
|
||||
}
|
||||
}
|
||||
mdbx_debug("Sub-db -%u root page %" PRIuPTR "", mx->mx_cursor.mc_dbi,
|
||||
mdbx_debug("Sub-db -%u root page %" PRIaPGNO "", mx->mx_cursor.mc_dbi,
|
||||
mx->mx_db.md_root);
|
||||
mx->mx_dbflag = DB_VALID | DB_USRVALID | DB_DUPDATA;
|
||||
/* #if UINT_MAX < SIZE_MAX
|
||||
@ -6684,7 +6678,7 @@ static void mdbx_xcursor_init2(MDB_cursor *mc, MDB_xcursor *src_mx,
|
||||
}
|
||||
mx->mx_db = src_mx->mx_db;
|
||||
mx->mx_cursor.mc_pg[0] = src_mx->mx_cursor.mc_pg[0];
|
||||
mdbx_debug("Sub-db -%u root page %" PRIuPTR "", mx->mx_cursor.mc_dbi,
|
||||
mdbx_debug("Sub-db -%u root page %" PRIaPGNO "", mx->mx_cursor.mc_dbi,
|
||||
mx->mx_db.md_root);
|
||||
}
|
||||
|
||||
@ -6884,8 +6878,8 @@ static int mdbx_update_key(MDB_cursor *mc, MDB_val *key) {
|
||||
char kbuf2[DKBUF_MAXKEYSIZE * 2 + 1];
|
||||
k2.mv_data = NODEKEY(node);
|
||||
k2.mv_size = node->mn_ksize;
|
||||
mdbx_debug("update key %u (ofs %u) [%s] to [%s] on page %" PRIuPTR "", indx,
|
||||
ptr, mdbx_dkey(&k2, kbuf2, sizeof(kbuf2)), DKEY(key),
|
||||
mdbx_debug("update key %u (ofs %u) [%s] to [%s] on page %" PRIaPGNO "",
|
||||
indx, ptr, mdbx_dkey(&k2, kbuf2, sizeof(kbuf2)), DKEY(key),
|
||||
mp->mp_pgno);
|
||||
}
|
||||
|
||||
@ -7027,8 +7021,8 @@ static int mdbx_node_move(MDB_cursor *csrc, MDB_cursor *cdst, int fromleft) {
|
||||
return rc;
|
||||
}
|
||||
|
||||
mdbx_debug("moving %s node %u [%s] on page %" PRIuPTR
|
||||
" to node %u on page %" PRIuPTR "",
|
||||
mdbx_debug("moving %s node %u [%s] on page %" PRIaPGNO
|
||||
" to node %u on page %" PRIaPGNO "",
|
||||
IS_LEAF(csrc->mc_pg[csrc->mc_top]) ? "leaf" : "branch",
|
||||
csrc->mc_ki[csrc->mc_top], DKEY(&key),
|
||||
csrc->mc_pg[csrc->mc_top]->mp_pgno, cdst->mc_ki[cdst->mc_top],
|
||||
@ -7111,7 +7105,7 @@ static int mdbx_node_move(MDB_cursor *csrc, MDB_cursor *cdst, int fromleft) {
|
||||
key.mv_size = NODEKSZ(srcnode);
|
||||
key.mv_data = NODEKEY(srcnode);
|
||||
}
|
||||
mdbx_debug("update separator for source page %" PRIuPTR " to [%s]",
|
||||
mdbx_debug("update separator for source page %" PRIaPGNO " to [%s]",
|
||||
csrc->mc_pg[csrc->mc_top]->mp_pgno, DKEY(&key));
|
||||
mdbx_cursor_copy(csrc, &mn);
|
||||
mn.mc_snum--;
|
||||
@ -7141,7 +7135,7 @@ static int mdbx_node_move(MDB_cursor *csrc, MDB_cursor *cdst, int fromleft) {
|
||||
key.mv_size = NODEKSZ(srcnode);
|
||||
key.mv_data = NODEKEY(srcnode);
|
||||
}
|
||||
mdbx_debug("update separator for destination page %" PRIuPTR " to [%s]",
|
||||
mdbx_debug("update separator for destination page %" PRIaPGNO " to [%s]",
|
||||
cdst->mc_pg[cdst->mc_top]->mp_pgno, DKEY(&key));
|
||||
mdbx_cursor_copy(cdst, &mn);
|
||||
mn.mc_snum--;
|
||||
@ -7185,7 +7179,7 @@ static int mdbx_page_merge(MDB_cursor *csrc, MDB_cursor *cdst) {
|
||||
psrc = csrc->mc_pg[csrc->mc_top];
|
||||
pdst = cdst->mc_pg[cdst->mc_top];
|
||||
|
||||
mdbx_debug("merging page %" PRIuPTR " into %" PRIuPTR "", psrc->mp_pgno,
|
||||
mdbx_debug("merging page %" PRIaPGNO " into %" PRIaPGNO "", psrc->mp_pgno,
|
||||
pdst->mp_pgno);
|
||||
|
||||
mdbx_cassert(csrc, csrc->mc_snum > 1); /* can't merge root page */
|
||||
@ -7243,7 +7237,7 @@ static int mdbx_page_merge(MDB_cursor *csrc, MDB_cursor *cdst) {
|
||||
}
|
||||
}
|
||||
|
||||
mdbx_debug("dst page %" PRIuPTR " now has %u keys (%.1f%% filled)",
|
||||
mdbx_debug("dst page %" PRIaPGNO " now has %u keys (%.1f%% filled)",
|
||||
pdst->mp_pgno, NUMKEYS(pdst),
|
||||
(float)PAGEFILL(cdst->mc_txn->mt_env, pdst) / 10);
|
||||
|
||||
@ -7348,7 +7342,7 @@ static int mdbx_rebalance(MDB_cursor *mc) {
|
||||
minkeys = 1;
|
||||
thresh = FILL_THRESHOLD;
|
||||
}
|
||||
mdbx_debug("rebalancing %s page %" PRIuPTR " (has %u keys, %.1f%% full)",
|
||||
mdbx_debug("rebalancing %s page %" PRIaPGNO " (has %u keys, %.1f%% full)",
|
||||
IS_LEAF(mc->mc_pg[mc->mc_top]) ? "leaf" : "branch",
|
||||
mdbx_dbg_pgno(mc->mc_pg[mc->mc_top]),
|
||||
NUMKEYS(mc->mc_pg[mc->mc_top]),
|
||||
@ -7356,7 +7350,7 @@ static int mdbx_rebalance(MDB_cursor *mc) {
|
||||
|
||||
if (PAGEFILL(mc->mc_txn->mt_env, mc->mc_pg[mc->mc_top]) >= thresh &&
|
||||
NUMKEYS(mc->mc_pg[mc->mc_top]) >= minkeys) {
|
||||
mdbx_debug("no need to rebalance page %" PRIuPTR ", above fill threshold",
|
||||
mdbx_debug("no need to rebalance page %" PRIaPGNO ", above fill threshold",
|
||||
mdbx_dbg_pgno(mc->mc_pg[mc->mc_top]));
|
||||
return MDB_SUCCESS;
|
||||
}
|
||||
@ -7482,7 +7476,7 @@ static int mdbx_rebalance(MDB_cursor *mc) {
|
||||
fromleft = 1;
|
||||
}
|
||||
|
||||
mdbx_debug("found neighbor page %" PRIuPTR " (%u keys, %.1f%% full)",
|
||||
mdbx_debug("found neighbor page %" PRIaPGNO " (%u keys, %.1f%% full)",
|
||||
mn.mc_pg[mn.mc_top]->mp_pgno, NUMKEYS(mn.mc_pg[mn.mc_top]),
|
||||
(float)PAGEFILL(mc->mc_txn->mt_env, mn.mc_pg[mn.mc_top]) / 10);
|
||||
|
||||
@ -7692,7 +7686,7 @@ static int mdbx_page_split(MDB_cursor *mc, MDB_val *newkey, MDB_val *newdata,
|
||||
newindx = mc->mc_ki[mc->mc_top];
|
||||
nkeys = NUMKEYS(mp);
|
||||
|
||||
mdbx_debug("-----> splitting %s page %" PRIuPTR
|
||||
mdbx_debug("-----> splitting %s page %" PRIaPGNO
|
||||
" and adding [%s] at index %i/%i",
|
||||
IS_LEAF(mp) ? "leaf" : "branch", mp->mp_pgno, DKEY(newkey),
|
||||
mc->mc_ki[mc->mc_top], nkeys);
|
||||
@ -7701,7 +7695,7 @@ static int mdbx_page_split(MDB_cursor *mc, MDB_val *newkey, MDB_val *newdata,
|
||||
if ((rc = mdbx_page_new(mc, mp->mp_flags, 1, &rp)))
|
||||
return rc;
|
||||
rp->mp_leaf2_ksize = mp->mp_leaf2_ksize;
|
||||
mdbx_debug("new right sibling: page %" PRIuPTR "", rp->mp_pgno);
|
||||
mdbx_debug("new right sibling: page %" PRIaPGNO "", rp->mp_pgno);
|
||||
|
||||
/* Usually when splitting the root page, the cursor
|
||||
* height is 1. But when called from mdbx_update_key,
|
||||
@ -7718,7 +7712,7 @@ static int mdbx_page_split(MDB_cursor *mc, MDB_val *newkey, MDB_val *newdata,
|
||||
mc->mc_pg[0] = pp;
|
||||
mc->mc_ki[0] = 0;
|
||||
mc->mc_db->md_root = pp->mp_pgno;
|
||||
mdbx_debug("root split! new root = %" PRIuPTR "", pp->mp_pgno);
|
||||
mdbx_debug("root split! new root = %" PRIaPGNO "", pp->mp_pgno);
|
||||
new_root = mc->mc_db->md_depth++;
|
||||
|
||||
/* Add left (implicit) pointer. */
|
||||
@ -7736,7 +7730,7 @@ static int mdbx_page_split(MDB_cursor *mc, MDB_val *newkey, MDB_val *newdata,
|
||||
ptop = 0;
|
||||
} else {
|
||||
ptop = mc->mc_top - 1;
|
||||
mdbx_debug("parent branch page is %" PRIuPTR "", mc->mc_pg[ptop]->mp_pgno);
|
||||
mdbx_debug("parent branch page is %" PRIaPGNO "", mc->mc_pg[ptop]->mp_pgno);
|
||||
}
|
||||
|
||||
mdbx_cursor_copy(mc, &mn);
|
||||
@ -8421,14 +8415,13 @@ static int __cold mdbx_env_compact(MDB_env *env, mdbx_filehandle_t fd) {
|
||||
root = new_root = txn->mt_dbs[MAIN_DBI].md_root;
|
||||
if (root != P_INVALID) {
|
||||
/* Count free pages + freeDB pages. Subtract from last_pg
|
||||
* to find the new last_pg, which also becomes the new root.
|
||||
*/
|
||||
MDB_ID freecount = 0;
|
||||
* to find the new last_pg, which also becomes the new root. */
|
||||
pgno_t freecount = 0;
|
||||
MDB_cursor mc;
|
||||
MDB_val key, data;
|
||||
mdbx_cursor_init(&mc, txn, FREE_DBI, NULL);
|
||||
while ((rc = mdbx_cursor_get(&mc, &key, &data, MDB_NEXT)) == 0)
|
||||
freecount += *(MDB_ID *)data.mv_data;
|
||||
freecount += *(pgno_t *)data.mv_data;
|
||||
if (rc != MDB_NOTFOUND)
|
||||
goto finish;
|
||||
freecount += txn->mt_dbs[FREE_DBI].md_branch_pages +
|
||||
@ -9138,11 +9131,11 @@ int __cold mdbx_reader_list(MDB_env *env, MDB_msg_func *func, void *ctx) {
|
||||
if (mr[i].mr_pid) {
|
||||
txnid_t txnid = mr[i].mr_txnid;
|
||||
if (txnid == ~(txnid_t)0)
|
||||
snprintf(buf, sizeof(buf), "%10d %" PRIxPTR " -\n", (int)mr[i].mr_pid,
|
||||
(size_t)mr[i].mr_tid);
|
||||
snprintf(buf, sizeof(buf), "%10" PRIuPTR " %" PRIxPTR " -\n",
|
||||
(size_t)mr[i].mr_pid, (size_t)mr[i].mr_tid);
|
||||
else
|
||||
snprintf(buf, sizeof(buf), "%10d %" PRIxPTR " %" PRIuPTR "\n",
|
||||
(int)mr[i].mr_pid, (size_t)mr[i].mr_tid, txnid);
|
||||
snprintf(buf, sizeof(buf), "%10" PRIuPTR " %" PRIxPTR " %" PRIaTXN "\n",
|
||||
(size_t)mr[i].mr_pid, (size_t)mr[i].mr_tid, txnid);
|
||||
|
||||
if (first) {
|
||||
first = 0;
|
||||
@ -9264,8 +9257,8 @@ int __cold mdbx_reader_check0(MDB_env *env, int rdt_locked, int *dead) {
|
||||
/* clean it */
|
||||
for (unsigned j = i; j < snap_nreaders; j++) {
|
||||
if (mr[j].mr_pid == pid) {
|
||||
mdbx_debug("clear stale reader pid %u txn %" PRIiPTR "", (unsigned)pid,
|
||||
mr[j].mr_txnid);
|
||||
mdbx_debug("clear stale reader pid %" PRIuPTR " txn %" PRIaTXN "",
|
||||
(size_t)pid, mr[j].mr_txnid);
|
||||
mr[j].mr_pid = 0;
|
||||
count++;
|
||||
}
|
||||
@ -9280,9 +9273,8 @@ int __cold mdbx_reader_check0(MDB_env *env, int rdt_locked, int *dead) {
|
||||
return rc;
|
||||
}
|
||||
|
||||
static unsigned __hot mdbx_midl_search(MDB_IDL ids, MDB_ID id) {
|
||||
/*
|
||||
* binary search of id in ids
|
||||
static unsigned __hot mdbx_midl_search(MDB_IDL ids, pgno_t id) {
|
||||
/* binary search of id in ids
|
||||
* if found, returns position of id
|
||||
* if not found, returns first position greater than id */
|
||||
unsigned base = 0;
|
||||
@ -9312,8 +9304,8 @@ static unsigned __hot mdbx_midl_search(MDB_IDL ids, MDB_ID id) {
|
||||
}
|
||||
|
||||
static MDB_IDL mdbx_midl_alloc(int num) {
|
||||
MDB_IDL ids = malloc((num + 2) * sizeof(MDB_ID));
|
||||
if (ids) {
|
||||
MDB_IDL ids = malloc((num + 2) * sizeof(pgno_t));
|
||||
if (likely(ids)) {
|
||||
*ids++ = num;
|
||||
*ids = 0;
|
||||
}
|
||||
@ -9326,19 +9318,22 @@ static void mdbx_midl_free(MDB_IDL ids) {
|
||||
}
|
||||
|
||||
static void mdbx_midl_shrink(MDB_IDL *idp) {
|
||||
MDB_IDL ids = *idp;
|
||||
if (*(--ids) > MDB_IDL_UM_MAX &&
|
||||
(ids = realloc(ids, (MDB_IDL_UM_MAX + 2) * sizeof(MDB_ID)))) {
|
||||
*ids++ = MDB_IDL_UM_MAX;
|
||||
*idp = ids;
|
||||
MDB_IDL ids = *idp - 1;
|
||||
if (unlikely(*ids > MDB_IDL_UM_MAX)) {
|
||||
/* shrink to MDB_IDL_UM_MAX */
|
||||
ids = realloc(ids, (MDB_IDL_UM_MAX + 2) * sizeof(pgno_t));
|
||||
if (likely(ids)) {
|
||||
*ids++ = MDB_IDL_UM_MAX;
|
||||
*idp = ids;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int mdbx_midl_grow(MDB_IDL *idp, int num) {
|
||||
MDB_IDL idn = *idp - 1;
|
||||
/* grow it */
|
||||
idn = realloc(idn, (*idn + num + 2) * sizeof(MDB_ID));
|
||||
if (!idn)
|
||||
idn = realloc(idn, (*idn + num + 2) * sizeof(pgno_t));
|
||||
if (unlikely(!idn))
|
||||
return MDBX_ENOMEM;
|
||||
*idn++ += num;
|
||||
*idp = idn;
|
||||
@ -9350,7 +9345,8 @@ static int mdbx_midl_need(MDB_IDL *idp, unsigned num) {
|
||||
num += ids[0];
|
||||
if (num > ids[-1]) {
|
||||
num = (num + num / 4 + (256 + 2)) & -256;
|
||||
if (!(ids = realloc(ids - 1, num * sizeof(MDB_ID))))
|
||||
ids = realloc(ids - 1, num * sizeof(pgno_t));
|
||||
if (unlikely(!ids))
|
||||
return MDBX_ENOMEM;
|
||||
*ids++ = num - 2;
|
||||
*idp = ids;
|
||||
@ -9358,7 +9354,7 @@ static int mdbx_midl_need(MDB_IDL *idp, unsigned num) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int mdbx_midl_append(MDB_IDL *idp, MDB_ID id) {
|
||||
static int mdbx_midl_append(MDB_IDL *idp, pgno_t id) {
|
||||
MDB_IDL ids = *idp;
|
||||
/* Too big? */
|
||||
if (ids[0] >= ids[-1]) {
|
||||
@ -9379,13 +9375,13 @@ static int mdbx_midl_append_list(MDB_IDL *idp, MDB_IDL app) {
|
||||
return MDBX_ENOMEM;
|
||||
ids = *idp;
|
||||
}
|
||||
memcpy(&ids[ids[0] + 1], &app[1], app[0] * sizeof(MDB_ID));
|
||||
memcpy(&ids[ids[0] + 1], &app[1], app[0] * sizeof(pgno_t));
|
||||
ids[0] += app[0];
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int mdbx_midl_append_range(MDB_IDL *idp, MDB_ID id, unsigned n) {
|
||||
MDB_ID *ids = *idp, len = ids[0];
|
||||
static int mdbx_midl_append_range(MDB_IDL *idp, pgno_t id, unsigned n) {
|
||||
pgno_t *ids = *idp, len = ids[0];
|
||||
/* Too big? */
|
||||
if (len + n > ids[-1]) {
|
||||
if (mdbx_midl_grow(idp, n | MDB_IDL_UM_MAX))
|
||||
@ -9400,8 +9396,8 @@ static int mdbx_midl_append_range(MDB_IDL *idp, MDB_ID id, unsigned n) {
|
||||
}
|
||||
|
||||
static void __hot mdbx_midl_xmerge(MDB_IDL idl, MDB_IDL merge) {
|
||||
MDB_ID old_id, merge_id, i = merge[0], j = idl[0], k = i + j, total = k;
|
||||
idl[0] = (MDB_ID)-1; /* delimiter for idl scan below */
|
||||
pgno_t old_id, merge_id, i = merge[0], j = idl[0], k = i + j, total = k;
|
||||
idl[0] = ~(pgno_t)0; /* delimiter for idl scan below */
|
||||
old_id = idl[j];
|
||||
while (i) {
|
||||
merge_id = merge[i--];
|
||||
@ -9413,11 +9409,10 @@ static void __hot mdbx_midl_xmerge(MDB_IDL idl, MDB_IDL merge) {
|
||||
}
|
||||
|
||||
/* Quicksort + Insertion sort for small arrays */
|
||||
|
||||
#define SMALL 8
|
||||
#define MIDL_SWAP(a, b) \
|
||||
{ \
|
||||
MDB_ID itmp = (a); \
|
||||
pgno_t itmp = (a); \
|
||||
(a) = (b); \
|
||||
(b) = itmp; \
|
||||
}
|
||||
@ -9426,7 +9421,7 @@ static void __hot mdbx_midl_sort(MDB_IDL ids) {
|
||||
/* Max possible depth of int-indexed tree * 2 items/level */
|
||||
int istack[sizeof(int) * CHAR_BIT * 2];
|
||||
int i, j, k, l, ir, jstack;
|
||||
MDB_ID a;
|
||||
pgno_t a;
|
||||
|
||||
ir = (int)ids[0];
|
||||
l = 1;
|
||||
@ -9488,9 +9483,8 @@ static void __hot mdbx_midl_sort(MDB_IDL ids) {
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned __hot mdbx_mid2l_search(MDB_ID2L ids, MDB_ID id) {
|
||||
/*
|
||||
* binary search of id in ids
|
||||
static unsigned __hot mdbx_mid2l_search(MDB_ID2L ids, pgno_t id) {
|
||||
/* binary search of id in ids
|
||||
* if found, returns position of id
|
||||
* if not found, returns first position greater than id */
|
||||
unsigned base = 0;
|
||||
|
@ -13,7 +13,7 @@
|
||||
*/
|
||||
|
||||
/* IDL sizes - likely should be even bigger
|
||||
* limiting factors: sizeof(ID), thread stack size */
|
||||
* limiting factors: sizeof(pgno_t), thread stack size */
|
||||
#define MDB_IDL_LOGN 16 /* DB_SIZE is 2^16, UM_SIZE is 2^17 */
|
||||
#define MDB_IDL_DB_SIZE (1 << MDB_IDL_LOGN)
|
||||
#define MDB_IDL_UM_SIZE (1 << (MDB_IDL_LOGN + 1))
|
||||
@ -21,7 +21,7 @@
|
||||
#define MDB_IDL_DB_MAX (MDB_IDL_DB_SIZE - 1)
|
||||
#define MDB_IDL_UM_MAX (MDB_IDL_UM_SIZE - 1)
|
||||
|
||||
#define MDB_IDL_SIZEOF(ids) (((ids)[0] + 1) * sizeof(MDB_ID))
|
||||
#define MDB_IDL_SIZEOF(ids) (((ids)[0] + 1) * sizeof(pgno_t))
|
||||
#define MDB_IDL_IS_ZERO(ids) ((ids)[0] == 0)
|
||||
#define MDB_IDL_CPY(dst, src) (memcpy(dst, src, MDB_IDL_SIZEOF(src)))
|
||||
#define MDB_IDL_FIRST(ids) ((ids)[1])
|
||||
@ -33,6 +33,6 @@
|
||||
/* Append ID to IDL. The IDL must be big enough. */
|
||||
#define mdbx_midl_xappend(idl, id) \
|
||||
do { \
|
||||
MDB_ID *xidl = (idl), xlen = ++(xidl[0]); \
|
||||
pgno_t *xidl = (idl), xlen = ++(xidl[0]); \
|
||||
xidl[xlen] = (id); \
|
||||
} while (0)
|
||||
|
@ -26,6 +26,7 @@
|
||||
#include <unistd.h>
|
||||
|
||||
#include "../../mdbx.h"
|
||||
#include "../bits.h"
|
||||
#include "../midl.h"
|
||||
|
||||
typedef struct flagbit {
|
||||
@ -316,17 +317,18 @@ static int handle_userdb(const size_t record_number, const MDB_val *key,
|
||||
static int handle_freedb(const size_t record_number, const MDB_val *key,
|
||||
const MDB_val *data) {
|
||||
char *bad = "";
|
||||
size_t pg, prev;
|
||||
pgno_t pg, prev;
|
||||
ssize_t i, number, span = 0;
|
||||
size_t *iptr = data->mv_data, txnid = *(size_t *)key->mv_data;
|
||||
pgno_t *iptr = data->mv_data;
|
||||
txnid_t txnid = *(txnid_t *)key->mv_data;
|
||||
|
||||
if (key->mv_size != sizeof(txnid))
|
||||
if (key->mv_size != sizeof(txnid_t))
|
||||
problem_add("entry", record_number, "wrong txn-id size",
|
||||
"key-size %" PRIiPTR "", key->mv_size);
|
||||
else if (txnid < 1 || txnid > envinfo.me_last_txnid)
|
||||
problem_add("entry", record_number, "wrong txn-id", "%" PRIuPTR "", txnid);
|
||||
problem_add("entry", record_number, "wrong txn-id", "%" PRIaTXN "", txnid);
|
||||
|
||||
if (data->mv_size < sizeof(size_t) || data->mv_size % sizeof(size_t))
|
||||
if (data->mv_size < sizeof(pgno_t) || data->mv_size % sizeof(pgno_t))
|
||||
problem_add("entry", record_number, "wrong idl size", "%" PRIuPTR "",
|
||||
data->mv_size);
|
||||
else {
|
||||
@ -334,9 +336,9 @@ static int handle_freedb(const size_t record_number, const MDB_val *key,
|
||||
if (number >= MDB_IDL_UM_MAX)
|
||||
problem_add("entry", record_number, "wrong idl length", "%" PRIiPTR "",
|
||||
number);
|
||||
else if ((number + 1) * sizeof(size_t) != data->mv_size)
|
||||
else if ((number + 1) * sizeof(pgno_t) != data->mv_size)
|
||||
problem_add("entry", record_number, "mismatch idl length",
|
||||
"%" PRIiPTR " != %" PRIuPTR "", number * sizeof(size_t),
|
||||
"%" PRIiPTR " != %" PRIuPTR "", (number + 1) * sizeof(pgno_t),
|
||||
data->mv_size);
|
||||
else {
|
||||
freedb_pages += number;
|
||||
@ -344,9 +346,9 @@ static int handle_freedb(const size_t record_number, const MDB_val *key,
|
||||
reclaimable_pages += number;
|
||||
for (i = number, prev = 1; --i >= 0;) {
|
||||
pg = iptr[i];
|
||||
if (pg < 2 /* META_PAGE */ || pg > envinfo.me_last_pgno)
|
||||
if (pg < NUM_METAS || pg > envinfo.me_last_pgno)
|
||||
problem_add("entry", record_number, "wrong idl entry",
|
||||
"2 < %" PRIiPTR " < %" PRIiPTR "", pg,
|
||||
"%u < %" PRIiPTR " < %" PRIiPTR "", NUM_METAS, pg,
|
||||
envinfo.me_last_pgno);
|
||||
else if (pg <= prev) {
|
||||
bad = " [bad sequence]";
|
||||
@ -359,7 +361,7 @@ static int handle_freedb(const size_t record_number, const MDB_val *key,
|
||||
;
|
||||
}
|
||||
if (verbose > 2 && !only_subdb) {
|
||||
print(" transaction %" PRIuPTR ", %" PRIiPTR
|
||||
print(" transaction %" PRIaTXN ", %" PRIiPTR
|
||||
" pages, maxspan %" PRIiPTR "%s\n",
|
||||
txnid, number, span, bad);
|
||||
if (verbose > 3) {
|
||||
@ -369,9 +371,9 @@ static int handle_freedb(const size_t record_number, const MDB_val *key,
|
||||
for (span = 1; --j >= 0 && iptr[j] == pg + span; span++)
|
||||
;
|
||||
if (span > 1)
|
||||
print(" %9zu[%" PRIiPTR "]\n", pg, span);
|
||||
print(" %9" PRIaPGNO "[%" PRIiPTR "]\n", pg, span);
|
||||
else
|
||||
print(" %9zu\n", pg);
|
||||
print(" %9" PRIaPGNO "\n", pg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user