diff --git a/src/mdbx_dump.c b/src/mdbx_dump.c index 5cd3a39c..75b7c79e 100644 --- a/src/mdbx_dump.c +++ b/src/mdbx_dump.c @@ -209,6 +209,8 @@ static int dump_sdb(MDBX_txn *txn, MDBX_dbi dbi, char *name) { rc = MDBX_SUCCESS; if (unlikely(rc != MDBX_SUCCESS)) error("mdbx_cursor_get", rc); + + mdbx_cursor_close(cursor); return rc; } @@ -243,7 +245,7 @@ int main(int argc, char *argv[]) { MDBX_dbi dbi; prog = argv[0]; char *envname; - char *subname = nullptr; + char *subname = nullptr, *buf4free = nullptr; unsigned envflags = 0; bool alldbs = false, list = false; @@ -389,7 +391,13 @@ int main(int argc, char *argv[]) { if (memchr(key.iov_base, '\0', key.iov_len)) continue; - subname = mdbx_malloc(key.iov_len + 1); + subname = mdbx_realloc(buf4free, key.iov_len + 1); + if (!subname) { + rc = MDBX_ENOMEM; + break; + } + + buf4free = subname; memcpy(subname, key.iov_base, key.iov_len); subname[key.iov_len] = '\0'; @@ -442,7 +450,6 @@ int main(int argc, char *argv[]) { break; } } - mdbx_free(subname); } mdbx_cursor_close(cursor); cursor = nullptr; @@ -476,6 +483,7 @@ txn_abort: mdbx_txn_abort(txn); env_close: mdbx_env_close(env); + free(buf4free); return rc ? EXIT_FAILURE : EXIT_SUCCESS; } diff --git a/src/mdbx_load.c b/src/mdbx_load.c index 2c59ede6..c54049bb 100644 --- a/src/mdbx_load.c +++ b/src/mdbx_load.c @@ -118,7 +118,6 @@ static MDBX_envinfo envinfo; static int mode = GLOBAL; static MDBX_val kbuf, dbuf; -static MDBX_val k0buf; #define STRLENOF(s) (sizeof(s) - 1) @@ -481,11 +480,9 @@ int main(int argc, char *argv[]) { MDBX_cursor *mc = nullptr; MDBX_dbi dbi; char *envname = nullptr; - int envflags = MDBX_UTTERLY_NOSYNC, putflags = 0; - bool append = false; + int envflags = MDBX_UTTERLY_NOSYNC, putflags = MDBX_UPSERT; bool quiet = false; bool rescue = false; - MDBX_val prevk; prog = argv[0]; if (argc < 2) @@ -508,7 +505,7 @@ int main(int argc, char *argv[]) { mdbx_build.options); return EXIT_SUCCESS; case 'a': - append = true; + putflags |= MDBX_APPEND; break; case 'f': if (freopen(optarg, "r", stdin) == nullptr) { @@ -524,7 +521,7 @@ int main(int argc, char *argv[]) { subname = mdbx_strdup(optarg); break; case 'N': - putflags = MDBX_NOOVERWRITE | MDBX_NODUPDATA; + putflags |= MDBX_NOOVERWRITE | MDBX_NODUPDATA; break; case 'T': mode |= NOHDR | PRINT; @@ -565,6 +562,11 @@ int main(int argc, char *argv[]) { dbuf.iov_len = 4096; dbuf.iov_base = mdbx_malloc(dbuf.iov_len); + if (!dbuf.iov_base) { + rc = MDBX_ENOMEM; + error("value-buffer", rc); + goto env_close; + } /* read first header for mapsize= */ if (!(mode & NOHDR)) { @@ -625,17 +627,19 @@ int main(int argc, char *argv[]) { goto env_close; } - kbuf.iov_len = mdbx_env_get_maxvalsize_ex(env, MDBX_DUPSORT); - if (kbuf.iov_len >= INTPTR_MAX / 4) { + kbuf.iov_len = mdbx_env_get_maxvalsize_ex(env, 0) + 1; + if (kbuf.iov_len >= INTPTR_MAX / 2) { fprintf(stderr, "mdbx_env_get_maxkeysize() failed, returns %zu\n", kbuf.iov_len); goto env_close; } - kbuf.iov_len = (kbuf.iov_len + 1) * 2; - kbuf.iov_base = malloc(kbuf.iov_len * 2); - k0buf.iov_len = kbuf.iov_len; - k0buf.iov_base = (char *)kbuf.iov_base + kbuf.iov_len; - prevk.iov_base = k0buf.iov_base; + + kbuf.iov_base = malloc(kbuf.iov_len); + if (!kbuf.iov_base) { + rc = MDBX_ENOMEM; + error("key-buffer", rc); + goto env_close; + } while (rc == MDBX_SUCCESS) { if (user_break) { @@ -661,9 +665,10 @@ int main(int argc, char *argv[]) { } const char *const dbi_name = subname ? subname : "@MAIN"; - rc = mdbx_dbi_open_ex(txn, subname, dbi_flags | MDBX_CREATE, &dbi, - append ? equal_or_greater : nullptr, - append ? equal_or_greater : nullptr); + rc = + mdbx_dbi_open_ex(txn, subname, dbi_flags | MDBX_CREATE, &dbi, + (putflags & MDBX_APPEND) ? equal_or_greater : nullptr, + (putflags & MDBX_APPEND) ? equal_or_greater : nullptr); if (unlikely(rc != MDBX_SUCCESS)) { error("mdbx_dbi_open_ex", rc); goto txn_abort; @@ -691,19 +696,17 @@ int main(int argc, char *argv[]) { } } + if (putflags & MDBX_APPEND) + putflags = (dbi_flags & MDBX_DUPSORT) ? putflags | MDBX_APPENDDUP + : putflags & ~MDBX_APPENDDUP; + rc = mdbx_cursor_open(txn, dbi, &mc); if (unlikely(rc != MDBX_SUCCESS)) { error("mdbx_cursor_open", rc); goto txn_abort; } - /* if (append) { - mc->mc_flags |= C_SKIPORD; - if (mc->mc_xcursor) - mc->mc_xcursor->mx_cursor.mc_flags |= C_SKIPORD; - } */ int batch = 0; - prevk.iov_len = 0; while (rc == MDBX_SUCCESS) { MDBX_val key, data; rc = readline(&key, &kbuf); @@ -718,18 +721,7 @@ int main(int argc, char *argv[]) { goto txn_abort; } - int appflag = 0; - if (append) { - appflag = MDBX_APPEND; - if (dbi_flags & MDBX_DUPSORT) { - if (prevk.iov_len == key.iov_len && - memcmp(prevk.iov_base, key.iov_base, key.iov_len) == 0) - appflag = MDBX_APPEND | MDBX_APPENDDUP; - else - memcpy(prevk.iov_base, key.iov_base, prevk.iov_len = key.iov_len); - } - } - rc = mdbx_cursor_put(mc, &key, &data, putflags | appflag); + rc = mdbx_cursor_put(mc, &key, &data, putflags); if (rc == MDBX_KEYEXIST && putflags) continue; if (rc == MDBX_BAD_VALSIZE && rescue) { @@ -770,11 +762,6 @@ int main(int argc, char *argv[]) { error("mdbx_cursor_open", rc); goto txn_abort; } - /* if (append) { - mc->mc_flags |= C_SKIPORD; - if (mc->mc_xcursor) - mc->mc_xcursor->mx_cursor.mc_flags |= C_SKIPORD; - } */ } } @@ -815,6 +802,8 @@ txn_abort: mdbx_txn_abort(txn); env_close: mdbx_env_close(env); + free(kbuf.iov_base); + free(dbuf.iov_base); return rc ? EXIT_FAILURE : EXIT_SUCCESS; }