---
name: "mdb.c"
section: "3"
platform: "linux"
package: "lmdb-doc"
version: "0.9.31-1"
release: "Debian 13 (Trixie)"
platforms: ["linux"]
url: "https://new.carta.tech/mdb.c"
---

# mdb.c(3)

Lightning memory-mapped database library.

## NAME

mdb.c - Lightning memory-mapped database library.

## SYNOPSIS

`#include <sys/types.h>`\
 `#include <sys/stat.h>`\
 `#include <sys/param.h>`\
 `#include <sys/uio.h>`\
 `#include <sys/mman.h>`\
 `#include <fcntl.h>`\
 `#include <errno.h>`\
 `#include <limits.h>`\
 `#include <stddef.h>`\
 `#include <inttypes.h>`\
 `#include <stdio.h>`\
 `#include <stdlib.h>`\
 `#include <string.h>`\
 `#include <time.h>`\
 `#include <unistd.h>`\
 `#include <netinet/in.h>`\
 `#include <resolv.h>`\
 `#include <pthread.h>`\
 `#include <signal.h>`\
 `#include 'lmdb.h'`\
 `#include 'midl.h'`\

### Data Structures

struct **MDB\_rxbody**\
 struct **MDB\_reader**\
 struct **MDB\_txbody**\
 struct **MDB\_txninfo**\
 struct **MDB\_page**\
 struct **MDB\_page2**\
 struct **MDB\_node**\
 struct **MDB\_db**\
 struct **MDB\_meta**\
 union **MDB\_metabuf**\
 struct **MDB\_dbx**\
 struct **MDB\_txn**\
 Opaque structure for a transaction handle.  struct **MDB\_cursor**\
 Opaque structure for navigating through a database.  struct **MDB\_xcursor**\
 struct **MDB\_pgstate**\
 struct **MDB\_env**\
 Opaque structure for a database environment.  struct **MDB\_ntxn**\
 struct **MDB\_name**\
 struct **mdb\_copy**\

### Macros

\#define **\_GNU\_SOURCE**   1\
 \#define **MDB\_PID\_T**   pid\_t\
 \#define **MDB\_THR\_T**   pthread\_t\
 \#define **CACHEFLUSH**(addr,  bytes,  cache)\
 \#define **MDB\_USE\_POSIX\_MUTEX**   1\
 \#define **VGMEMP\_CREATE**(h,  r,  z)\
 \#define **VGMEMP\_ALLOC**(h,  a,  s)\
 \#define **VGMEMP\_FREE**(h,  a)\
 \#define **VGMEMP\_DESTROY**(h)\
 \#define **VGMEMP\_DEFINED**(a,  s)\
 \#define **BYTE\_ORDER**   \_\_BYTE\_ORDER\
 \#define **LITTLE\_ENDIAN**   \_\_LITTLE\_ENDIAN\
 \#define **BIG\_ENDIAN**   \_\_BIG\_ENDIAN\
 \#define **ESECT**   \_\_attribute\_\_ ((section('text\_env')))\
 \#define **CALL\_CONV**\
 \#define **MDB\_DEVEL**   0\
 \#define **mdb\_func\_**   '\<mdb\_unknown\>'\
 \#define **MDB\_NO\_ROOT**   (**MDB\_LAST\_ERRCODE** + 10)\
 \#define **MDB\_USE\_ROBUST**   1\
 \#define **THREAD\_RET**   void \*\
 \#define **THREAD\_CREATE**(thr,  start,  arg)   pthread\_create(&thr,NULL,start,arg)\
 \#define **THREAD\_FINISH**(thr)   pthread\_join(thr,NULL)\
 \#define **Z**   'z'\
 \#define **MDB\_PIDLOCK**   1\
 \#define **LOCK\_MUTEX0**(mutex)   pthread\_mutex\_lock(mutex)\
 \#define **UNLOCK\_MUTEX**(mutex)   pthread\_mutex\_unlock(mutex)\
 \#define **mdb\_mutex\_consistent**(mutex)   pthread\_mutex\_consistent(mutex)\
 \#define **ErrCode**()   errno\
 \#define **HANDLE**   int\
 \#define **INVALID\_HANDLE\_VALUE**   (-1)\
 \#define **GET\_PAGESIZE**(x)   ((x) = sysconf(\_SC\_PAGE\_SIZE))\
 \#define **MNAME\_LEN**   (sizeof(pthread\_mutex\_t))\
 \#define **LOCK\_MUTEX**(rc,  env,  mutex)   ((rc) = **LOCK\_MUTEX0**(mutex))\
 \#define **mdb\_mutex\_failed**(env,  mutex,  rc)   (rc)\
 \#define **MDB\_DSYNC**   O\_SYNC\
 \#define **MDB\_FDATASYNC**   fdatasync\
 \#define **MDB\_MSYNC**(addr,  len,  flags)   msync(addr,len,flags)\
 \#define **MS\_SYNC**   1\
 \#define **MS\_ASYNC**   0\
 \#define **MDB\_DEBUG**   0\
 \#define **DPRINTF**(args)   ((void) 0)\
 \#define **DPUTS**(arg)   DPRINTF(('%s', arg))\
 \#define **DDBI**(mc)   	(((mc)-\>mc\_flags & **C\_SUB**) ? -(int)(mc)-\>mc\_dbi : (int)(mc)-\>mc\_dbi)\
 \#define **MAX\_PAGESIZE**   (**PAGEBASE** ? 0x10000 : 0x8000)\
 The maximum size of a database page.  #define **MDB\_MINKEYS**   2\
 \#define **MDB\_MAGIC**   0xBEEFC0DE\
 \#define **MDB\_DATA\_VERSION**   ((**MDB\_DEVEL**) ? 999 : 1)\
 \#define **MDB\_LOCK\_VERSION**   1\
 \#define **MDB\_MAXKEYSIZE**   ((**MDB\_DEVEL**) ? 0 : 511)\
 The max size of a key we can write, or 0 for computed max.  #define **ENV\_MAXKEY**(env)   (**MDB\_MAXKEYSIZE**)\
 \#define **MAXDATASIZE**   0xffffffffUL\
 The maximum size of a data item.  #define **DKBUF**\
 \#define **DKEY**(x)   0\
 \#define **P\_INVALID**   (~(**pgno\_t**)0)\
 \#define **F\_ISSET**(w,  f)   (((w) & (f)) == (f))\
 \#define **EVEN**(n)   (((n) + 1U) & -2) /\* sign-extending -2 to match n+1U \*/\
 \#define **DEFAULT\_MAPSIZE**   1048576\
 \#define **DEFAULT\_READERS**   126\
 \#define **CACHELINE**   64\
 \#define **mr\_txnid**   mru.mrx.mrb\_txnid\
 \#define **mr\_pid**   mru.mrx.mrb\_pid\
 \#define **mr\_tid**   mru.mrx.mrb\_tid\
 \#define **mti\_magic**   mt1.mtb.mtb\_magic\
 \#define **mti\_format**   mt1.mtb.mtb\_format\
 \#define **mti\_rmutex**   mt1.mtb.mtb\_rmutex\
 \#define **mti\_rmname**   mt1.mtb.mtb\_rmname\
 \#define **mti\_txnid**   mt1.mtb.mtb\_txnid\
 \#define **mti\_numreaders**   mt1.mtb.mtb\_numreaders\
 \#define **mti\_wmutex**   mt2.mt2\_wmutex\
 \#define **MDB\_LOCK\_FORMAT**\
 \#define **mp\_pgno**   mp\_p.p\_pgno\
 \#define **mp\_next**   mp\_p.p\_next\
 \#define **P\_BRANCH**   0x01\
 \#define **P\_LEAF**   0x02\
 \#define **P\_OVERFLOW**   0x04\
 \#define **P\_META**   0x08\
 \#define **P\_DIRTY**   0x10\
 \#define **P\_LEAF2**   0x20\
 \#define **P\_SUBP**   0x40\
 \#define **P\_LOOSE**   0x4000\
 \#define **P\_KEEP**   0x8000\
 \#define **mp\_lower**   mp\_pb.pb.pb\_lower\
 \#define **mp\_upper**   mp\_pb.pb.pb\_upper\
 \#define **mp\_pages**   mp\_pb.pb\_pages\
 \#define **MP\_PGNO**(p)   (((**MDB\_page2** \*)(void \*)(p))-\>mp2\_p)\
 \#define **MP\_PAD**(p)   (((**MDB\_page2** \*)(void \*)(p))-\>mp2\_pad)\
 \#define **MP\_FLAGS**(p)   (((**MDB\_page2** \*)(void \*)(p))-\>mp2\_flags)\
 \#define **MP\_LOWER**(p)   (((**MDB\_page2** \*)(void \*)(p))-\>mp2\_lower)\
 \#define **MP\_UPPER**(p)   (((**MDB\_page2** \*)(void \*)(p))-\>mp2\_upper)\
 \#define **MP\_PTRS**(p)   (((**MDB\_page2** \*)(void \*)(p))-\>mp2\_ptrs)\
 \#define **PAGEHDRSZ**   ((unsigned) offsetof(**MDB\_page**, mp\_ptrs))\
 \#define **METADATA**(p)   ((void \*)((char \*)(p) + **PAGEHDRSZ**))\
 \#define **PAGEBASE**   ((**MDB\_DEVEL**) ? **PAGEHDRSZ** : 0)\
 \#define **NUMKEYS**(p)   ((MP\_LOWER(p) - (**PAGEHDRSZ**-**PAGEBASE**)) \>\> 1)\
 \#define **SIZELEFT**(p)   (**indx\_t**)(MP\_UPPER(p) - MP\_LOWER(p))\
 \#define **PAGEFILL**(env,  p)\
 \#define **FILL\_THRESHOLD**   250\
 \#define **IS\_LEAF**(p)   **F\_ISSET**(MP\_FLAGS(p), **P\_LEAF**)\
 \#define **IS\_LEAF2**(p)   **F\_ISSET**(MP\_FLAGS(p), **P\_LEAF2**)\
 \#define **IS\_BRANCH**(p)   **F\_ISSET**(MP\_FLAGS(p), **P\_BRANCH**)\
 \#define **IS\_OVERFLOW**(p)   **F\_ISSET**(MP\_FLAGS(p), **P\_OVERFLOW**)\
 \#define **IS\_SUBP**(p)   **F\_ISSET**(MP\_FLAGS(p), **P\_SUBP**)\
 \#define **OVPAGES**(size,  psize)   ((**PAGEHDRSZ**-1 + (size)) / (psize) + 1)\
 \#define **NEXT\_LOOSE\_PAGE**(p)   (\*(**MDB\_page** \*\*)((p) + 2))\
 \#define **F\_BIGDATA**   0x01\
 \#define **F\_SUBDATA**   0x02\
 \#define **F\_DUPDATA**   0x04\
 \#define **NODE\_ADD\_FLAGS**   (**F\_DUPDATA**\|**F\_SUBDATA**\|**MDB\_RESERVE**\|**MDB\_APPEND**)\
 \#define **NODESIZE**   offsetof(**MDB\_node**, mn\_data)\
 \#define **PGNO\_TOPWORD**   ((**pgno\_t**)-1 \> 0xffffffffu ? 32 : 0)\
 \#define **INDXSIZE**(k)   (**NODESIZE** + ((k) == NULL ? 0 : (k)-\>mv\_size))\
 \#define **LEAFSIZE**(k,  d)   (**NODESIZE** + (k)-\>mv\_size + (d)-\>mv\_size)\
 \#define **NODEPTR**(p,  i)   ((**MDB\_node** \*)((char \*)(p) + MP\_PTRS(p)\[i\] + **PAGEBASE**))\
 \#define **NODEKEY**(node)   (void \*)((node)-\>mn\_data)\
 \#define **NODEDATA**(node)   (void \*)((char \*)(node)-\>mn\_data + (node)-\>mn\_ksize)\
 \#define **NODEPGNO**(node)\
 \#define **SETPGNO**(node,  pgno)\
 \#define **NODEDSZ**(node)   ((node)-\>mn\_lo \| ((unsigned)(node)-\>mn\_hi \<\< 16))\
 \#define **SETDSZ**(node,  size)\
 \#define **NODEKSZ**(node)   ((node)-\>mn\_ksize)\
 \#define **COPY\_PGNO**(dst,  src)\
 \#define **LEAF2KEY**(p,  i,  ks)   ((char \*)(p) + **PAGEHDRSZ** + ((i)\*(ks)))\
 \#define **MDB\_GET\_KEY**(node,  keyptr)\
 \#define **MDB\_GET\_KEY2**(node,  key)   { key.mv\_size = **NODEKSZ**(node); key.mv\_data = **NODEKEY**(node); }\
 \#define **MDB\_VALID**   0x8000\
 \#define **PERSISTENT\_FLAGS**   (0xffff & ~(**MDB\_VALID**))\
 \#define **VALID\_FLAGS**\
 \#define **FREE\_DBI**   0\
 \#define **MAIN\_DBI**   1\
 \#define **CORE\_DBS**   2\
 \#define **NUM\_METAS**   2\
 \#define **mm\_psize**   mm\_dbs\[**FREE\_DBI**\].md\_pad\
 \#define **mm\_flags**   mm\_dbs\[**FREE\_DBI**\].md\_flags\
 \#define **DB\_DIRTY**   0x01\
 \#define **DB\_STALE**   0x02\
 \#define **DB\_NEW**   0x04\
 \#define **DB\_VALID**   0x08\
 \#define **DB\_USRVALID**   0x10\
 \#define **DB\_DUPDATA**   0x20\
 \#define **MDB\_TXN\_BEGIN\_FLAGS**   **MDB\_RDONLY**\
 \#define **MDB\_TXN\_RDONLY**   **MDB\_RDONLY**\
 \#define **MDB\_TXN\_WRITEMAP**   **MDB\_WRITEMAP**\
 \#define **MDB\_TXN\_FINISHED**   0x01\
 \#define **MDB\_TXN\_ERROR**   0x02\
 \#define **MDB\_TXN\_DIRTY**   0x04\
 \#define **MDB\_TXN\_SPILLS**   0x08\
 \#define **MDB\_TXN\_HAS\_CHILD**   0x10\
 \#define **MDB\_TXN\_BLOCKED**   (**MDB\_TXN\_FINISHED**\|**MDB\_TXN\_ERROR**\|**MDB\_TXN\_HAS\_CHILD**)\
 \#define **CURSOR\_STACK**   32\
 \#define **C\_INITIALIZED**   0x01\
 \#define **C\_EOF**   0x02\
 \#define **C\_SUB**   0x04\
 \#define **C\_DEL**   0x08\
 \#define **C\_UNTRACK**   0x40\
 \#define **XCURSOR\_INITED**(mc)   	((mc)-\>mc\_xcursor && ((mc)-\>mc\_xcursor-\>mx\_cursor.mc\_flags & **C\_INITIALIZED**))\
 \#define **XCURSOR\_REFRESH**(mc,  top,  mp)\
 \#define **MDB\_FATAL\_ERROR**   0x80000000U\
 \#define **MDB\_ENV\_ACTIVE**   0x20000000U\
 \#define **MDB\_ENV\_TXKEY**   0x10000000U\
 \#define **MDB\_FSYNCONLY**   0x08000000U\
 \#define **me\_pglast**   me\_pgstate.mf\_pglast\
 \#define **me\_pghead**   me\_pgstate.mf\_pghead\
 \#define **me\_rmutex**   me\_txns-\>mti\_rmutex\
 \#define **me\_wmutex**   me\_txns-\>mti\_wmutex\
 \#define **MDB\_COMMIT\_PAGES**   64\
 \#define **MAX\_WRITE**   (0x40000000U \>\> (sizeof(ssize\_t) == 4))\
 \#define **TXN\_DBI\_EXIST**(txn,  dbi,  validity)   	((txn) && (dbi)\<(txn)-\>mt\_numdbs && ((txn)-\>mt\_dbflags\[dbi\] & (validity)))\
 \#define **TXN\_DBI\_CHANGED**(txn,  dbi)   	((txn)-\>mt\_dbiseqs\[dbi\] != (txn)-\>mt\_env-\>me\_dbiseqs\[dbi\])\
 \#define **MDB\_END\_NAMES**\
 \#define **MDB\_END\_OPMASK**   0x0F\
 \#define **MDB\_END\_UPDATE**   0x10\
 \#define **MDB\_END\_FREE**   0x20\
 \#define **MDB\_END\_SLOT**   **MDB\_NOTLS**\
 \#define **MDB\_PS\_MODIFY**   1\
 \#define **MDB\_PS\_ROOTONLY**   2\
 \#define **MDB\_PS\_FIRST**   4\
 \#define **MDB\_PS\_LAST**   8\
 \#define **MDB\_SPLIT\_REPLACE**   **MDB\_APPENDDUP**\
 \#define **mdb\_env\_close0**(env,  excl)   mdb\_env\_close1(env)\
 \#define **mdb\_cmp\_clong**   **mdb\_cmp\_cint**\
 \#define **mdb\_cassert**(mc,  expr)   mdb\_assert0((mc)-\>mc\_txn-\>mt\_env, expr, #expr)\
 \#define **mdb\_tassert**(txn,  expr)   mdb\_assert0((txn)-\>mt\_env, expr, #expr)\
 \#define **mdb\_eassert**(env,  expr)   mdb\_assert0(env, expr, #expr)\
 \#define **mdb\_assert0**(env,  expr,  expr\_txt)\
 \#define **DO\_PWRITE**(rc,  fd,  ptr,  size,  len,  pos)\
 \#define **MDB\_NAME**(str)   str\
 \#define **mdb\_name\_cpy**   strcpy\
 \#define **MDB\_SUFFLEN**   9\
 \#define **mdb\_fname\_destroy**(fname)   	do { if ((fname).mn\_alloced) free((fname).mn\_val); } while (0)\
 \#define **MDB\_CLOEXEC**   0\
 \#define **MDB\_ERRCODE\_ROFS**   EROFS\
 \#define **CHANGEABLE**   (**MDB\_NOSYNC**\|**MDB\_NOMETASYNC**\|**MDB\_MAPASYNC**\|**MDB\_NOMEMINIT**)\
 \#define **CHANGELESS**\
 \#define **MDB\_NOSPILL**   0x8000\
 \#define **WITH\_CURSOR\_TRACKING**(mn,  act)\
 \#define **MDB\_WBUF**   (1024\*1024)\
 \#define **MDB\_EOF**   0x10\
 \#define **DO\_WRITE**(rc,  fd,  ptr,  w2,  len)   len = write(fd, ptr, w2); rc = (len \>= 0)\
 \#define **DO\_WRITE**(rc,  fd,  ptr,  w2,  len)   len = write(fd, ptr, w2); rc = (len \>= 0)\

### Typedefs

typedef pthread\_mutex\_t **mdb\_mutex\_t**\[1\]\
 typedef pthread\_mutex\_t \* **mdb\_mutexref\_t**\
 typedef **MDB\_ID** **pgno\_t**\
 typedef **MDB\_ID** **txnid\_t**\
 typedef uint16\_t **indx\_t**\
 typedef char **mdb\_nchar\_t**\

### Enumerations

enum { **MDB\_END\_COMMITTED**, **MDB\_END\_EMPTY\_COMMIT**, **MDB\_END\_ABORT**, **MDB\_END\_RESET**, **MDB\_END\_RESET\_TMP**, **MDB\_END\_FAIL\_BEGIN**, **MDB\_END\_FAIL\_BEGINCHILD** }\
 enum **Pidlock\_op** { **Pidset** = F\_SETLK, **Pidcheck** = F\_GETLK }\
 enum **mdb\_fopen\_type** { **MDB\_O\_RDONLY** = O\_RDONLY, **MDB\_O\_RDWR** = O\_RDWR \|O\_CREAT, **MDB\_O\_META** = O\_WRONLY\|MDB\_DSYNC \|MDB\_CLOEXEC, **MDB\_O\_COPY** = O\_WRONLY\|O\_CREAT\|O\_EXCL\|MDB\_CLOEXEC, **MDB\_O\_MASK** = MDB\_O\_RDWR\|MDB\_CLOEXEC \| MDB\_O\_RDONLY\|MDB\_O\_META\|MDB\_O\_COPY, **MDB\_O\_LOCKS** = MDB\_O\_RDWR\|MDB\_CLOEXEC \| ((MDB\_O\_MASK+1) & ~MDB\_O\_MASK) }\

### Functions

static int **mdb\_page\_alloc** (**MDB\_cursor** \*mc, int num, **MDB\_page** \*\*mp)\
 static int **mdb\_page\_new** (**MDB\_cursor** \*mc, uint32\_t flags, int num, **MDB\_page** \*\*mp)\
 static int **mdb\_page\_touch** (**MDB\_cursor** \*mc)\
 static void **mdb\_txn\_end** (**MDB\_txn** \*txn, unsigned mode)\
 static int **mdb\_page\_get** (**MDB\_cursor** \*mc, **pgno\_t** pgno, **MDB\_page** \*\*mp, int \*lvl)\
 static int **mdb\_page\_search\_root** (**MDB\_cursor** \*mc, **MDB\_val** \*key, int modify)\
 static int **mdb\_page\_search** (**MDB\_cursor** \*mc, **MDB\_val** \*key, int flags)\
 static int **mdb\_page\_merge** (**MDB\_cursor** \*csrc, **MDB\_cursor** \*cdst)\
 static int **mdb\_page\_split** (**MDB\_cursor** \*mc, **MDB\_val** \*newkey, **MDB\_val** \*newdata, **pgno\_t** newpgno, unsigned int nflags)\
 static int **mdb\_env\_read\_header** (**MDB\_env** \*env, **MDB\_meta** \*meta)\
 static **MDB\_meta** \* **mdb\_env\_pick\_meta** (const **MDB\_env** \*env)\
 static int **mdb\_env\_write\_meta** (**MDB\_txn** \*txn)\
 static void **mdb\_env\_close0** (**MDB\_env** \*env, int excl)\
 static **MDB\_node** \* **mdb\_node\_search** (**MDB\_cursor** \*mc, **MDB\_val** \*key, int \*exactp)\
 static int **mdb\_node\_add** (**MDB\_cursor** \*mc, **indx\_t** indx, **MDB\_val** \*key, **MDB\_val** \*data, **pgno\_t** pgno, unsigned int flags)\
 static void **mdb\_node\_del** (**MDB\_cursor** \*mc, int ksize)\
 static void **mdb\_node\_shrink** (**MDB\_page** \*mp, **indx\_t** indx)\
 static int **mdb\_node\_move** (**MDB\_cursor** \*csrc, **MDB\_cursor** \*cdst, int fromleft)\
 static int **mdb\_node\_read** (**MDB\_cursor** \*mc, **MDB\_node** \*leaf, **MDB\_val** \*data)\
 static size\_t **mdb\_leaf\_size** (**MDB\_env** \*env, **MDB\_val** \*key, **MDB\_val** \*data)\
 static size\_t **mdb\_branch\_size** (**MDB\_env** \*env, **MDB\_val** \*key)\
 static int **mdb\_rebalance** (**MDB\_cursor** \*mc)\
 static int **mdb\_update\_key** (**MDB\_cursor** \*mc, **MDB\_val** \*key)\
 static void **mdb\_cursor\_pop** (**MDB\_cursor** \*mc)\
 static int **mdb\_cursor\_push** (**MDB\_cursor** \*mc, **MDB\_page** \*mp)\
 static int **mdb\_cursor\_del0** (**MDB\_cursor** \*mc)\
 static int **mdb\_del0** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_val** \*key, **MDB\_val** \*data, unsigned flags)\
 static int **mdb\_cursor\_sibling** (**MDB\_cursor** \*mc, int move\_right)\
 static int **mdb\_cursor\_next** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data, **MDB\_cursor\_op** op)\
 static int **mdb\_cursor\_prev** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data, **MDB\_cursor\_op** op)\
 static int **mdb\_cursor\_set** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data, **MDB\_cursor\_op** op, int \*exactp)\
 static int **mdb\_cursor\_first** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data)\
 static int **mdb\_cursor\_last** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data)\
 static void **mdb\_cursor\_init** (**MDB\_cursor** \*mc, **MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_xcursor** \*mx)\
 static void **mdb\_xcursor\_init0** (**MDB\_cursor** \*mc)\
 static void **mdb\_xcursor\_init1** (**MDB\_cursor** \*mc, **MDB\_node** \*node)\
 static void **mdb\_xcursor\_init2** (**MDB\_cursor** \*mc, **MDB\_xcursor** \*src\_mx, int force)\
 static int **mdb\_drop0** (**MDB\_cursor** \*mc, int subs)\
 static void **mdb\_default\_cmp** (**MDB\_txn** \*txn, **MDB\_dbi** dbi)\
 static int **mdb\_reader\_check0** (**MDB\_env** \*env, int rlocked, int \*dead)\
 char \*ESECT **mdb\_version** (int \*major, int \*minor, int \*patch)\
 Return the LMDB library version information.  char \* **mdb\_strerror** (int err)\
 Return a string describing a given error code.  static void ESECT **mdb\_assert\_fail** (**MDB\_env** \*env, const char \*expr\_txt, const char \*func, const char \*file, int line)\
 int **mdb\_cmp** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, const **MDB\_val** \*a, const **MDB\_val** \*b)\
 Compare two data items according to a particular database.  int **mdb\_dcmp** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, const **MDB\_val** \*a, const **MDB\_val** \*b)\
 Compare two data items according to a particular database.  static **MDB\_page** \* **mdb\_page\_malloc** (**MDB\_txn** \*txn, unsigned num)\
 static void **mdb\_page\_free** (**MDB\_env** \*env, **MDB\_page** \*mp)\
 static void **mdb\_dpage\_free** (**MDB\_env** \*env, **MDB\_page** \*dp)\
 static void **mdb\_dlist\_free** (**MDB\_txn** \*txn)\
 static int **mdb\_page\_loose** (**MDB\_cursor** \*mc, **MDB\_page** \*mp)\
 static int **mdb\_pages\_xkeep** (**MDB\_cursor** \*mc, unsigned pflags, int all)\
 static int **mdb\_page\_flush** (**MDB\_txn** \*txn, int keep)\
 static int **mdb\_page\_spill** (**MDB\_cursor** \*m0, **MDB\_val** \*key, **MDB\_val** \*data)\
 static **txnid\_t** **mdb\_find\_oldest** (**MDB\_txn** \*txn)\
 static void **mdb\_page\_dirty** (**MDB\_txn** \*txn, **MDB\_page** \*mp)\
 static void **mdb\_page\_copy** (**MDB\_page** \*dst, **MDB\_page** \*src, unsigned int psize)\
 static int **mdb\_page\_unspill** (**MDB\_txn** \*txn, **MDB\_page** \*mp, **MDB\_page** \*\*ret)\
 int **mdb\_env\_sync** (**MDB\_env** \*env, int force)\
 Flush the data buffers to disk.  static int **mdb\_cursor\_shadow** (**MDB\_txn** \*src, **MDB\_txn** \*dst)\
 static void **mdb\_cursors\_close** (**MDB\_txn** \*txn, unsigned merge)\
 static int **mdb\_reader\_pid** (**MDB\_env** \*env, enum Pidlock\_op op, MDB\_PID\_T pid)\
 static int **mdb\_txn\_renew0** (**MDB\_txn** \*txn)\
 int **mdb\_txn\_renew** (**MDB\_txn** \*txn)\
 Renew a read-only transaction.  int **mdb\_txn\_begin** (**MDB\_env** \*env, **MDB\_txn** \*parent, unsigned int flags, **MDB\_txn** \*\*ret)\
 Create a transaction for use with the environment.  **MDB\_env** \* **mdb\_txn\_env** (**MDB\_txn** \*txn)\
 Returns the transaction's **MDB\_env**.  size\_t **mdb\_txn\_id** (**MDB\_txn** \*txn)\
 Return the transaction's ID.  static void **mdb\_dbis\_update** (**MDB\_txn** \*txn, int keep)\
 void **mdb\_txn\_reset** (**MDB\_txn** \*txn)\
 Reset a read-only transaction.  void **mdb\_txn\_abort** (**MDB\_txn** \*txn)\
 Abandon all the operations of the transaction instead of saving them.  static int **mdb\_freelist\_save** (**MDB\_txn** \*txn)\
 int **mdb\_txn\_commit** (**MDB\_txn** \*txn)\
 Commit all the operations of a transaction into the database.  static void ESECT **mdb\_env\_init\_meta0** (**MDB\_env** \*env, **MDB\_meta** \*meta)\
 static int ESECT **mdb\_env\_init\_meta** (**MDB\_env** \*env, **MDB\_meta** \*meta)\
 int ESECT **mdb\_env\_create** (**MDB\_env** \*\*env)\
 Create an LMDB environment handle.  static int ESECT **mdb\_env\_map** (**MDB\_env** \*env, void \*addr)\
 int ESECT **mdb\_env\_set\_mapsize** (**MDB\_env** \*env, size\_t size)\
 Set the size of the memory map to use for this environment.  int ESECT **mdb\_env\_set\_maxdbs** (**MDB\_env** \*env, **MDB\_dbi** dbs)\
 Set the maximum number of named databases for the environment.  int ESECT **mdb\_env\_set\_maxreaders** (**MDB\_env** \*env, unsigned int readers)\
 Set the maximum number of threads/reader slots for the environment.  int ESECT **mdb\_env\_get\_maxreaders** (**MDB\_env** \*env, unsigned int \*readers)\
 Get the maximum number of threads/reader slots for the environment.  static int ESECT **mdb\_fsize** (**HANDLE** fd, size\_t \*size)\
 static int ESECT **mdb\_fname\_init** (const char \*path, unsigned envflags, **MDB\_name** \*fname)\
 static int ESECT **mdb\_fopen** (const **MDB\_env** \*env, **MDB\_name** \*fname, enum **mdb\_fopen\_type** which, **mdb\_mode\_t** mode, **HANDLE** \*res)\
 static int ESECT **mdb\_env\_open2** (**MDB\_env** \*env)\
 static void **mdb\_env\_reader\_dest** (void \*ptr)\
 static int ESECT **mdb\_env\_share\_locks** (**MDB\_env** \*env, int \*excl)\
 static int ESECT **mdb\_env\_excl\_lock** (**MDB\_env** \*env, int \*excl)\
 static int ESECT **mdb\_env\_setup\_locks** (**MDB\_env** \*env, **MDB\_name** \*fname, int mode, int \*excl)\
 int ESECT **mdb\_env\_open** (**MDB\_env** \*env, const char \*path, unsigned int flags, **mdb\_mode\_t** mode)\
 Open an environment handle.  void ESECT **mdb\_env\_close** (**MDB\_env** \*env)\
 Close the environment and release the memory map.  static int **mdb\_cmp\_long** (const **MDB\_val** \*a, const **MDB\_val** \*b)\
 static int **mdb\_cmp\_int** (const **MDB\_val** \*a, const **MDB\_val** \*b)\
 static int **mdb\_cmp\_cint** (const **MDB\_val** \*a, const **MDB\_val** \*b)\
 static int **mdb\_cmp\_memn** (const **MDB\_val** \*a, const **MDB\_val** \*b)\
 static int **mdb\_cmp\_memnr** (const **MDB\_val** \*a, const **MDB\_val** \*b)\
 static int **mdb\_page\_search\_lowest** (**MDB\_cursor** \*mc)\
 static int **mdb\_ovpage\_free** (**MDB\_cursor** \*mc, **MDB\_page** \*mp)\
 int **mdb\_get** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_val** \*key, **MDB\_val** \*data)\
 Get items from a database.  int **mdb\_cursor\_get** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data, **MDB\_cursor\_op** op)\
 Retrieve by cursor.  static int **mdb\_cursor\_touch** (**MDB\_cursor** \*mc)\
 int **mdb\_cursor\_put** (**MDB\_cursor** \*mc, **MDB\_val** \*key, **MDB\_val** \*data, unsigned int flags)\
 Store by cursor.  int **mdb\_cursor\_del** (**MDB\_cursor** \*mc, unsigned int flags)\
 Delete current key/data pair.  int **mdb\_cursor\_open** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_cursor** \*\*ret)\
 Create a cursor handle.  int **mdb\_cursor\_renew** (**MDB\_txn** \*txn, **MDB\_cursor** \*mc)\
 Renew a cursor handle.  int **mdb\_cursor\_count** (**MDB\_cursor** \*mc, size\_t \*countp)\
 Return count of duplicates for current key.  void **mdb\_cursor\_close** (**MDB\_cursor** \*mc)\
 Close a cursor handle.  **MDB\_txn** \* **mdb\_cursor\_txn** (**MDB\_cursor** \*mc)\
 Return the cursor's transaction handle.  **MDB\_dbi** **mdb\_cursor\_dbi** (**MDB\_cursor** \*mc)\
 Return the cursor's database handle.  static void **mdb\_cursor\_copy** (const **MDB\_cursor** \*csrc, **MDB\_cursor** \*cdst)\
 int **mdb\_del** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_val** \*key, **MDB\_val** \*data)\
 Delete items from a database.  int **mdb\_put** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_val** \*key, **MDB\_val** \*data, unsigned int flags)\
 Store items into a database.  static THREAD\_RET ESECT CALL\_CONV **mdb\_env\_copythr** (void \*arg)\
 static int ESECT **mdb\_env\_cthr\_toggle** (**mdb\_copy** \*my, int adjust)\
 static int ESECT **mdb\_env\_cwalk** (**mdb\_copy** \*my, **pgno\_t** \*pg, int flags)\
 static int ESECT **mdb\_env\_copyfd1** (**MDB\_env** \*env, **HANDLE** fd)\
 static int ESECT **mdb\_env\_copyfd0** (**MDB\_env** \*env, **HANDLE** fd)\
 int ESECT **mdb\_env\_copyfd2** (**MDB\_env** \*env, **HANDLE** fd, unsigned int flags)\
 int ESECT **mdb\_env\_copyfd** (**MDB\_env** \*env, **HANDLE** fd)\
 int ESECT **mdb\_env\_copy2** (**MDB\_env** \*env, const char \*path, unsigned int flags)\
 Copy an LMDB environment to the specified path, with options.  int ESECT **mdb\_env\_copy** (**MDB\_env** \*env, const char \*path)\
 Copy an LMDB environment to the specified path.  int ESECT **mdb\_env\_set\_flags** (**MDB\_env** \*env, unsigned int flag, int onoff)\
 Set environment flags.  int ESECT **mdb\_env\_get\_flags** (**MDB\_env** \*env, unsigned int \*arg)\
 Get environment flags.  int ESECT **mdb\_env\_set\_userctx** (**MDB\_env** \*env, void \*ctx)\
 Set application information associated with the **MDB\_env**.  void \*ESECT **mdb\_env\_get\_userctx** (**MDB\_env** \*env)\
 Get the application information associated with the **MDB\_env**.  int ESECT **mdb\_env\_set\_assert** (**MDB\_env** \*env, **MDB\_assert\_func** \*func)\
 int ESECT **mdb\_env\_get\_path** (**MDB\_env** \*env, const char \*\*arg)\
 Return the path that was used in **mdb\_env\_open()**.  int ESECT **mdb\_env\_get\_fd** (**MDB\_env** \*env, **mdb\_filehandle\_t** \*arg)\
 Return the filedescriptor for the given environment.  static int ESECT **mdb\_stat0** (**MDB\_env** \*env, **MDB\_db** \*db, **MDB\_stat** \*arg)\
 int ESECT **mdb\_env\_stat** (**MDB\_env** \*env, **MDB\_stat** \*arg)\
 Return statistics about the LMDB environment.  int ESECT **mdb\_env\_info** (**MDB\_env** \*env, **MDB\_envinfo** \*arg)\
 Return information about the LMDB environment.  int **mdb\_dbi\_open** (**MDB\_txn** \*txn, const char \*name, unsigned int flags, **MDB\_dbi** \*dbi)\
 Open a database in the environment.  int ESECT **mdb\_stat** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_stat** \*arg)\
 Retrieve statistics for a database.  void **mdb\_dbi\_close** (**MDB\_env** \*env, **MDB\_dbi** dbi)\
 Close a database handle. Normally unnecessary. Use with care:  int **mdb\_dbi\_flags** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, unsigned int \*flags)\
 Retrieve the DB flags for a database handle.  int **mdb\_drop** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, int del)\
 Empty or delete+close a database.  int **mdb\_set\_compare** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_cmp\_func** \*cmp)\
 Set a custom key comparison function for a database.  int **mdb\_set\_dupsort** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_cmp\_func** \*cmp)\
 Set a custom data comparison function for a **MDB\_DUPSORT** database.  int **mdb\_set\_relfunc** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, **MDB\_rel\_func** \*rel)\
 Set a relocation function for a **MDB\_FIXEDMAP** database.  int **mdb\_set\_relctx** (**MDB\_txn** \*txn, **MDB\_dbi** dbi, void \*ctx)\
 Set a context pointer for a **MDB\_FIXEDMAP** database's relocation function.  int ESECT **mdb\_env\_get\_maxkeysize** (**MDB\_env** \*env)\
 Get the maximum size of keys and **MDB\_DUPSORT** data we can write.  int ESECT **mdb\_reader\_list** (**MDB\_env** \*env, **MDB\_msg\_func** \*func, void \*ctx)\
 Dump the entries in the reader lock table.  static int ESECT **mdb\_pid\_insert** (MDB\_PID\_T \*ids, MDB\_PID\_T pid)\
 int ESECT **mdb\_reader\_check** (**MDB\_env** \*env, int \*dead)\
 Check for stale entries in the reader lock table.

### Variables

static char \*const **mdb\_errstr** \[\]\
 static const **mdb\_nchar\_t** \*const **mdb\_suffixes** \[2\]\[2\]\

## Detailed Description

Lightning memory-mapped database library.

A Btree-based database management library modeled loosely on the BerkeleyDB API, but much simplified.

## Macro Definition Documentation

### #define mr\_txnid mru.mrx.mrb\_txnid

shorthand for mrb\_txnid

### #define mm\_psize mm\_dbs\[FREE\_DBI\].md\_pad

The size of pages used in this DB

### #define mm\_flags mm\_dbs\[FREE\_DBI\].md\_flags

Any persistent environment flags. **Environment Flags**

### #define MDB\_FATAL\_ERROR 0x80000000U

Failed to update the meta page. Probably an I/O error.

### #define MDB\_ENV\_ACTIVE 0x20000000U

Some fields are initialized.

### #define MDB\_ENV\_TXKEY 0x10000000U

me\_txkey is set

### #define MDB\_FSYNCONLY 0x08000000U

fdatasync is unreliable

### #define me\_rmutex me\_txns-\>mti\_rmutex

Shared reader lock

### #define me\_wmutex me\_txns-\>mti\_wmutex

Shared writer lock

### #define DO\_PWRITE(rc, fd, ptr, size, len, pos)

**Value:**

```
    do {     len = pwrite(fd, ptr, size, pos);       if (len == -1 && ErrCode() == EINTR) continue;     rc = (len >= 0); break; } while(1)
```

## Author

Generated automatically by Doxygen for LMDB from the source code.
