From 5863d5cc616b2e0ff4738358e27ed1d095f3eead Mon Sep 17 00:00:00 2001 From: Howard Chu Date: Thu, 6 Dec 2012 08:25:43 -0800 Subject: [PATCH] Freelist fixes Keep list sorted if it grows during a write. Don't free pghead until we're sure our writes are all finished. --- libraries/liblmdb/mdb.c | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/libraries/liblmdb/mdb.c b/libraries/liblmdb/mdb.c index d1f957bcd8..a74471b813 100644 --- a/libraries/liblmdb/mdb.c +++ b/libraries/liblmdb/mdb.c @@ -2156,15 +2156,15 @@ free2: key.mv_data = NULL; mdb_page_search(&mc, &key, MDB_PS_MODIFY); - mdb_midl_sort(txn->mt_free_pgs); #if MDB_DEBUG > 1 { unsigned int i; MDB_IDL idl = txn->mt_free_pgs; + mdb_midl_sort(txn->mt_free_pgs); DPRINTF("IDL write txn %zu root %zu num %zu", txn->mt_txnid, txn->mt_dbs[FREE_DBI].md_root, idl[0]); - for (i=0; imt_free_pgs[0]; data.mv_size = MDB_IDL_SIZEOF(txn->mt_free_pgs); + mdb_midl_sort(txn->mt_free_pgs); rc = mdb_cursor_put(&mc, &key, &data, 0); if (rc) { mdb_txn_abort(txn); @@ -2213,8 +2214,6 @@ again: id = mop->mo_txnid; mdb_cursor_put(&mc, &key, &data, 0); } - env->me_pghead = NULL; - free(mop); } else { /* was completely used up */ mdb_cursor_del(&mc, 0); @@ -2225,16 +2224,21 @@ again: env->me_pglast = 0; } + /* Check for growth of freelist again */ + if (freecnt != txn->mt_free_pgs[0]) + goto free2; + + if (env->me_pghead) { + free(env->me_pghead); + env->me_pghead = NULL; + } + while (env->me_pgfree) { MDB_oldpages *mop = env->me_pgfree; env->me_pgfree = mop->mo_next; free(mop); } - /* Check for growth of freelist again */ - if (freecnt != txn->mt_free_pgs[0]) - goto free2; - if (!MDB_IDL_IS_ZERO(txn->mt_free_pgs)) { if (mdb_midl_shrink(&txn->mt_free_pgs)) env->me_free_pgs = txn->mt_free_pgs; -- 2.39.5