Skip to content

Commit

Permalink
mdbx_0_10_3 (#33)
Browse files Browse the repository at this point in the history
  • Loading branch information
AskAlexSharov authored Sep 7, 2021
1 parent 22d7fdb commit f21495b
Show file tree
Hide file tree
Showing 2 changed files with 111 additions and 70 deletions.
131 changes: 71 additions & 60 deletions mdbx/mdbx.c
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
* <http://www.OpenLDAP.org/license.html>. */

#define xMDBX_ALLOY 1
#define MDBX_BUILD_SOURCERY 4c0edad9e694f89ccb919dbe9a40cc1c9570bde6d8b72ba610260ffb4f5c608f_v0_10_2_0_g70933d81
#define MDBX_BUILD_SOURCERY 3917b803f28da617e8accc6ee369d6f4b1eb6353bd8281b3c0f43b8500c5eb92_v0_10_3_1_gc714ee9b
#ifdef MDBX_CONFIG_H
#include MDBX_CONFIG_H
#endif
Expand Down Expand Up @@ -15256,59 +15256,58 @@ __cold static int mdbx_setup_dxb(MDBX_env *env, const int lck_rc,
}
}

//------------------------------------------------- setup madvise/readahead
atomic_store32(&env->me_lck->mti_discarded_tail,
bytes2pgno(env, used_aligned2os_bytes), mo_Relaxed);
} /* lck exclusive, lck_rc == MDBX_RESULT_TRUE */

//---------------------------------------------------- setup madvise/readahead
#if MDBX_ENABLE_MADVISE
if (used_aligned2os_bytes < env->me_dxb_mmap.current) {
if (used_aligned2os_bytes < env->me_dxb_mmap.current) {
#if defined(MADV_REMOVE)
if ((env->me_flags & MDBX_WRITEMAP) != 0 &&
/* not recovery mode */ env->me_stuck_meta < 0) {
mdbx_notice("open-MADV_%s %u..%u", "REMOVE (deallocate file space)",
env->me_lck->mti_discarded_tail.weak,
bytes2pgno(env, env->me_dxb_mmap.current));
err = madvise(env->me_map + used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes,
MADV_REMOVE)
? ignore_enosys(errno)
: MDBX_SUCCESS;
if (unlikely(MDBX_IS_ERROR(err)))
return err;
}
#endif /* MADV_REMOVE */
#if defined(MADV_DONTNEED)
mdbx_notice("open-MADV_%s %u..%u", "DONTNEED",
if (lck_rc && (env->me_flags & MDBX_WRITEMAP) != 0 &&
/* not recovery mode */ env->me_stuck_meta < 0) {
mdbx_notice("open-MADV_%s %u..%u", "REMOVE (deallocate file space)",
env->me_lck->mti_discarded_tail.weak,
bytes2pgno(env, env->me_dxb_mmap.current));
err = madvise(env->me_map + used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes,
MADV_DONTNEED)
? ignore_enosys(errno)
: MDBX_SUCCESS;
err =
madvise(env->me_map + used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes, MADV_REMOVE)
? ignore_enosys(errno)
: MDBX_SUCCESS;
if (unlikely(MDBX_IS_ERROR(err)))
return err;
}
#endif /* MADV_REMOVE */
#if defined(MADV_DONTNEED)
mdbx_notice("open-MADV_%s %u..%u", "DONTNEED",
env->me_lck->mti_discarded_tail.weak,
bytes2pgno(env, env->me_dxb_mmap.current));
err =
madvise(env->me_map + used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes, MADV_DONTNEED)
? ignore_enosys(errno)
: MDBX_SUCCESS;
if (unlikely(MDBX_IS_ERROR(err)))
return err;
#elif defined(POSIX_MADV_DONTNEED)
err = ignore_enosys(
posix_madvise(env->me_map + used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes,
POSIX_MADV_DONTNEED));
if (unlikely(MDBX_IS_ERROR(err)))
return err;
err = ignore_enosys(posix_madvise(
env->me_map + used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes, POSIX_MADV_DONTNEED));
if (unlikely(MDBX_IS_ERROR(err)))
return err;
#elif defined(POSIX_FADV_DONTNEED)
err = ignore_enosys(
posix_fadvise(env->me_lazy_fd, used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes,
POSIX_FADV_DONTNEED));
if (unlikely(MDBX_IS_ERROR(err)))
return err;
err = ignore_enosys(posix_fadvise(
env->me_lazy_fd, used_aligned2os_bytes,
env->me_dxb_mmap.current - used_aligned2os_bytes, POSIX_FADV_DONTNEED));
if (unlikely(MDBX_IS_ERROR(err)))
return err;
#endif /* MADV_DONTNEED */
}
}

err = mdbx_set_readahead(env, bytes2pgno(env, used_bytes), readahead, true);
if (unlikely(err != MDBX_SUCCESS))
return err;
err = mdbx_set_readahead(env, bytes2pgno(env, used_bytes), readahead, true);
if (unlikely(err != MDBX_SUCCESS))
return err;
#endif /* MDBX_ENABLE_MADVISE */
} /* lck exclusive, lck_rc == MDBX_RESULT_TRUE */

return rc;
}
Expand Down Expand Up @@ -16327,33 +16326,36 @@ static int __hot cmp_int_unaligned(const MDBX_val *a, const MDBX_val *b) {
/* Compare two items lexically */
static int __hot cmp_lexical(const MDBX_val *a, const MDBX_val *b) {
if (a->iov_len == b->iov_len)
return memcmp(a->iov_base, b->iov_base, a->iov_len);
return a->iov_len ? memcmp(a->iov_base, b->iov_base, a->iov_len) : 0;

const int diff_len = (a->iov_len < b->iov_len) ? -1 : 1;
const size_t shortest = (a->iov_len < b->iov_len) ? a->iov_len : b->iov_len;
int diff_data = memcmp(a->iov_base, b->iov_base, shortest);
int diff_data = shortest ? memcmp(a->iov_base, b->iov_base, shortest) : 0;
return likely(diff_data) ? diff_data : diff_len;
}

/* Compare two items in reverse byte order */
static int __hot cmp_reverse(const MDBX_val *a, const MDBX_val *b) {
const uint8_t *pa = (const uint8_t *)a->iov_base + a->iov_len;
const uint8_t *pb = (const uint8_t *)b->iov_base + b->iov_len;
const size_t shortest = (a->iov_len < b->iov_len) ? a->iov_len : b->iov_len;

const uint8_t *const end = pa - shortest;
while (pa != end) {
int diff = *--pa - *--pb;
if (likely(diff))
return diff;
if (likely(shortest)) {
const uint8_t *pa = (const uint8_t *)a->iov_base + a->iov_len;
const uint8_t *pb = (const uint8_t *)b->iov_base + b->iov_len;
const uint8_t *const end = pa - shortest;
do {
int diff = *--pa - *--pb;
if (likely(diff))
return diff;
} while (pa != end);
}
return CMP2INT(a->iov_len, b->iov_len);
}

/* Fast non-lexically comparator */
static int __hot cmp_lenfast(const MDBX_val *a, const MDBX_val *b) {
int diff = CMP2INT(a->iov_len, b->iov_len);
return likely(diff) ? diff : memcmp(a->iov_base, b->iov_base, a->iov_len);
return likely(diff || a->iov_len == 0)
? diff
: memcmp(a->iov_base, b->iov_base, a->iov_len);
}

static bool unsure_equal(MDBX_cmp_func cmp, const MDBX_val *a,
Expand Down Expand Up @@ -16943,8 +16945,10 @@ int mdbx_get_ex(MDBX_txn *txn, MDBX_dbi dbi, MDBX_val *key, MDBX_val *data,
MDBX_node *node = page_node(cx.outer.mc_pg[cx.outer.mc_top],
cx.outer.mc_ki[cx.outer.mc_top]);
if (F_ISSET(node_flags(node), F_DUPDATA)) {
// coverity[uninit_use : FALSE]
mdbx_tassert(txn, cx.outer.mc_xcursor == &cx.inner &&
(cx.inner.mx_cursor.mc_flags & C_INITIALIZED));
// coverity[uninit_use : FALSE]
*values_count =
(sizeof(*values_count) >= sizeof(cx.inner.mx_db.md_entries) ||
cx.inner.mx_db.md_entries <= PTRDIFF_MAX)
Expand Down Expand Up @@ -20692,18 +20696,20 @@ __cold static int mdbx_page_check(MDBX_cursor *const mc,
break;
case F_DUPDATA /* short sub-page */:
if (unlikely(dsize <= PAGEHDRSZ)) {
rc = bad_page(mp, "invalid nested-page record size (%zu)\n", dsize);
rc = bad_page(mp, "invalid nested/sub-page record size (%zu)\n",
dsize);
continue;
} else {
const MDBX_page *const sp = (MDBX_page *)data;
const char *const end_of_subpage = data + dsize;
const int nsubkeys = page_numkeys(sp);
switch (sp->mp_flags) {
switch (sp->mp_flags & /* ignore legacy P_DIRTY flag */ ~0x10) {
case P_LEAF | P_SUBP:
case P_LEAF | P_LEAF2 | P_SUBP:
break;
default:
rc = bad_page(mp, "invalid nested-page flags (%u)\n", sp->mp_flags);
rc = bad_page(mp, "invalid nested/sub-page flags (0x%02x)\n",
sp->mp_flags);
continue;
}

Expand Down Expand Up @@ -23964,7 +23970,7 @@ __cold static int mdbx_walk_tree(mdbx_walk_ctx_t *ctx, const pgno_t pgno,
size_t subalign_bytes = 0;
MDBX_page_type_t subtype;

switch (sp->mp_flags) {
switch (sp->mp_flags & /* ignore legacy P_DIRTY flag */ ~0x10) {
case P_LEAF | P_SUBP:
subtype = MDBX_subpage_leaf;
break;
Expand Down Expand Up @@ -27547,6 +27553,7 @@ retry_mapview:;

if (limit < map->limit) {
/* unmap an excess at end of mapping. */
// coverity[offset_free : FALSE]
if (unlikely(munmap(map->dxb + limit, map->limit - limit)))
return errno;
map->limit = limit;
Expand Down Expand Up @@ -27620,6 +27627,7 @@ retry_mapview:;
if (unlikely(munmap(map->address, map->limit)))
return errno;

// coverity[pass_freed_arg : FALSE]
ptr = mmap(map->address, limit, mmap_prot,
(flags & MDBX_MRESIZE_MAY_MOVE)
? mmap_flags
Expand All @@ -27629,11 +27637,13 @@ retry_mapview:;
if (MAP_FIXED_NOREPLACE != 0 && MAP_FIXED_NOREPLACE != MAP_FIXED &&
unlikely(ptr == MAP_FAILED) && !(flags & MDBX_MRESIZE_MAY_MOVE) &&
errno == /* kernel don't support MAP_FIXED_NOREPLACE */ EINVAL)
// coverity[pass_freed_arg : FALSE]
ptr = mmap(map->address, limit, mmap_prot, mmap_flags | MAP_FIXED,
map->fd, 0);

if (unlikely(ptr == MAP_FAILED)) {
/* try to restore prev mapping */
// coverity[pass_freed_arg : FALSE]
ptr = mmap(map->address, map->limit, mmap_prot,
(flags & MDBX_MRESIZE_MAY_MOVE)
? mmap_flags
Expand All @@ -27643,6 +27653,7 @@ retry_mapview:;
if (MAP_FIXED_NOREPLACE != 0 && MAP_FIXED_NOREPLACE != MAP_FIXED &&
unlikely(ptr == MAP_FAILED) && !(flags & MDBX_MRESIZE_MAY_MOVE) &&
errno == /* kernel don't support MAP_FIXED_NOREPLACE */ EINVAL)
// coverity[pass_freed_arg : FALSE]
ptr = mmap(map->address, map->limit, mmap_prot, mmap_flags | MAP_FIXED,
map->fd, 0);
if (unlikely(ptr == MAP_FAILED)) {
Expand Down Expand Up @@ -28407,10 +28418,10 @@ __dll_export
const struct MDBX_version_info mdbx_version = {
0,
10,
2,
0,
{"2021-07-26T05:23:52+03:00", "3db98a1d3d2364d8cb260df82f1150932547e4b9", "70933d81a86128d6a6f14d7102a9544e4f1807b2",
"v0.10.2-0-g70933d81"},
3,
1,
{"2021-09-03T23:10:22+03:00", "65f29a1cfa62516b31ebf0595fdccb5c5069dc31", "c714ee9b555e03d5892ff57c8c0d460d06950ddb",
"v0.10.3-1-gc714ee9b"},
sourcery};

__dll_export
Expand Down
50 changes: 40 additions & 10 deletions mdbx/mdbx.h
Original file line number Diff line number Diff line change
Expand Up @@ -461,7 +461,8 @@ typedef mode_t mdbx_mode_t;
#endif /* MDBX_PRINTF_ARGS */

#if defined(DOXYGEN) || \
(defined(__cplusplus) && __has_cpp_attribute(maybe_unused) && \
(defined(__cplusplus) && __cplusplus >= 201603 && \
__has_cpp_attribute(maybe_unused) && \
__has_cpp_attribute(maybe_unused) >= 201603) || \
(!defined(__cplusplus) && defined(__STDC_VERSION__) && \
__STDC_VERSION__ > 202005L)
Expand All @@ -472,6 +473,12 @@ typedef mode_t mdbx_mode_t;
#define MDBX_MAYBE_UNUSED
#endif /* MDBX_MAYBE_UNUSED */

#if __has_attribute(no_sanitize)
#define MDBX_NOSANITIZE_ENUM __attribute((__no_sanitize__("enum")))
#else
#define MDBX_NOSANITIZE_ENUM
#endif /* MDBX_NOSANITIZE_ENUM */

/* Oh, below are some songs and dances since:
* - C++ requires explicit definition of the necessary operators.
* - the proper implementation of DEFINE_ENUM_FLAG_OPERATORS for C++ required
Expand All @@ -497,28 +504,40 @@ typedef mode_t mdbx_mode_t;
/// used to define flags (based on Microsoft's DEFINE_ENUM_FLAG_OPERATORS).
#define DEFINE_ENUM_FLAG_OPERATORS(ENUM) \
extern "C++" { \
MDBX_CXX01_CONSTEXPR ENUM operator|(ENUM a, ENUM b) { \
MDBX_NOSANITIZE_ENUM MDBX_CXX01_CONSTEXPR ENUM operator|(ENUM a, ENUM b) { \
return ENUM(unsigned(a) | unsigned(b)); \
} \
MDBX_CXX14_CONSTEXPR ENUM &operator|=(ENUM &a, ENUM b) { return a = a | b; } \
MDBX_CXX01_CONSTEXPR ENUM operator&(ENUM a, ENUM b) { \
MDBX_NOSANITIZE_ENUM MDBX_CXX14_CONSTEXPR ENUM &operator|=(ENUM &a, \
ENUM b) { \
return a = a | b; \
} \
MDBX_NOSANITIZE_ENUM MDBX_CXX01_CONSTEXPR ENUM operator&(ENUM a, ENUM b) { \
return ENUM(unsigned(a) & unsigned(b)); \
} \
MDBX_CXX01_CONSTEXPR ENUM operator&(ENUM a, unsigned b) { \
MDBX_NOSANITIZE_ENUM MDBX_CXX01_CONSTEXPR ENUM operator&(ENUM a, \
unsigned b) { \
return ENUM(unsigned(a) & b); \
} \
MDBX_CXX01_CONSTEXPR ENUM operator&(unsigned a, ENUM b) { \
MDBX_NOSANITIZE_ENUM MDBX_CXX01_CONSTEXPR ENUM operator&(unsigned a, \
ENUM b) { \
return ENUM(a & unsigned(b)); \
} \
MDBX_CXX14_CONSTEXPR ENUM &operator&=(ENUM &a, ENUM b) { return a = a & b; } \
MDBX_CXX14_CONSTEXPR ENUM &operator&=(ENUM &a, unsigned b) { \
MDBX_NOSANITIZE_ENUM MDBX_CXX14_CONSTEXPR ENUM &operator&=(ENUM &a, \
ENUM b) { \
return a = a & b; \
} \
MDBX_NOSANITIZE_ENUM MDBX_CXX14_CONSTEXPR ENUM &operator&=(ENUM &a, \
unsigned b) { \
return a = a & b; \
} \
MDBX_CXX01_CONSTEXPR unsigned operator~(ENUM a) { return ~unsigned(a); } \
MDBX_CXX01_CONSTEXPR ENUM operator^(ENUM a, ENUM b) { \
MDBX_NOSANITIZE_ENUM MDBX_CXX01_CONSTEXPR ENUM operator^(ENUM a, ENUM b) { \
return ENUM(unsigned(a) ^ unsigned(b)); \
} \
MDBX_CXX14_CONSTEXPR ENUM &operator^=(ENUM &a, ENUM b) { return a = a ^ b; } \
MDBX_NOSANITIZE_ENUM MDBX_CXX14_CONSTEXPR ENUM &operator^=(ENUM &a, \
ENUM b) { \
return a = a ^ b; \
} \
}
#else /* __cplusplus */
/* nope for C since it always allows these operators for enums */
Expand Down Expand Up @@ -790,6 +809,10 @@ enum MDBX_log_level_t {
and all other log-messages */
MDBX_LOG_EXTRA = 7,

#ifdef ENABLE_UBSAN
MDBX_LOG_MAX = 7 /* avoid UBSAN false-positive trap by a tests */,
#endif /* ENABLE_UBSAN */

/** for \ref mdbx_setup_debug() only: Don't change current settings */
MDBX_LOG_DONTCHANGE = -1
};
Expand All @@ -803,6 +826,8 @@ typedef enum MDBX_log_level_t MDBX_log_level_t;
* effect, but `MDBX_DBG_ASSERT`, `MDBX_DBG_AUDIT` and `MDBX_DBG_JITTER` only if
* libmdbx builded with \ref MDBX_DEBUG. */
enum MDBX_debug_flags_t {
MDBX_DBG_NONE = 0,

/** Enable assertion checks.
* Requires build with \ref MDBX_DEBUG > 0 */
MDBX_DBG_ASSERT = 1,
Expand All @@ -825,6 +850,11 @@ enum MDBX_debug_flags_t {
/** Allow read and write transactions overlapping for the same thread */
MDBX_DBG_LEGACY_OVERLAP = 32,

#ifdef ENABLE_UBSAN
MDBX_DBG_MAX = ((unsigned)MDBX_LOG_MAX) << 16 |
63 /* avoid UBSAN false-positive trap by a tests */,
#endif /* ENABLE_UBSAN */

/** for mdbx_setup_debug() only: Don't change current settings */
MDBX_DBG_DONTCHANGE = -1
};
Expand Down

0 comments on commit f21495b

Please sign in to comment.