Full_Name: Hallvard B Furuseth Version: mdb.master 27aaecc744955d08d2bfe7a3ca786d742267c5bd OS: Linux x86_64 URL: Submission from: (NULL) (193.69.163.163) Submitted by: hallvard If the malloc at mdb_page_malloc() line 1348 fails, me_pgfirst has already been incremented and those pages can be lost. I'll fix that one. Not this, however: If a child transaction aborts, it loses pages it used up: It does not give them back to me_pghead, nor to the parent's mt_free_pgs. It does not rewind me_pgfirst/me_last to their state at txn_begin. This program illustrates. The DB grows to 107 pages. mdb_stat can see 10 of them, same as if everything was done in the main txn. MainDB will have max 1 entry while running. #include <lmdb.h> #include <stdio.h> #include <stdlib.h> int main(void) { int rc, i; MDB_val key = { sizeof(i), &i }, data = { 0, "" }; MDB_env *env; MDB_txn *txn, *ctxn; MDB_dbi dbi; # define dbname "test.mdb" # define E(e) { rc = (e); if (rc) { fprintf(stderr, "%d: %s: %s\n", \ __LINE__, #e, mdb_strerror(rc)); return rc; } } E(mdb_env_create(&env)); E(mdb_env_open(env, dbname, MDB_NOSYNC|MDB_NOSUBDIR, 0666)); for (i = 0; i < 100; ) { E(mdb_txn_begin(env, NULL, 0, &txn)); if (!i) { E(mdb_dbi_open(txn, NULL, MDB_CREATE, &dbi)); } else { E(mdb_txn_begin(env, txn, 0, &ctxn)); E(mdb_put(ctxn, dbi, &key, &data, 0)); mdb_txn_abort(ctxn); E(mdb_del(txn, dbi, &key, NULL)); } i++; E(mdb_put(txn, dbi, &key, &data, 0)); E(mdb_txn_commit(txn)); if (i % 20 == 0) system("du " dbname); } mdb_env_close(env); return 0; }
changed notes changed state Open to Test moved from Incoming to Software Bugs
changed notes
changed notes changed state Test to Release
changed notes changed state Release to Closed
fixed in mdb.master. fixed in master fixed in RE24