text: /* https://en.wikipedia.org/wiki/Operating_system_abstraction_layer */
  
  /*
   * Copyright 2015-2022 Leonid Yuriev <leo@yuriev.ru>
   * and other libmdbx authors: please see AUTHORS file.
   * All rights reserved.
   *
   * Redistribution and use in source and binary forms, with or without
   * modification, are permitted only as authorized by the OpenLDAP
   * Public License.
   *
   * A copy of this license is available in the file LICENSE in the
   * top-level directory of the distribution or, alternatively, at
   * <http://www.OpenLDAP.org/license.html>.
   */
  
  #pragma once
  
  /*----------------------------------------------------------------------------*/
  /* Microsoft compiler generates a lot of warning for self includes... */
  
  #ifdef _MSC_VER
  #pragma warning(push, 1)
  #pragma warning(disable : 4548) /* expression before comma has no effect;      \
                                     expected expression with side - effect */
  #pragma warning(disable : 4530) /* C++ exception handler used, but unwind      \
                                   * semantics are not enabled. Specify /EHsc */
  #pragma warning(disable : 4577) /* 'noexcept' used with no exception handling  \
                                   * mode specified; termination on exception is \
                                   * not guaranteed. Specify /EHsc */
  #endif                          /* _MSC_VER (warnings) */
  
  #if defined(_WIN32) || defined(_WIN64)
  #if !defined(_CRT_SECURE_NO_WARNINGS)
  #define _CRT_SECURE_NO_WARNINGS
  #endif /* _CRT_SECURE_NO_WARNINGS */
  #if !defined(_NO_CRT_STDIO_INLINE) && MDBX_BUILD_SHARED_LIBRARY &&             \
      !defined(xMDBX_TOOLS) && MDBX_WITHOUT_MSVC_CRT
  #define _NO_CRT_STDIO_INLINE
  #endif
  #elif !defined(_POSIX_C_SOURCE)
  #define _POSIX_C_SOURCE 200809L
  #endif /* Windows */
  
  /*----------------------------------------------------------------------------*/
  /* C99 includes */
  #include <inttypes.h>
  #include <stddef.h>
  #include <stdint.h>
  #include <stdlib.h>
  
  #include <assert.h>
  #include <fcntl.h>
  #include <limits.h>
  #include <stdio.h>
  #include <string.h>
  #include <time.h>
  
  /* C11' alignas() */
  #if __has_include(<stdalign.h>)
  #include <stdalign.h>
  #endif
  #if defined(alignas) || defined(__cplusplus)
  #define MDBX_ALIGNAS(N) alignas(N)
  #elif defined(__STDC_VERSION__) && __STDC_VERSION__ >= 201112L
  #define MDBX_ALIGNAS(N) _Alignas(N)
  #elif defined(_MSC_VER)
  #define MDBX_ALIGNAS(N) __declspec(align(N))
  #elif __has_attribute(__aligned__) || defined(__GNUC__)
  #define MDBX_ALIGNAS(N) __attribute__((__aligned__(N)))
  #else
  #error "FIXME: Required alignas() or equivalent."
  #endif /* MDBX_ALIGNAS */
  
  /*----------------------------------------------------------------------------*/
  /* Systems includes */
  
  #ifdef __APPLE__
  #include <TargetConditionals.h>
  #endif /* Apple OSX & iOS */
  
  #if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) ||     \
      defined(__BSD__) || defined(__bsdi__) || defined(__DragonFly__) ||         \
      defined(__APPLE__) || defined(__MACH__)
  #include <sys/cdefs.h>
  #include <sys/mount.h>
  #include <sys/sysctl.h>
  #include <sys/types.h>
  #if defined(__FreeBSD__) || defined(__DragonFly__)
  #include <vm/vm_param.h>
  #elif defined(__OpenBSD__) || defined(__NetBSD__)
  #include <uvm/uvm_param.h>
  #else
  #define SYSCTL_LEGACY_NONCONST_MIB
  #endif
  #ifndef __MACH__
  #include <sys/vmmeter.h>
  #endif
  #else
  #include <malloc.h>
  #if !(defined(__sun) || defined(__SVR4) || defined(__svr4__) ||                \
        defined(_WIN32) || defined(_WIN64))
  #include <mntent.h>
  #endif /* !Solaris */
  #endif /* !xBSD */
  
  #if defined(__FreeBSD__) || __has_include(<malloc_np.h>)
  #include <malloc_np.h>
  #endif
  
  #if defined(__APPLE__) || defined(__MACH__) || __has_include(<malloc/malloc.h>)
  #include <malloc/malloc.h>
  #endif /* MacOS */
  
  #if defined(__MACH__)
  #include <mach/host_info.h>
  #include <mach/mach_host.h>
  #include <mach/mach_port.h>
  #include <uuid/uuid.h>
  #endif
  
  #if defined(__linux__) || defined(__gnu_linux__)
  #include <sched.h>
  #include <sys/sendfile.h>
  #include <sys/statfs.h>
  #endif /* Linux */
  
  #ifndef _XOPEN_SOURCE
  #define _XOPEN_SOURCE 0
  #endif
  
  #ifndef _XOPEN_SOURCE_EXTENDED
  #define _XOPEN_SOURCE_EXTENDED 0
  #else
  #include <utmpx.h>
  #endif /* _XOPEN_SOURCE_EXTENDED */
  
  #if defined(__sun) || defined(__SVR4) || defined(__svr4__)
  #include <kstat.h>
  #include <sys/mnttab.h>
  /* On Solaris, it's easier to add a missing prototype rather than find a
   * combination of #defines that break nothing. */
  __extern_C key_t ftok(const char *, int);
  #endif /* SunOS/Solaris */
  
  #if defined(_WIN32) || defined(_WIN64)
  #ifndef _WIN32_WINNT
  #define _WIN32_WINNT 0x0601 /* Windows 7 */
  #elif _WIN32_WINNT < 0x0500
  #error At least 'Windows 2000' API is required for libmdbx.
  #endif /* _WIN32_WINNT */
  #if (defined(__MINGW32__) || defined(__MINGW64__)) &&                          \
      !defined(__USE_MINGW_ANSI_STDIO)
  #define __USE_MINGW_ANSI_STDIO 1
  #endif /* MinGW */
  #ifndef WIN32_LEAN_AND_MEAN
  #define WIN32_LEAN_AND_MEAN
  #endif /* WIN32_LEAN_AND_MEAN */
  #include <excpt.h>
  #include <tlhelp32.h>
  #include <windows.h>
  #include <winnt.h>
  #include <winternl.h>
  #define HAVE_SYS_STAT_H
  #define HAVE_SYS_TYPES_H
  typedef HANDLE mdbx_thread_t;
  typedef unsigned mdbx_thread_key_t;
  #define MAP_FAILED NULL
  #define HIGH_DWORD(v) ((DWORD)((sizeof(v) > 4) ? ((uint64_t)(v) >> 32) : 0))
  #define THREAD_CALL WINAPI
  #define THREAD_RESULT DWORD
  typedef struct {
    HANDLE mutex;
    HANDLE event[2];
  } mdbx_condpair_t;
  typedef CRITICAL_SECTION mdbx_fastmutex_t;
  
  #if !defined(_MSC_VER) && !defined(__try)
  /* *INDENT-OFF* */
  /* clang-format off */
  #define __try
  #define __except(COND) if(false)
  /* *INDENT-ON* */
  /* clang-format on */
  #endif /* stub for MSVC's __try/__except */
  
  #if MDBX_WITHOUT_MSVC_CRT
  
  #ifndef mdbx_malloc
  static inline void *mdbx_malloc(size_t bytes) {
    return HeapAlloc(GetProcessHeap(), 0, bytes);
  }
  #endif /* mdbx_malloc */
  
  #ifndef mdbx_calloc
  static inline void *mdbx_calloc(size_t nelem, size_t size) {
    return HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, nelem * size);
  }
  #endif /* mdbx_calloc */
  
  #ifndef mdbx_realloc
  static inline void *mdbx_realloc(void *ptr, size_t bytes) {
    return ptr ? HeapReAlloc(GetProcessHeap(), 0, ptr, bytes)
               : HeapAlloc(GetProcessHeap(), 0, bytes);
  }
  #endif /* mdbx_realloc */
  
  #ifndef mdbx_free
  static inline void mdbx_free(void *ptr) { HeapFree(GetProcessHeap(), 0, ptr); }
  #endif /* mdbx_free */
  
  #else /* MDBX_WITHOUT_MSVC_CRT */
  
  #define mdbx_malloc malloc
  #define mdbx_calloc calloc
  #define mdbx_realloc realloc
  #define mdbx_free free
  #define mdbx_strdup _strdup
  
  #endif /* MDBX_WITHOUT_MSVC_CRT */
  
  #ifndef snprintf
  #define snprintf _snprintf /* ntdll */
  #endif
  
  #ifndef vsnprintf
  #define vsnprintf _vsnprintf /* ntdll */
  #endif
  
  #else /*----------------------------------------------------------------------*/
  
  #include <unistd.h>
  #if !defined(_POSIX_MAPPED_FILES) || _POSIX_MAPPED_FILES < 1
  #error "libmdbx requires the _POSIX_MAPPED_FILES feature"
  #endif /* _POSIX_MAPPED_FILES */
  
  #include <pthread.h>
  #include <semaphore.h>
  #include <signal.h>
  #include <sys/file.h>
  #include <sys/ipc.h>
  #include <sys/mman.h>
  #include <sys/param.h>
  #include <sys/stat.h>
  #include <sys/statvfs.h>
  #include <sys/uio.h>
  typedef pthread_t mdbx_thread_t;
  typedef pthread_key_t mdbx_thread_key_t;
  #define INVALID_HANDLE_VALUE (-1)
  #define THREAD_CALL
  #define THREAD_RESULT void *
  typedef struct {
    pthread_mutex_t mutex;
    pthread_cond_t cond[2];
  } mdbx_condpair_t;
  typedef pthread_mutex_t mdbx_fastmutex_t;
  #define mdbx_malloc malloc
  #define mdbx_calloc calloc
  #define mdbx_realloc realloc
  #define mdbx_free free
  #define mdbx_strdup strdup
  #endif /* Platform */
  
  #if __GLIBC_PREREQ(2, 12) || defined(__FreeBSD__) || defined(malloc_usable_size)
  /* malloc_usable_size() already provided */
  #elif defined(__APPLE__)
  #define malloc_usable_size(ptr) malloc_size(ptr)
  #elif defined(_MSC_VER) && !MDBX_WITHOUT_MSVC_CRT
  #define malloc_usable_size(ptr) _msize(ptr)
  #endif /* malloc_usable_size */
  
  #ifdef __ANDROID_API__
  #include <android/log.h>
  #if __ANDROID_API__ >= 21
  #include <sys/sendfile.h>
  #endif
  #endif /* Android */
  
  /* *INDENT-OFF* */
  /* clang-format off */
  #if defined(HAVE_SYS_STAT_H) || __has_include(<sys/stat.h>)
  #include <sys/stat.h>
  #endif
  #if defined(HAVE_SYS_TYPES_H) || __has_include(<sys/types.h>)
  #include <sys/types.h>
  #endif
  #if defined(HAVE_SYS_FILE_H) || __has_include(<sys/file.h>)
  #include <sys/file.h>
  #endif
  /* *INDENT-ON* */
  /* clang-format on */
  
  #ifndef SSIZE_MAX
  #define SSIZE_MAX INTPTR_MAX
  #endif
  
  #if !defined(MADV_DODUMP) && defined(MADV_CORE)
  #define MADV_DODUMP MADV_CORE
  #endif /* MADV_CORE -> MADV_DODUMP */
  
  #if !defined(MADV_DONTDUMP) && defined(MADV_NOCORE)
  #define MADV_DONTDUMP MADV_NOCORE
  #endif /* MADV_NOCORE -> MADV_DONTDUMP */
  
  #if defined(i386) || defined(__386) || defined(__i386) || defined(__i386__) || \
      defined(i486) || defined(__i486) || defined(__i486__) ||                   \
      defined(i586) | defined(__i586) || defined(__i586__) || defined(i686) ||   \
      defined(__i686) || defined(__i686__) || defined(_M_IX86) ||                \
      defined(_X86_) || defined(__THW_INTEL__) || defined(__I86__) ||            \
      defined(__INTEL__) || defined(__x86_64) || defined(__x86_64__) ||          \
      defined(__amd64__) || defined(__amd64) || defined(_M_X64) ||               \
      defined(_M_AMD64) || defined(__IA32__) || defined(__INTEL__)
  #ifndef __ia32__
  /* LY: define neutral __ia32__ for x86 and x86-64 */
  #define __ia32__ 1
  #endif /* __ia32__ */
  #if !defined(__amd64__) && (defined(__x86_64) || defined(__x86_64__) ||        \
                              defined(__amd64) || defined(_M_X64))
  /* LY: define trusty __amd64__ for all AMD64/x86-64 arch */
  #define __amd64__ 1
  #endif /* __amd64__ */
  #endif /* all x86 */
  
  #if (-6 & 5) || CHAR_BIT != 8 || UINT_MAX < 0xffffffff || ULONG_MAX % 0xFFFF
  #error                                                                         \
      "Sanity checking failed: Two's complement, reasonably sized integer types"
  #endif
  
  #if UINTPTR_MAX > 0xffffFFFFul || ULONG_MAX > 0xffffFFFFul
  #define MDBX_WORDBITS 64
  #else
  #define MDBX_WORDBITS 32
  #endif /* MDBX_WORDBITS */
  
  /*----------------------------------------------------------------------------*/
  /* Compiler's includes for builtins/intrinsics */
  
  #if defined(_MSC_VER) || defined(__INTEL_COMPILER)
  #include <intrin.h>
  #elif __GNUC_PREREQ(4, 4) || defined(__clang__)
  #if defined(__ia32__) || defined(__e2k__)
  #include <x86intrin.h>
  #endif /* __ia32__ */
  #if defined(__ia32__)
  #include <cpuid.h>
  #endif /* __ia32__ */
  #elif defined(__SUNPRO_C) || defined(__sun) || defined(sun)
  #include <mbarrier.h>
  #elif (defined(_HPUX_SOURCE) || defined(__hpux) || defined(__HP_aCC)) &&       \
      (defined(HP_IA64) || defined(__ia64))
  #include <machine/sys/inline.h>
  #elif defined(__IBMC__) && defined(__powerpc)
  #include <atomic.h>
  #elif defined(_AIX)
  #include <builtins.h>
  #include <sys/atomic_op.h>
  #elif (defined(__osf__) && defined(__DECC)) || defined(__alpha)
  #include <c_asm.h>
  #include <machine/builtins.h>
  #elif defined(__MWERKS__)
  /* CodeWarrior - troubles ? */
  #pragma gcc_extensions
  #elif defined(__SNC__)
  /* Sony PS3 - troubles ? */
  #elif defined(__hppa__) || defined(__hppa)
  #include <machine/inline.h>
  #else
  #error Unsupported C compiler, please use GNU C 4.4 or newer
  #endif /* Compiler */
  
  /*----------------------------------------------------------------------------*/
  /* Byteorder */
  
  #if !defined(__BYTE_ORDER__) || !defined(__ORDER_LITTLE_ENDIAN__) ||           \
      !defined(__ORDER_BIG_ENDIAN__)
  
  /* *INDENT-OFF* */
  /* clang-format off */
  #if defined(__GLIBC__) || defined(__GNU_LIBRARY__) || defined(__ANDROID_API__) ||  \
      defined(HAVE_ENDIAN_H) || __has_include(<endian.h>)
  #include <endian.h>
  #elif defined(__APPLE__) || defined(__MACH__) || defined(__OpenBSD__) ||       \
      defined(HAVE_MACHINE_ENDIAN_H) || __has_include(<machine/endian.h>)
  #include <machine/endian.h>
  #elif defined(HAVE_SYS_ISA_DEFS_H) || __has_include(<sys/isa_defs.h>)
  #include <sys/isa_defs.h>
  #elif (defined(HAVE_SYS_TYPES_H) && defined(HAVE_SYS_ENDIAN_H)) ||             \
      (__has_include(<sys/types.h>) && __has_include(<sys/endian.h>))
  #include <sys/endian.h>
  #include <sys/types.h>
  #elif defined(__bsdi__) || defined(__DragonFly__) || defined(__FreeBSD__) ||   \
      defined(__NetBSD__) ||                              \
      defined(HAVE_SYS_PARAM_H) || __has_include(<sys/param.h>)
  #include <sys/param.h>
  #endif /* OS */
  /* *INDENT-ON* */
  /* clang-format on */
  
  #if defined(__BYTE_ORDER) && defined(__LITTLE_ENDIAN) && defined(__BIG_ENDIAN)
  #define __ORDER_LITTLE_ENDIAN__ __LITTLE_ENDIAN
  #define __ORDER_BIG_ENDIAN__ __BIG_ENDIAN
  #define __BYTE_ORDER__ __BYTE_ORDER
  #elif defined(_BYTE_ORDER) && defined(_LITTLE_ENDIAN) && defined(_BIG_ENDIAN)
  #define __ORDER_LITTLE_ENDIAN__ _LITTLE_ENDIAN
  #define __ORDER_BIG_ENDIAN__ _BIG_ENDIAN
  #define __BYTE_ORDER__ _BYTE_ORDER
  #else
  #define __ORDER_LITTLE_ENDIAN__ 1234
  #define __ORDER_BIG_ENDIAN__ 4321
  
  #if defined(__LITTLE_ENDIAN__) ||                                              \
      (defined(_LITTLE_ENDIAN) && !defined(_BIG_ENDIAN)) ||                      \
      defined(__ARMEL__) || defined(__THUMBEL__) || defined(__AARCH64EL__) ||    \
      defined(__MIPSEL__) || defined(_MIPSEL) || defined(__MIPSEL) ||            \
      defined(_M_ARM) || defined(_M_ARM64) || defined(__e2k__) ||                \
      defined(__elbrus_4c__) || defined(__elbrus_8c__) || defined(__bfin__) ||   \
      defined(__BFIN__) || defined(__ia64__) || defined(_IA64) ||                \
      defined(__IA64__) || defined(__ia64) || defined(_M_IA64) ||                \
      defined(__itanium__) || defined(__ia32__) || defined(__CYGWIN__) ||        \
      defined(_WIN64) || defined(_WIN32) || defined(__TOS_WIN__) ||              \
      defined(__WINDOWS__)
  #define __BYTE_ORDER__ __ORDER_LITTLE_ENDIAN__
  
  #elif defined(__BIG_ENDIAN__) ||                                               \
      (defined(_BIG_ENDIAN) && !defined(_LITTLE_ENDIAN)) ||                      \
      defined(__ARMEB__) || defined(__THUMBEB__) || defined(__AARCH64EB__) ||    \
      defined(__MIPSEB__) || defined(_MIPSEB) || defined(__MIPSEB) ||            \
      defined(__m68k__) || defined(M68000) || defined(__hppa__) ||               \
      defined(__hppa) || defined(__HPPA__) || defined(__sparc__) ||              \
      defined(__sparc) || defined(__370__) || defined(__THW_370__) ||            \
      defined(__s390__) || defined(__s390x__) || defined(__SYSC_ZARCH__)
  #define __BYTE_ORDER__ __ORDER_BIG_ENDIAN__
  
  #else
  #error __BYTE_ORDER__ should be defined.
  #endif /* Arch */
  
  #endif
  #endif /* __BYTE_ORDER__ || __ORDER_LITTLE_ENDIAN__ || __ORDER_BIG_ENDIAN__ */
  
  /* Get the size of a memory page for the system.
   * This is the basic size that the platform's memory manager uses, and is
   * fundamental to the use of memory-mapped files. */
  MDBX_MAYBE_UNUSED MDBX_NOTHROW_CONST_FUNCTION static __inline size_t
  mdbx_syspagesize(void) {
  #if defined(_WIN32) || defined(_WIN64)
    SYSTEM_INFO si;
    GetSystemInfo(&si);
    return si.dwPageSize;
  #else
    return sysconf(_SC_PAGE_SIZE);
  #endif
  }
  
  typedef struct mdbx_mmap_param {
    union {
      void *address;
      uint8_t *dxb;
      struct MDBX_lockinfo *lck;
    };
    mdbx_filehandle_t fd;
    size_t limit;   /* mapping length, but NOT a size of file nor DB */
    size_t current; /* mapped region size, i.e. the size of file and DB */
    uint64_t filesize /* in-process cache of a file size */;
  #if defined(_WIN32) || defined(_WIN64)
    HANDLE section; /* memory-mapped section handle */
  #endif
  } mdbx_mmap_t;
  
  typedef union bin128 {
    __anonymous_struct_extension__ struct { uint64_t x, y; };
    __anonymous_struct_extension__ struct { uint32_t a, b, c, d; };
  } bin128_t;
  
  #if defined(_WIN32) || defined(_WIN64)
  typedef union MDBX_srwlock {
    struct {
      long volatile readerCount;
      long volatile writerCount;
    };
    RTL_SRWLOCK native;
  } MDBX_srwlock;
  #endif /* Windows */
  
  #ifndef __cplusplus
  
  MDBX_MAYBE_UNUSED MDBX_INTERNAL_FUNC void mdbx_osal_jitter(bool tiny);
  MDBX_MAYBE_UNUSED static __inline void mdbx_jitter4testing(bool tiny);
  
  /*----------------------------------------------------------------------------*/
  /* Atomics */
  
  #if defined(__cplusplus) && !defined(__STDC_NO_ATOMICS__) && (__has_include(<cstdatomic>) || __has_extension(cxx_atomic))
  #include <cstdatomic>
  #define MDBX_HAVE_C11ATOMICS
  #elif !defined(__cplusplus) &&                                                 \
      (__STDC_VERSION__ >= 201112L || __has_extension(c_atomic)) &&              \
      !defined(__STDC_NO_ATOMICS__) &&                                           \
      (__GNUC_PREREQ(4, 9) || __CLANG_PREREQ(3, 8) ||                            \
       !(defined(__GNUC__) || defined(__clang__)))
  #include <stdatomic.h>
  #define MDBX_HAVE_C11ATOMICS
  #elif defined(__GNUC__) || defined(__clang__)
  #elif defined(_MSC_VER)
  #pragma warning(disable : 4163) /* 'xyz': not available as an intrinsic */
  #pragma warning(disable : 4133) /* 'function': incompatible types - from       \
                                     'size_t' to 'LONGLONG' */
  #pragma warning(disable : 4244) /* 'return': conversion from 'LONGLONG' to     \
                                     'std::size_t', possible loss of data */
  #pragma warning(disable : 4267) /* 'function': conversion from 'size_t' to     \
                                     'long', possible loss of data */
  #pragma intrinsic(_InterlockedExchangeAdd, _InterlockedCompareExchange)
  #pragma intrinsic(_InterlockedExchangeAdd64, _InterlockedCompareExchange64)
  #elif defined(__APPLE__)
  #include <libkern/OSAtomic.h>
  #else
  #error FIXME atomic-ops
  #endif
  
  /*----------------------------------------------------------------------------*/
  /* Memory/Compiler barriers, cache coherence */
  
  #if __has_include(<sys/cachectl.h>)
  #include <sys/cachectl.h>
  #elif defined(__mips) || defined(__mips__) || defined(__mips64) ||             \
      defined(__mips64__) || defined(_M_MRX000) || defined(_MIPS_) ||            \
      defined(__MWERKS__) || defined(__sgi)
  /* MIPS should have explicit cache control */
  #include <sys/cachectl.h>
  #endif
  
  MDBX_MAYBE_UNUSED static __inline void mdbx_compiler_barrier(void) {
  #if defined(__clang__) || defined(__GNUC__)
    __asm__ __volatile__("" ::: "memory");
  #elif defined(_MSC_VER)
    _ReadWriteBarrier();
  #elif defined(__INTEL_COMPILER) /* LY: Intel Compiler may mimic GCC and MSC */
    __memory_barrier();
  #elif defined(__SUNPRO_C) || defined(__sun) || defined(sun)
    __compiler_barrier();
  #elif (defined(_HPUX_SOURCE) || defined(__hpux) || defined(__HP_aCC)) &&       \
      (defined(HP_IA64) || defined(__ia64))
    _Asm_sched_fence(/* LY: no-arg meaning 'all expect ALU', e.g. 0x3D3D */);
  #elif defined(_AIX) || defined(__ppc__) || defined(__powerpc__) ||             \
      defined(__ppc64__) || defined(__powerpc64__)
    __fence();
  #else
  #error "Could not guess the kind of compiler, please report to us."
  #endif
  }
  
  MDBX_MAYBE_UNUSED static __inline void mdbx_memory_barrier(void) {
  #ifdef MDBX_HAVE_C11ATOMICS
    atomic_thread_fence(memory_order_seq_cst);
  #elif defined(__ATOMIC_SEQ_CST)
  #ifdef __clang__
    __c11_atomic_thread_fence(__ATOMIC_SEQ_CST);
  #else
    __atomic_thread_fence(__ATOMIC_SEQ_CST);
  #endif
  #elif defined(__clang__) || defined(__GNUC__)
    __sync_synchronize();
  #elif defined(_WIN32) || defined(_WIN64)
    MemoryBarrier();
  #elif defined(__INTEL_COMPILER) /* LY: Intel Compiler may mimic GCC and MSC */
  #if defined(__ia32__)
    _mm_mfence();
  #else
    __mf();
  #endif
  #elif defined(__SUNPRO_C) || defined(__sun) || defined(sun)
    __machine_rw_barrier();
  #elif (defined(_HPUX_SOURCE) || defined(__hpux) || defined(__HP_aCC)) &&       \
      (defined(HP_IA64) || defined(__ia64))
    _Asm_mf();
  #elif defined(_AIX) || defined(__ppc__) || defined(__powerpc__) ||             \
      defined(__ppc64__) || defined(__powerpc64__)
    __lwsync();
  #else
  #error "Could not guess the kind of compiler, please report to us."
  #endif
  }
  
  /*----------------------------------------------------------------------------*/
  /* libc compatibility stuff */
  
  #if (!defined(__GLIBC__) && __GLIBC_PREREQ(2, 1)) &&                           \
      (defined(_GNU_SOURCE) || defined(_BSD_SOURCE))
  #define mdbx_asprintf asprintf
  #define mdbx_vasprintf vasprintf
  #else
  MDBX_MAYBE_UNUSED MDBX_INTERNAL_FUNC
      MDBX_PRINTF_ARGS(2, 3) int mdbx_asprintf(char **strp, const char *fmt, ...);
  MDBX_INTERNAL_FUNC int mdbx_vasprintf(char **strp, const char *fmt, va_list ap);
  #endif
  
  /*----------------------------------------------------------------------------*/
  /* OS abstraction layer stuff */
  
  /* max bytes to write in one call */
  #if defined(_WIN32) || defined(_WIN64)
  #define MAX_WRITE UINT32_C(0x01000000)
  #else
  #define MAX_WRITE UINT32_C(0x3fff0000)
  #endif
  
  #if defined(__linux__) || defined(__gnu_linux__)
  MDBX_INTERNAL_VAR uint32_t mdbx_linux_kernel_version;
  MDBX_INTERNAL_VAR bool mdbx_RunningOnWSL1 /* Windows Subsystem 1 for Linux */;
  #endif /* Linux */
  
  #ifndef mdbx_strdup
  LIBMDBX_API char *mdbx_strdup(const char *str);
  #endif
  
  MDBX_MAYBE_UNUSED static __inline int mdbx_get_errno(void) {
  #if defined(_WIN32) || defined(_WIN64)
    DWORD rc = GetLastError();
  #else
    int rc = errno;
  #endif
    return rc;
  }
  
  #ifndef mdbx_memalign_alloc
  MDBX_INTERNAL_FUNC int mdbx_memalign_alloc(size_t alignment, size_t bytes,
                                             void **result);
  #endif
  #ifndef mdbx_memalign_free
  MDBX_INTERNAL_FUNC void mdbx_memalign_free(void *ptr);
  #endif
  
  MDBX_INTERNAL_FUNC int mdbx_condpair_init(mdbx_condpair_t *condpair);
  MDBX_INTERNAL_FUNC int mdbx_condpair_lock(mdbx_condpair_t *condpair);
  MDBX_INTERNAL_FUNC int mdbx_condpair_unlock(mdbx_condpair_t *condpair);
  MDBX_INTERNAL_FUNC int mdbx_condpair_signal(mdbx_condpair_t *condpair,
                                              bool part);
  MDBX_INTERNAL_FUNC int mdbx_condpair_wait(mdbx_condpair_t *condpair, bool part);
  MDBX_INTERNAL_FUNC int mdbx_condpair_destroy(mdbx_condpair_t *condpair);
  
  MDBX_INTERNAL_FUNC int mdbx_fastmutex_init(mdbx_fastmutex_t *fastmutex);
  MDBX_INTERNAL_FUNC int mdbx_fastmutex_acquire(mdbx_fastmutex_t *fastmutex);
  MDBX_INTERNAL_FUNC int mdbx_fastmutex_release(mdbx_fastmutex_t *fastmutex);
  MDBX_INTERNAL_FUNC int mdbx_fastmutex_destroy(mdbx_fastmutex_t *fastmutex);
  
  MDBX_INTERNAL_FUNC int mdbx_pwritev(mdbx_filehandle_t fd, struct iovec *iov,
                                      int iovcnt, uint64_t offset,
                                      size_t expected_written);
  MDBX_INTERNAL_FUNC int mdbx_pread(mdbx_filehandle_t fd, void *buf, size_t count,
                                    uint64_t offset);
  MDBX_INTERNAL_FUNC int mdbx_pwrite(mdbx_filehandle_t fd, const void *buf,
                                     size_t count, uint64_t offset);
  MDBX_INTERNAL_FUNC int mdbx_write(mdbx_filehandle_t fd, const void *buf,
                                    size_t count);
  
  MDBX_INTERNAL_FUNC int
  mdbx_thread_create(mdbx_thread_t *thread,
                     THREAD_RESULT(THREAD_CALL *start_routine)(void *),
                     void *arg);
  MDBX_INTERNAL_FUNC int mdbx_thread_join(mdbx_thread_t thread);
  
  enum mdbx_syncmode_bits {
    MDBX_SYNC_NONE = 0,
    MDBX_SYNC_DATA = 1,
    MDBX_SYNC_SIZE = 2,
    MDBX_SYNC_IODQ = 4
  };
  
  MDBX_INTERNAL_FUNC int mdbx_fsync(mdbx_filehandle_t fd,
                                    const enum mdbx_syncmode_bits mode_bits);
  MDBX_INTERNAL_FUNC int mdbx_ftruncate(mdbx_filehandle_t fd, uint64_t length);
  MDBX_INTERNAL_FUNC int mdbx_fseek(mdbx_filehandle_t fd, uint64_t pos);
  MDBX_INTERNAL_FUNC int mdbx_filesize(mdbx_filehandle_t fd, uint64_t *length);
  
  enum mdbx_openfile_purpose {
    MDBX_OPEN_DXB_READ = 0,
    MDBX_OPEN_DXB_LAZY = 1,
    MDBX_OPEN_DXB_DSYNC = 2,
    MDBX_OPEN_LCK = 3,
    MDBX_OPEN_COPY = 4,
    MDBX_OPEN_DELETE = 5
  };
  
  MDBX_INTERNAL_FUNC int mdbx_openfile(const enum mdbx_openfile_purpose purpose,
                                       const MDBX_env *env, const char *pathname,
                                       mdbx_filehandle_t *fd,
                                       mdbx_mode_t unix_mode_bits);
  MDBX_INTERNAL_FUNC int mdbx_closefile(mdbx_filehandle_t fd);
  MDBX_INTERNAL_FUNC int mdbx_removefile(const char *pathname);
  MDBX_INTERNAL_FUNC int mdbx_removedirectory(const char *pathname);
  MDBX_INTERNAL_FUNC int mdbx_is_pipe(mdbx_filehandle_t fd);
  MDBX_INTERNAL_FUNC int mdbx_lockfile(mdbx_filehandle_t fd, bool wait);
  
  #define MMAP_OPTION_TRUNCATE 1
  #define MMAP_OPTION_SEMAPHORE 2
  MDBX_INTERNAL_FUNC int mdbx_mmap(const int flags, mdbx_mmap_t *map,
                                   const size_t must, const size_t limit,
                                   const unsigned options);
  MDBX_INTERNAL_FUNC int mdbx_munmap(mdbx_mmap_t *map);
  #define MDBX_MRESIZE_MAY_MOVE 0x00000100
  #define MDBX_MRESIZE_MAY_UNMAP 0x00000200
  MDBX_INTERNAL_FUNC int mdbx_mresize(const int flags, mdbx_mmap_t *map,
                                      size_t size, size_t limit);
  #if defined(_WIN32) || defined(_WIN64)
  typedef struct {
    unsigned limit, count;
    HANDLE handles[31];
  } mdbx_handle_array_t;
  MDBX_INTERNAL_FUNC int
  mdbx_suspend_threads_before_remap(MDBX_env *env, mdbx_handle_array_t **array);
  MDBX_INTERNAL_FUNC int
  mdbx_resume_threads_after_remap(mdbx_handle_array_t *array);
  #endif /* Windows */
  MDBX_INTERNAL_FUNC int mdbx_msync(mdbx_mmap_t *map, size_t offset,
                                    size_t length,
                                    enum mdbx_syncmode_bits mode_bits);
  MDBX_INTERNAL_FUNC int mdbx_check_fs_rdonly(mdbx_filehandle_t handle,
                                              const char *pathname, int err);
  
  MDBX_MAYBE_UNUSED static __inline uint32_t mdbx_getpid(void) {
    STATIC_ASSERT(sizeof(mdbx_pid_t) <= sizeof(uint32_t));
  #if defined(_WIN32) || defined(_WIN64)
    return GetCurrentProcessId();
  #else
    return getpid();
  #endif
  }
  
  MDBX_MAYBE_UNUSED static __inline uintptr_t mdbx_thread_self(void) {
    mdbx_tid_t thunk;
    STATIC_ASSERT(sizeof(uintptr_t) >= sizeof(thunk));
  #if defined(_WIN32) || defined(_WIN64)
    thunk = GetCurrentThreadId();
  #else
    thunk = pthread_self();
  #endif
    return (uintptr_t)thunk;
  }
  
  MDBX_INTERNAL_FUNC uint64_t mdbx_osal_monotime(void);
  MDBX_INTERNAL_FUNC uint64_t
  mdbx_osal_16dot16_to_monotime(uint32_t seconds_16dot16);
  MDBX_INTERNAL_FUNC uint32_t mdbx_osal_monotime_to_16dot16(uint64_t monotime);
  
  MDBX_INTERNAL_FUNC bin128_t mdbx_osal_bootid(void);
  /*----------------------------------------------------------------------------*/
  /* lck stuff */
  
  /// \brief Initialization of synchronization primitives linked with MDBX_env
  ///   instance both in LCK-file and within the current process.
  /// \param
  ///   global_uniqueness_flag = true - denotes that there are no other processes
  ///     working with DB and LCK-file. Thus the function MUST initialize
  ///     shared synchronization objects in memory-mapped LCK-file.
  ///   global_uniqueness_flag = false - denotes that at least one process is
  ///     already working with DB and LCK-file, including the case when DB
  ///     has already been opened in the current process. Thus the function
  ///     MUST NOT initialize shared synchronization objects in memory-mapped
  ///     LCK-file that are already in use.
  /// \return Error code or zero on success.
  MDBX_INTERNAL_FUNC int mdbx_lck_init(MDBX_env *env,
                                       MDBX_env *inprocess_neighbor,
                                       int global_uniqueness_flag);
  
  /// \brief Disconnects from shared interprocess objects and destructs
  ///   synchronization objects linked with MDBX_env instance
  ///   within the current process.
  /// \param
  ///   inprocess_neighbor = NULL - if the current process does not have other
  ///     instances of MDBX_env linked with the DB being closed.
  ///     Thus the function MUST check for other processes working with DB or
  ///     LCK-file, and keep or destroy shared synchronization objects in
  ///     memory-mapped LCK-file depending on the result.
  ///   inprocess_neighbor = not-NULL - pointer to another instance of MDBX_env
  ///     (anyone of there is several) working with DB or LCK-file within the
  ///     current process. Thus the function MUST NOT try to acquire exclusive
  ///     lock and/or try to destruct shared synchronization objects linked with
  ///     DB or LCK-file. Moreover, the implementation MUST ensure correct work
  ///     of other instances of MDBX_env within the current process, e.g.
  ///     restore POSIX-fcntl locks after the closing of file descriptors.
  /// \return Error code (MDBX_PANIC) or zero on success.
  MDBX_INTERNAL_FUNC int mdbx_lck_destroy(MDBX_env *env,
                                          MDBX_env *inprocess_neighbor);
  
  /// \brief Connects to shared interprocess locking objects and tries to acquire
  ///   the maximum lock level (shared if exclusive is not available)
  ///   Depending on implementation or/and platform (Windows) this function may
  ///   acquire the non-OS super-level lock (e.g. for shared synchronization
  ///   objects initialization), which will be downgraded to OS-exclusive or
  ///   shared via explicit calling of mdbx_lck_downgrade().
  /// \return
  ///   MDBX_RESULT_TRUE (-1) - if an exclusive lock was acquired and thus
  ///     the current process is the first and only after the last use of DB.
  ///   MDBX_RESULT_FALSE (0) - if a shared lock was acquired and thus
  ///     DB has already been opened and now is used by other processes.
  ///   Otherwise (not 0 and not -1) - error code.
  MDBX_INTERNAL_FUNC int mdbx_lck_seize(MDBX_env *env);
  
  /// \brief Downgrades the level of initially acquired lock to
  ///   operational level specified by argument. The reson for such downgrade:
  ///    - unblocking of other processes that are waiting for access, i.e.
  ///      if (env->me_flags & MDBX_EXCLUSIVE) != 0, then other processes
  ///      should be made aware that access is unavailable rather than
  ///      wait for it.
  ///    - freeing locks that interfere file operation (especially for Windows)
  ///   (env->me_flags & MDBX_EXCLUSIVE) == 0 - downgrade to shared lock.
  ///   (env->me_flags & MDBX_EXCLUSIVE) != 0 - downgrade to exclusive
  ///   operational lock.
  /// \return Error code or zero on success
  MDBX_INTERNAL_FUNC int mdbx_lck_downgrade(MDBX_env *env);
  
  /// \brief Locks LCK-file or/and table of readers for (de)registering.
  /// \return Error code or zero on success
  MDBX_INTERNAL_FUNC int mdbx_rdt_lock(MDBX_env *env);
  
  /// \brief Unlocks LCK-file or/and table of readers after (de)registering.
  MDBX_INTERNAL_FUNC void mdbx_rdt_unlock(MDBX_env *env);
  
  /// \brief Acquires lock for DB change (on writing transaction start)
  ///   Reading transactions will not be blocked.
  ///   Declared as LIBMDBX_API because it is used in mdbx_chk.
  /// \return Error code or zero on success
  LIBMDBX_API int mdbx_txn_lock(MDBX_env *env, bool dont_wait);
  
  /// \brief Releases lock once DB changes is made (after writing transaction
  ///   has finished).
  ///   Declared as LIBMDBX_API because it is used in mdbx_chk.
  LIBMDBX_API void mdbx_txn_unlock(MDBX_env *env);
  
  /// \brief Sets alive-flag of reader presence (indicative lock) for PID of
  ///   the current process. The function does no more than needed for
  ///   the correct working of mdbx_rpid_check() in other processes.
  /// \return Error code or zero on success
  MDBX_INTERNAL_FUNC int mdbx_rpid_set(MDBX_env *env);
  
  /// \brief Resets alive-flag of reader presence (indicative lock)
  ///   for PID of the current process. The function does no more than needed
  ///   for the correct working of mdbx_rpid_check() in other processes.
  /// \return Error code or zero on success
  MDBX_INTERNAL_FUNC int mdbx_rpid_clear(MDBX_env *env);
  
  /// \brief Checks for reading process status with the given pid with help of
  ///   alive-flag of presence (indicative lock) or using another way.
  /// \return
  ///   MDBX_RESULT_TRUE (-1) - if the reader process with the given PID is alive
  ///     and working with DB (indicative lock is present).
  ///   MDBX_RESULT_FALSE (0) - if the reader process with the given PID is absent
  ///     or not working with DB (indicative lock is not present).
  ///   Otherwise (not 0 and not -1) - error code.
  MDBX_INTERNAL_FUNC int mdbx_rpid_check(MDBX_env *env, uint32_t pid);
  
  #if defined(_WIN32) || defined(_WIN64)
  
  typedef void(WINAPI *MDBX_srwlock_function)(MDBX_srwlock *);
  MDBX_INTERNAL_VAR MDBX_srwlock_function mdbx_srwlock_Init,
      mdbx_srwlock_AcquireShared, mdbx_srwlock_ReleaseShared,
      mdbx_srwlock_AcquireExclusive, mdbx_srwlock_ReleaseExclusive;
  
  #if _WIN32_WINNT < 0x0600 /* prior to Windows Vista */
  typedef enum _FILE_INFO_BY_HANDLE_CLASS {
    FileBasicInfo,
    FileStandardInfo,
    FileNameInfo,
    FileRenameInfo,
    FileDispositionInfo,
    FileAllocationInfo,
    FileEndOfFileInfo,
    FileStreamInfo,
    FileCompressionInfo,
    FileAttributeTagInfo,
    FileIdBothDirectoryInfo,
    FileIdBothDirectoryRestartInfo,
    FileIoPriorityHintInfo,
    FileRemoteProtocolInfo,
    MaximumFileInfoByHandleClass
  } FILE_INFO_BY_HANDLE_CLASS,
      *PFILE_INFO_BY_HANDLE_CLASS;
  
  typedef struct _FILE_END_OF_FILE_INFO {
    LARGE_INTEGER EndOfFile;
  } FILE_END_OF_FILE_INFO, *PFILE_END_OF_FILE_INFO;
  
  #define REMOTE_PROTOCOL_INFO_FLAG_LOOPBACK 0x00000001
  #define REMOTE_PROTOCOL_INFO_FLAG_OFFLINE 0x00000002
  
  typedef struct _FILE_REMOTE_PROTOCOL_INFO {
    USHORT StructureVersion;
    USHORT StructureSize;
    DWORD Protocol;
    USHORT ProtocolMajorVersion;
    USHORT ProtocolMinorVersion;
    USHORT ProtocolRevision;
    USHORT Reserved;
    DWORD Flags;
    struct {
      DWORD Reserved[8];
    } GenericReserved;
    struct {
      DWORD Reserved[16];
    } ProtocolSpecificReserved;
  } FILE_REMOTE_PROTOCOL_INFO, *PFILE_REMOTE_PROTOCOL_INFO;
  
  #endif /* _WIN32_WINNT < 0x0600 (prior to Windows Vista) */
  
  typedef BOOL(WINAPI *MDBX_GetFileInformationByHandleEx)(
      _In_ HANDLE hFile, _In_ FILE_INFO_BY_HANDLE_CLASS FileInformationClass,
      _Out_ LPVOID lpFileInformation, _In_ DWORD dwBufferSize);
  MDBX_INTERNAL_VAR MDBX_GetFileInformationByHandleEx
      mdbx_GetFileInformationByHandleEx;
  
  typedef BOOL(WINAPI *MDBX_GetVolumeInformationByHandleW)(
      _In_ HANDLE hFile, _Out_opt_ LPWSTR lpVolumeNameBuffer,
      _In_ DWORD nVolumeNameSize, _Out_opt_ LPDWORD lpVolumeSerialNumber,
      _Out_opt_ LPDWORD lpMaximumComponentLength,
      _Out_opt_ LPDWORD lpFileSystemFlags,
      _Out_opt_ LPWSTR lpFileSystemNameBuffer, _In_ DWORD nFileSystemNameSize);
  MDBX_INTERNAL_VAR MDBX_GetVolumeInformationByHandleW
      mdbx_GetVolumeInformationByHandleW;
  
  typedef DWORD(WINAPI *MDBX_GetFinalPathNameByHandleW)(_In_ HANDLE hFile,
                                                        _Out_ LPWSTR lpszFilePath,
                                                        _In_ DWORD cchFilePath,
                                                        _In_ DWORD dwFlags);
  MDBX_INTERNAL_VAR MDBX_GetFinalPathNameByHandleW mdbx_GetFinalPathNameByHandleW;
  
  typedef BOOL(WINAPI *MDBX_SetFileInformationByHandle)(
      _In_ HANDLE hFile, _In_ FILE_INFO_BY_HANDLE_CLASS FileInformationClass,
      _Out_ LPVOID lpFileInformation, _In_ DWORD dwBufferSize);
  MDBX_INTERNAL_VAR MDBX_SetFileInformationByHandle
      mdbx_SetFileInformationByHandle;
  
  typedef NTSTATUS(NTAPI *MDBX_NtFsControlFile)(
      IN HANDLE FileHandle, IN OUT HANDLE Event,
      IN OUT PVOID /* PIO_APC_ROUTINE */ ApcRoutine, IN OUT PVOID ApcContext,
      OUT PIO_STATUS_BLOCK IoStatusBlock, IN ULONG FsControlCode,
      IN OUT PVOID InputBuffer, IN ULONG InputBufferLength,
      OUT OPTIONAL PVOID OutputBuffer, IN ULONG OutputBufferLength);
  MDBX_INTERNAL_VAR MDBX_NtFsControlFile mdbx_NtFsControlFile;
  
  typedef uint64_t(WINAPI *MDBX_GetTickCount64)(void);
  MDBX_INTERNAL_VAR MDBX_GetTickCount64 mdbx_GetTickCount64;
  
  #if !defined(_WIN32_WINNT_WIN8) || _WIN32_WINNT < _WIN32_WINNT_WIN8
  typedef struct _WIN32_MEMORY_RANGE_ENTRY {
    PVOID VirtualAddress;
    SIZE_T NumberOfBytes;
  } WIN32_MEMORY_RANGE_ENTRY, *PWIN32_MEMORY_RANGE_ENTRY;
  #endif /* Windows 8.x */
  
  typedef BOOL(WINAPI *MDBX_PrefetchVirtualMemory)(
      HANDLE hProcess, ULONG_PTR NumberOfEntries,
      PWIN32_MEMORY_RANGE_ENTRY VirtualAddresses, ULONG Flags);
  MDBX_INTERNAL_VAR MDBX_PrefetchVirtualMemory mdbx_PrefetchVirtualMemory;
  
  typedef enum _SECTION_INHERIT { ViewShare = 1, ViewUnmap = 2 } SECTION_INHERIT;
  
  typedef NTSTATUS(NTAPI *MDBX_NtExtendSection)(IN HANDLE SectionHandle,
                                                IN PLARGE_INTEGER NewSectionSize);
  MDBX_INTERNAL_VAR MDBX_NtExtendSection mdbx_NtExtendSection;
  
  static __inline bool mdbx_RunningUnderWine(void) {
    return !mdbx_NtExtendSection;
  }
  
  typedef LSTATUS(WINAPI *MDBX_RegGetValueA)(HKEY hkey, LPCSTR lpSubKey,
                                             LPCSTR lpValue, DWORD dwFlags,
                                             LPDWORD pdwType, PVOID pvData,
                                             LPDWORD pcbData);
  MDBX_INTERNAL_VAR MDBX_RegGetValueA mdbx_RegGetValueA;
  
  #endif /* Windows */
  
  #endif /* !__cplusplus */
  
  /*----------------------------------------------------------------------------*/
  
  #if defined(_MSC_VER) && _MSC_VER >= 1900
  /* LY: MSVC 2015/2017/2019 has buggy/inconsistent PRIuPTR/PRIxPTR macros
   * for internal format-args checker. */
  #undef PRIuPTR
  #undef PRIiPTR
  #undef PRIdPTR
  #undef PRIxPTR
  #define PRIuPTR "Iu"
  #define PRIiPTR "Ii"
  #define PRIdPTR "Id"
  #define PRIxPTR "Ix"
  #define PRIuSIZE "zu"
  #define PRIiSIZE "zi"
  #define PRIdSIZE "zd"
  #define PRIxSIZE "zx"
  #endif /* fix PRI*PTR for _MSC_VER */
  
  #ifndef PRIuSIZE
  #define PRIuSIZE PRIuPTR
  #define PRIiSIZE PRIiPTR
  #define PRIdSIZE PRIdPTR
  #define PRIxSIZE PRIxPTR
  #endif /* PRI*SIZE macros for MSVC */
  
  #ifdef _MSC_VER
  #pragma warning(pop)
  #endif
  