diff --git a/test/nested.cc b/test/nested.cc index 34527f65..cd197d41 100644 --- a/test/nested.cc +++ b/test/nested.cc @@ -128,6 +128,8 @@ void testcase_nested::push_txn() { std::move(speculum_snapshot)); log_verbose("begin level#%zu txn #%" PRIu64 ", flags 0x%x, serial %" PRIu64, stack.size(), mdbx_txn_id(nested_txn), flags, serial); + if (!dbi && stack.size() == 1) + dbi = db_table_open(true); } bool testcase_nested::pop_txn(bool abort) { @@ -139,6 +141,9 @@ bool testcase_nested::pop_txn(bool abort) { log_verbose( "abort level#%zu txn #%" PRIu64 ", undo serial %" PRIu64 " <- %" PRIu64, stack.size(), mdbx_txn_id(txn), serial, std::get<1>(stack.top())); + if (dbi > 0 && stack.size() == 1 && + is_handle_created_in_current_txn(dbi, txn)) + dbi = 0; int err = mdbx_txn_abort(txn); if (unlikely(err != MDBX_SUCCESS)) failure_perror("mdbx_txn_abort()", err); diff --git a/test/test.cc b/test/test.cc index f1494f8e..d13b7973 100644 --- a/test/test.cc +++ b/test/test.cc @@ -477,6 +477,15 @@ void testcase::update_canary(uint64_t increment) { log_trace("<< update_canary: sequence = %" PRIu64, canary_now.y); } +bool testcase::is_handle_created_in_current_txn(const MDBX_dbi handle, + MDBX_txn *txn) { + unsigned flags, state; + int err = mdbx_dbi_flags_ex(txn, handle, &flags, &state); + if (unlikely(err != MDBX_SUCCESS)) + failure_perror("mdbx_dbi_flags_ex()", err); + return (state & MDBX_DBI_CREAT) != 0; +} + int testcase::db_open__begin__table_create_open_clean(MDBX_dbi &handle) { db_open(); @@ -484,6 +493,9 @@ int testcase::db_open__begin__table_create_open_clean(MDBX_dbi &handle) { for (;;) { txn_begin(false); handle = db_table_open(true); + + if (is_handle_created_in_current_txn(handle, txn_guard.get())) + return MDBX_SUCCESS; db_table_clear(handle); err = breakable_commit(); if (likely(err == MDBX_SUCCESS)) { diff --git a/test/test.h b/test/test.h index b38ff0b8..4e6783c2 100644 --- a/test/test.h +++ b/test/test.h @@ -268,6 +268,7 @@ protected: void db_table_clear(MDBX_dbi handle, MDBX_txn *txn = nullptr); void db_table_close(MDBX_dbi handle); int db_open__begin__table_create_open_clean(MDBX_dbi &handle); + bool is_handle_created_in_current_txn(const MDBX_dbi handle, MDBX_txn *txn); bool wait4start(); void report(size_t nops_done);