lmdb 0.6 → 0.6.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (38) hide show
  1. checksums.yaml +4 -4
  2. data/ext/lmdb_ext/extconf.rb +7 -3
  3. data/ext/lmdb_ext/lmdb_ext.c +120 -110
  4. data/lib/lmdb/version.rb +1 -1
  5. data/lmdb.gemspec +4 -4
  6. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/.gitignore +8 -0
  7. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/COPYRIGHT +1 -1
  8. data/vendor/libraries/liblmdb/Doxyfile +1631 -0
  9. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/LICENSE +0 -0
  10. data/vendor/libraries/liblmdb/Makefile +118 -0
  11. data/vendor/libraries/liblmdb/intro.doc +192 -0
  12. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/lmdb.h +161 -61
  13. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/mdb.c +3244 -1302
  14. data/vendor/libraries/liblmdb/mdb_copy.1 +61 -0
  15. data/vendor/libraries/liblmdb/mdb_copy.c +84 -0
  16. data/vendor/libraries/liblmdb/mdb_drop.1 +40 -0
  17. data/vendor/libraries/liblmdb/mdb_drop.c +135 -0
  18. data/vendor/libraries/liblmdb/mdb_dump.1 +81 -0
  19. data/vendor/libraries/liblmdb/mdb_dump.c +319 -0
  20. data/vendor/libraries/liblmdb/mdb_load.1 +84 -0
  21. data/vendor/libraries/liblmdb/mdb_load.c +492 -0
  22. data/vendor/libraries/liblmdb/mdb_stat.1 +70 -0
  23. data/vendor/libraries/liblmdb/mdb_stat.c +264 -0
  24. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/midl.c +66 -5
  25. data/{ext/lmdb_ext → vendor/libraries}/liblmdb/midl.h +19 -5
  26. data/vendor/libraries/liblmdb/mtest.c +177 -0
  27. data/vendor/libraries/liblmdb/mtest2.c +124 -0
  28. data/vendor/libraries/liblmdb/mtest3.c +133 -0
  29. data/vendor/libraries/liblmdb/mtest4.c +168 -0
  30. data/vendor/libraries/liblmdb/mtest5.c +135 -0
  31. data/vendor/libraries/liblmdb/mtest6.c +141 -0
  32. data/vendor/libraries/liblmdb/sample-bdb.txt +73 -0
  33. data/vendor/libraries/liblmdb/sample-mdb.txt +62 -0
  34. data/vendor/libraries/liblmdb/tooltag +27 -0
  35. metadata +34 -14
  36. data/.gitignore +0 -15
  37. data/.travis.yml +0 -14
  38. data/ext/lmdb_ext/liblmdb/CHANGES +0 -112
@@ -0,0 +1,84 @@
1
+ .TH MDB_LOAD 1 "2015/09/30" "LMDB 0.9.17"
2
+ .\" Copyright 2014-2021 Howard Chu, Symas Corp. All Rights Reserved.
3
+ .\" Copying restrictions apply. See COPYRIGHT/LICENSE.
4
+ .SH NAME
5
+ mdb_load \- LMDB environment import tool
6
+ .SH SYNOPSIS
7
+ .B mdb_load
8
+ [\c
9
+ .BR \-V ]
10
+ [\c
11
+ .BI \-f \ file\fR]
12
+ [\c
13
+ .BR \-n ]
14
+ [\c
15
+ .BI \-s \ subdb\fR]
16
+ [\c
17
+ .BR \-N ]
18
+ [\c
19
+ .BR \-T ]
20
+ .BR \ envpath
21
+ .SH DESCRIPTION
22
+ The
23
+ .B mdb_load
24
+ utility reads from the standard input and loads it into the
25
+ LMDB environment
26
+ .BR envpath .
27
+
28
+ The input to
29
+ .B mdb_load
30
+ must be in the output format specified by the
31
+ .BR mdb_dump (1)
32
+ utility or as specified by the
33
+ .B -T
34
+ option below.
35
+ .SH OPTIONS
36
+ .TP
37
+ .BR \-V
38
+ Write the library version number to the standard output, and exit.
39
+ .TP
40
+ .BR \-a
41
+ Append all records in the order they appear in the input. The input is assumed to already be
42
+ in correctly sorted order and no sorting or checking for redundant values will be performed.
43
+ This option must be used to reload data that was produced by running
44
+ .B mdb_dump
45
+ on a database that uses custom compare functions.
46
+ .TP
47
+ .BR \-f \ file
48
+ Read from the specified file instead of from the standard input.
49
+ .TP
50
+ .BR \-n
51
+ Load an LMDB database which does not use subdirectories.
52
+ .TP
53
+ .BR \-s \ subdb
54
+ Load a specific subdatabase. If no database is specified, data is loaded into the main database.
55
+ .TP
56
+ .BR \-N
57
+ Don't overwrite existing records when loading into an already existing database; just skip them.
58
+ .TP
59
+ .BR \-T
60
+ Load data from simple text files. The input must be paired lines of text, where the first
61
+ line of the pair is the key item, and the second line of the pair is its corresponding
62
+ data item.
63
+
64
+ A simple escape mechanism, where newline and backslash (\\) characters are special, is
65
+ applied to the text input. Newline characters are interpreted as record separators.
66
+ Backslash characters in the text will be interpreted in one of two ways: If the backslash
67
+ character precedes another backslash character, the pair will be interpreted as a literal
68
+ backslash. If the backslash character precedes any other character, the two characters
69
+ following the backslash will be interpreted as a hexadecimal specification of a single
70
+ character; for example, \\0a is a newline character in the ASCII character set.
71
+
72
+ For this reason, any backslash or newline characters that naturally occur in the text
73
+ input must be escaped to avoid misinterpretation by
74
+ .BR mdb_load .
75
+
76
+ .SH DIAGNOSTICS
77
+ Exit status is zero if no errors occur.
78
+ Errors result in a non-zero exit status and
79
+ a diagnostic message being written to standard error.
80
+
81
+ .SH "SEE ALSO"
82
+ .BR mdb_dump (1)
83
+ .SH AUTHOR
84
+ Howard Chu of Symas Corporation <http://www.symas.com>
@@ -0,0 +1,492 @@
1
+ /* mdb_load.c - memory-mapped database load tool */
2
+ /*
3
+ * Copyright 2011-2021 Howard Chu, Symas Corp.
4
+ * All rights reserved.
5
+ *
6
+ * Redistribution and use in source and binary forms, with or without
7
+ * modification, are permitted only as authorized by the OpenLDAP
8
+ * Public License.
9
+ *
10
+ * A copy of this license is available in the file LICENSE in the
11
+ * top-level directory of the distribution or, alternatively, at
12
+ * <http://www.OpenLDAP.org/license.html>.
13
+ */
14
+ #include <stdio.h>
15
+ #include <stdlib.h>
16
+ #include <errno.h>
17
+ #include <string.h>
18
+ #include <ctype.h>
19
+ #include <unistd.h>
20
+ #include "lmdb.h"
21
+
22
+ #define PRINT 1
23
+ #define NOHDR 2
24
+ static int mode;
25
+
26
+ static char *subname = NULL;
27
+
28
+ static mdb_size_t lineno;
29
+ static int version;
30
+
31
+ static int flags;
32
+
33
+ static char *prog;
34
+
35
+ static int Eof;
36
+
37
+ static MDB_envinfo info;
38
+
39
+ static MDB_val kbuf, dbuf;
40
+ static MDB_val k0buf;
41
+
42
+ #define Yu MDB_PRIy(u)
43
+
44
+ #define STRLENOF(s) (sizeof(s)-1)
45
+
46
+ typedef struct flagbit {
47
+ int bit;
48
+ char *name;
49
+ int len;
50
+ } flagbit;
51
+
52
+ #define S(s) s, STRLENOF(s)
53
+
54
+ flagbit dbflags[] = {
55
+ { MDB_REVERSEKEY, S("reversekey") },
56
+ { MDB_DUPSORT, S("dupsort") },
57
+ { MDB_INTEGERKEY, S("integerkey") },
58
+ { MDB_DUPFIXED, S("dupfixed") },
59
+ { MDB_INTEGERDUP, S("integerdup") },
60
+ { MDB_REVERSEDUP, S("reversedup") },
61
+ { 0, NULL, 0 }
62
+ };
63
+
64
+ static void readhdr(void)
65
+ {
66
+ char *ptr;
67
+
68
+ flags = 0;
69
+ while (fgets(dbuf.mv_data, dbuf.mv_size, stdin) != NULL) {
70
+ lineno++;
71
+ if (!strncmp(dbuf.mv_data, "VERSION=", STRLENOF("VERSION="))) {
72
+ version=atoi((char *)dbuf.mv_data+STRLENOF("VERSION="));
73
+ if (version > 3) {
74
+ fprintf(stderr, "%s: line %"Yu": unsupported VERSION %d\n",
75
+ prog, lineno, version);
76
+ exit(EXIT_FAILURE);
77
+ }
78
+ } else if (!strncmp(dbuf.mv_data, "HEADER=END", STRLENOF("HEADER=END"))) {
79
+ break;
80
+ } else if (!strncmp(dbuf.mv_data, "format=", STRLENOF("format="))) {
81
+ if (!strncmp((char *)dbuf.mv_data+STRLENOF("FORMAT="), "print", STRLENOF("print")))
82
+ mode |= PRINT;
83
+ else if (strncmp((char *)dbuf.mv_data+STRLENOF("FORMAT="), "bytevalue", STRLENOF("bytevalue"))) {
84
+ fprintf(stderr, "%s: line %"Yu": unsupported FORMAT %s\n",
85
+ prog, lineno, (char *)dbuf.mv_data+STRLENOF("FORMAT="));
86
+ exit(EXIT_FAILURE);
87
+ }
88
+ } else if (!strncmp(dbuf.mv_data, "database=", STRLENOF("database="))) {
89
+ ptr = memchr(dbuf.mv_data, '\n', dbuf.mv_size);
90
+ if (ptr) *ptr = '\0';
91
+ if (subname) free(subname);
92
+ subname = strdup((char *)dbuf.mv_data+STRLENOF("database="));
93
+ } else if (!strncmp(dbuf.mv_data, "type=", STRLENOF("type="))) {
94
+ if (strncmp((char *)dbuf.mv_data+STRLENOF("type="), "btree", STRLENOF("btree"))) {
95
+ fprintf(stderr, "%s: line %"Yu": unsupported type %s\n",
96
+ prog, lineno, (char *)dbuf.mv_data+STRLENOF("type="));
97
+ exit(EXIT_FAILURE);
98
+ }
99
+ } else if (!strncmp(dbuf.mv_data, "mapaddr=", STRLENOF("mapaddr="))) {
100
+ int i;
101
+ ptr = memchr(dbuf.mv_data, '\n', dbuf.mv_size);
102
+ if (ptr) *ptr = '\0';
103
+ i = sscanf((char *)dbuf.mv_data+STRLENOF("mapaddr="), "%p", &info.me_mapaddr);
104
+ if (i != 1) {
105
+ fprintf(stderr, "%s: line %"Yu": invalid mapaddr %s\n",
106
+ prog, lineno, (char *)dbuf.mv_data+STRLENOF("mapaddr="));
107
+ exit(EXIT_FAILURE);
108
+ }
109
+ } else if (!strncmp(dbuf.mv_data, "mapsize=", STRLENOF("mapsize="))) {
110
+ int i;
111
+ ptr = memchr(dbuf.mv_data, '\n', dbuf.mv_size);
112
+ if (ptr) *ptr = '\0';
113
+ i = sscanf((char *)dbuf.mv_data+STRLENOF("mapsize="),
114
+ "%" MDB_SCNy(u), &info.me_mapsize);
115
+ if (i != 1) {
116
+ fprintf(stderr, "%s: line %"Yu": invalid mapsize %s\n",
117
+ prog, lineno, (char *)dbuf.mv_data+STRLENOF("mapsize="));
118
+ exit(EXIT_FAILURE);
119
+ }
120
+ } else if (!strncmp(dbuf.mv_data, "maxreaders=", STRLENOF("maxreaders="))) {
121
+ int i;
122
+ ptr = memchr(dbuf.mv_data, '\n', dbuf.mv_size);
123
+ if (ptr) *ptr = '\0';
124
+ i = sscanf((char *)dbuf.mv_data+STRLENOF("maxreaders="), "%u", &info.me_maxreaders);
125
+ if (i != 1) {
126
+ fprintf(stderr, "%s: line %"Yu": invalid maxreaders %s\n",
127
+ prog, lineno, (char *)dbuf.mv_data+STRLENOF("maxreaders="));
128
+ exit(EXIT_FAILURE);
129
+ }
130
+ } else {
131
+ int i;
132
+ for (i=0; dbflags[i].bit; i++) {
133
+ if (!strncmp(dbuf.mv_data, dbflags[i].name, dbflags[i].len) &&
134
+ ((char *)dbuf.mv_data)[dbflags[i].len] == '=') {
135
+ flags |= dbflags[i].bit;
136
+ break;
137
+ }
138
+ }
139
+ if (!dbflags[i].bit) {
140
+ ptr = memchr(dbuf.mv_data, '=', dbuf.mv_size);
141
+ if (!ptr) {
142
+ fprintf(stderr, "%s: line %"Yu": unexpected format\n",
143
+ prog, lineno);
144
+ exit(EXIT_FAILURE);
145
+ } else {
146
+ *ptr = '\0';
147
+ fprintf(stderr, "%s: line %"Yu": unrecognized keyword ignored: %s\n",
148
+ prog, lineno, (char *)dbuf.mv_data);
149
+ }
150
+ }
151
+ }
152
+ }
153
+ }
154
+
155
+ static void badend(void)
156
+ {
157
+ fprintf(stderr, "%s: line %"Yu": unexpected end of input\n",
158
+ prog, lineno);
159
+ }
160
+
161
+ static int unhex(unsigned char *c2)
162
+ {
163
+ int x, c;
164
+ x = *c2++ & 0x4f;
165
+ if (x & 0x40)
166
+ x -= 55;
167
+ c = x << 4;
168
+ x = *c2 & 0x4f;
169
+ if (x & 0x40)
170
+ x -= 55;
171
+ c |= x;
172
+ return c;
173
+ }
174
+
175
+ static int readline(MDB_val *out, MDB_val *buf)
176
+ {
177
+ unsigned char *c1, *c2, *end;
178
+ size_t len, l2;
179
+ int c;
180
+
181
+ if (!(mode & NOHDR)) {
182
+ c = fgetc(stdin);
183
+ if (c == EOF) {
184
+ Eof = 1;
185
+ return EOF;
186
+ }
187
+ if (c != ' ') {
188
+ lineno++;
189
+ if (fgets(buf->mv_data, buf->mv_size, stdin) == NULL) {
190
+ badend:
191
+ Eof = 1;
192
+ badend();
193
+ return EOF;
194
+ }
195
+ if (c == 'D' && !strncmp(buf->mv_data, "ATA=END", STRLENOF("ATA=END")))
196
+ return EOF;
197
+ goto badend;
198
+ }
199
+ }
200
+ if (fgets(buf->mv_data, buf->mv_size, stdin) == NULL) {
201
+ Eof = 1;
202
+ return EOF;
203
+ }
204
+ lineno++;
205
+
206
+ c1 = buf->mv_data;
207
+ len = strlen((char *)c1);
208
+ l2 = len;
209
+
210
+ /* Is buffer too short? */
211
+ while (c1[len-1] != '\n') {
212
+ buf->mv_data = realloc(buf->mv_data, buf->mv_size*2);
213
+ if (!buf->mv_data) {
214
+ Eof = 1;
215
+ fprintf(stderr, "%s: line %"Yu": out of memory, line too long\n",
216
+ prog, lineno);
217
+ return EOF;
218
+ }
219
+ c1 = buf->mv_data;
220
+ c1 += l2;
221
+ if (fgets((char *)c1, buf->mv_size+1, stdin) == NULL) {
222
+ Eof = 1;
223
+ badend();
224
+ return EOF;
225
+ }
226
+ buf->mv_size *= 2;
227
+ len = strlen((char *)c1);
228
+ l2 += len;
229
+ }
230
+ c1 = c2 = buf->mv_data;
231
+ len = l2;
232
+ c1[--len] = '\0';
233
+ end = c1 + len;
234
+
235
+ if (mode & PRINT) {
236
+ while (c2 < end) {
237
+ if (*c2 == '\\') {
238
+ if (c2[1] == '\\') {
239
+ *c1++ = *c2;
240
+ } else {
241
+ if (c2+3 > end || !isxdigit(c2[1]) || !isxdigit(c2[2])) {
242
+ Eof = 1;
243
+ badend();
244
+ return EOF;
245
+ }
246
+ *c1++ = unhex(++c2);
247
+ }
248
+ c2 += 2;
249
+ } else {
250
+ /* copies are redundant when no escapes were used */
251
+ *c1++ = *c2++;
252
+ }
253
+ }
254
+ } else {
255
+ /* odd length not allowed */
256
+ if (len & 1) {
257
+ Eof = 1;
258
+ badend();
259
+ return EOF;
260
+ }
261
+ while (c2 < end) {
262
+ if (!isxdigit(*c2) || !isxdigit(c2[1])) {
263
+ Eof = 1;
264
+ badend();
265
+ return EOF;
266
+ }
267
+ *c1++ = unhex(c2);
268
+ c2 += 2;
269
+ }
270
+ }
271
+ c2 = out->mv_data = buf->mv_data;
272
+ out->mv_size = c1 - c2;
273
+
274
+ return 0;
275
+ }
276
+
277
+ static void usage(void)
278
+ {
279
+ fprintf(stderr, "usage: %s [-V] [-a] [-f input] [-n] [-s name] [-N] [-T] dbpath\n", prog);
280
+ exit(EXIT_FAILURE);
281
+ }
282
+
283
+ static int greater(const MDB_val *a, const MDB_val *b)
284
+ {
285
+ return 1;
286
+ }
287
+
288
+ int main(int argc, char *argv[])
289
+ {
290
+ int i, rc;
291
+ MDB_env *env;
292
+ MDB_txn *txn;
293
+ MDB_cursor *mc;
294
+ MDB_dbi dbi;
295
+ char *envname;
296
+ int envflags = MDB_NOSYNC, putflags = 0;
297
+ int dohdr = 0, append = 0;
298
+ MDB_val prevk;
299
+
300
+ prog = argv[0];
301
+
302
+ if (argc < 2) {
303
+ usage();
304
+ }
305
+
306
+ /* -a: append records in input order
307
+ * -f: load file instead of stdin
308
+ * -n: use NOSUBDIR flag on env_open
309
+ * -s: load into named subDB
310
+ * -N: use NOOVERWRITE on puts
311
+ * -T: read plaintext
312
+ * -V: print version and exit
313
+ */
314
+ while ((i = getopt(argc, argv, "af:ns:NTV")) != EOF) {
315
+ switch(i) {
316
+ case 'V':
317
+ printf("%s\n", MDB_VERSION_STRING);
318
+ exit(0);
319
+ break;
320
+ case 'a':
321
+ append = 1;
322
+ break;
323
+ case 'f':
324
+ if (freopen(optarg, "r", stdin) == NULL) {
325
+ fprintf(stderr, "%s: %s: reopen: %s\n",
326
+ prog, optarg, strerror(errno));
327
+ exit(EXIT_FAILURE);
328
+ }
329
+ break;
330
+ case 'n':
331
+ envflags |= MDB_NOSUBDIR;
332
+ break;
333
+ case 's':
334
+ subname = strdup(optarg);
335
+ break;
336
+ case 'N':
337
+ putflags = MDB_NOOVERWRITE|MDB_NODUPDATA;
338
+ break;
339
+ case 'T':
340
+ mode |= NOHDR | PRINT;
341
+ break;
342
+ default:
343
+ usage();
344
+ }
345
+ }
346
+
347
+ if (optind != argc - 1)
348
+ usage();
349
+
350
+ dbuf.mv_size = 4096;
351
+ dbuf.mv_data = malloc(dbuf.mv_size);
352
+
353
+ if (!(mode & NOHDR))
354
+ readhdr();
355
+
356
+ envname = argv[optind];
357
+ rc = mdb_env_create(&env);
358
+ if (rc) {
359
+ fprintf(stderr, "mdb_env_create failed, error %d %s\n", rc, mdb_strerror(rc));
360
+ return EXIT_FAILURE;
361
+ }
362
+
363
+ mdb_env_set_maxdbs(env, 2);
364
+
365
+ if (info.me_maxreaders)
366
+ mdb_env_set_maxreaders(env, info.me_maxreaders);
367
+
368
+ if (info.me_mapsize)
369
+ mdb_env_set_mapsize(env, info.me_mapsize);
370
+
371
+ if (info.me_mapaddr)
372
+ envflags |= MDB_FIXEDMAP;
373
+
374
+ rc = mdb_env_open(env, envname, envflags, 0664);
375
+ if (rc) {
376
+ fprintf(stderr, "mdb_env_open failed, error %d %s\n", rc, mdb_strerror(rc));
377
+ goto env_close;
378
+ }
379
+
380
+ kbuf.mv_size = mdb_env_get_maxkeysize(env) * 2 + 2;
381
+ kbuf.mv_data = malloc(kbuf.mv_size * 2);
382
+ k0buf.mv_size = kbuf.mv_size;
383
+ k0buf.mv_data = (char *)kbuf.mv_data + kbuf.mv_size;
384
+ prevk.mv_data = k0buf.mv_data;
385
+
386
+ while(!Eof) {
387
+ MDB_val key, data;
388
+ int batch = 0;
389
+ int appflag;
390
+
391
+ if (!dohdr) {
392
+ dohdr = 1;
393
+ } else if (!(mode & NOHDR))
394
+ readhdr();
395
+
396
+ rc = mdb_txn_begin(env, NULL, 0, &txn);
397
+ if (rc) {
398
+ fprintf(stderr, "mdb_txn_begin failed, error %d %s\n", rc, mdb_strerror(rc));
399
+ goto env_close;
400
+ }
401
+
402
+ rc = mdb_open(txn, subname, flags|MDB_CREATE, &dbi);
403
+ if (rc) {
404
+ fprintf(stderr, "mdb_open failed, error %d %s\n", rc, mdb_strerror(rc));
405
+ goto txn_abort;
406
+ }
407
+ prevk.mv_size = 0;
408
+ if (append) {
409
+ mdb_set_compare(txn, dbi, greater);
410
+ if (flags & MDB_DUPSORT)
411
+ mdb_set_dupsort(txn, dbi, greater);
412
+ }
413
+
414
+ rc = mdb_cursor_open(txn, dbi, &mc);
415
+ if (rc) {
416
+ fprintf(stderr, "mdb_cursor_open failed, error %d %s\n", rc, mdb_strerror(rc));
417
+ goto txn_abort;
418
+ }
419
+
420
+ while(1) {
421
+ rc = readline(&key, &kbuf);
422
+ if (rc) /* rc == EOF */
423
+ break;
424
+
425
+ rc = readline(&data, &dbuf);
426
+ if (rc) {
427
+ fprintf(stderr, "%s: line %"Yu": failed to read key value\n", prog, lineno);
428
+ goto txn_abort;
429
+ }
430
+
431
+ if (append) {
432
+ appflag = MDB_APPEND;
433
+ if (flags & MDB_DUPSORT) {
434
+ if (prevk.mv_size == key.mv_size && !memcmp(prevk.mv_data, key.mv_data, key.mv_size))
435
+ appflag = MDB_CURRENT|MDB_APPENDDUP;
436
+ else {
437
+ memcpy(prevk.mv_data, key.mv_data, key.mv_size);
438
+ prevk.mv_size = key.mv_size;
439
+ }
440
+ }
441
+ } else {
442
+ appflag = 0;
443
+ }
444
+ rc = mdb_cursor_put(mc, &key, &data, putflags|appflag);
445
+ if (rc == MDB_KEYEXIST && putflags)
446
+ continue;
447
+ if (rc) {
448
+ fprintf(stderr, "mdb_cursor_put failed, error %d %s\n", rc, mdb_strerror(rc));
449
+ goto txn_abort;
450
+ }
451
+ batch++;
452
+ if (batch == 100) {
453
+ rc = mdb_txn_commit(txn);
454
+ if (rc) {
455
+ fprintf(stderr, "%s: line %"Yu": txn_commit: %s\n",
456
+ prog, lineno, mdb_strerror(rc));
457
+ goto env_close;
458
+ }
459
+ rc = mdb_txn_begin(env, NULL, 0, &txn);
460
+ if (rc) {
461
+ fprintf(stderr, "mdb_txn_begin failed, error %d %s\n", rc, mdb_strerror(rc));
462
+ goto env_close;
463
+ }
464
+ rc = mdb_cursor_open(txn, dbi, &mc);
465
+ if (rc) {
466
+ fprintf(stderr, "mdb_cursor_open failed, error %d %s\n", rc, mdb_strerror(rc));
467
+ goto txn_abort;
468
+ }
469
+ if (appflag & MDB_APPENDDUP) {
470
+ MDB_val k, d;
471
+ mdb_cursor_get(mc, &k, &d, MDB_LAST);
472
+ }
473
+ batch = 0;
474
+ }
475
+ }
476
+ rc = mdb_txn_commit(txn);
477
+ txn = NULL;
478
+ if (rc) {
479
+ fprintf(stderr, "%s: line %"Yu": txn_commit: %s\n",
480
+ prog, lineno, mdb_strerror(rc));
481
+ goto env_close;
482
+ }
483
+ mdb_dbi_close(env, dbi);
484
+ }
485
+
486
+ txn_abort:
487
+ mdb_txn_abort(txn);
488
+ env_close:
489
+ mdb_env_close(env);
490
+
491
+ return rc ? EXIT_FAILURE : EXIT_SUCCESS;
492
+ }
@@ -0,0 +1,70 @@
1
+ .TH MDB_STAT 1 "2017/07/31" "LMDB 0.9.70"
2
+ .\" Copyright 2012-2021 Howard Chu, Symas Corp. All Rights Reserved.
3
+ .\" Copying restrictions apply. See COPYRIGHT/LICENSE.
4
+ .SH NAME
5
+ mdb_stat \- LMDB environment status tool
6
+ .SH SYNOPSIS
7
+ .B mdb_stat
8
+ [\c
9
+ .BR \-V ]
10
+ [\c
11
+ .BR \-e ]
12
+ [\c
13
+ .BR \-f [ f [ f ]]]
14
+ [\c
15
+ .BR \-n ]
16
+ [\c
17
+ .BR \-v ]
18
+ [\c
19
+ .BR \-r [ r ]]
20
+ [\c
21
+ .BR \-a \ |
22
+ .BI \-s \ subdb\fR]
23
+ .BR \ envpath
24
+ .SH DESCRIPTION
25
+ The
26
+ .B mdb_stat
27
+ utility displays the status of an LMDB environment.
28
+ .SH OPTIONS
29
+ .TP
30
+ .BR \-V
31
+ Write the library version number to the standard output, and exit.
32
+ .TP
33
+ .BR \-e
34
+ Display information about the database environment.
35
+ .TP
36
+ .BR \-f
37
+ Display information about the environment freelist.
38
+ If \fB\-ff\fP is given, summarize each freelist entry.
39
+ If \fB\-fff\fP is given, display the full list of page IDs in the freelist.
40
+ .TP
41
+ .BR \-n
42
+ Display the status of an LMDB database which does not use subdirectories.
43
+ .TP
44
+ .BR \-v
45
+ Use the previous environment state instead of the latest state.
46
+ This may be useful if the latest state has been corrupted.
47
+ .TP
48
+ .BR \-r
49
+ Display information about the environment reader table.
50
+ Shows the process ID, thread ID, and transaction ID for each active
51
+ reader slot. The process ID and transaction ID are in decimal, the
52
+ thread ID is in hexadecimal. The transaction ID is displayed as "-"
53
+ if the reader does not currently have a read transaction open.
54
+ If \fB\-rr\fP is given, check for stale entries in the reader
55
+ table and clear them. The reader table will be printed again
56
+ after the check is performed.
57
+ .TP
58
+ .BR \-a
59
+ Display the status of all of the subdatabases in the environment.
60
+ .TP
61
+ .BR \-s \ subdb
62
+ Display the status of a specific subdatabase.
63
+ .SH DIAGNOSTICS
64
+ Exit status is zero if no errors occur.
65
+ Errors result in a non-zero exit status and
66
+ a diagnostic message being written to standard error.
67
+ .SH "SEE ALSO"
68
+ .BR mdb_copy (1)
69
+ .SH AUTHOR
70
+ Howard Chu of Symas Corporation <http://www.symas.com>