From d133b08f68f3ff8724166bef28b8c85aacdd6e5a Mon Sep 17 00:00:00 2001 From: Reid Horuff Date: Wed, 9 Nov 2016 12:12:40 -0800 Subject: [PATCH] Use correct sequence number when creating memtable Summary: copied from: https://github.com/mdlugajczyk/rocksdb/commit/5ebfd2623a01e69a4cbeae3ed2b788f2a84056ad Opening existing RocksDB attempts recovery from log files, which uses wrong sequence number to create the memtable. This is a regression introduced in change a400336. This change includes a test demonstrating the problem, without the fix the test fails with "Operation failed. Try again.: Transaction could not check for conflicts for operation at SequenceNumber 1 as the MemTable only contains changes newer than SequenceNumber 2. Increasing the value of the max_write_buffer_number_to_maintain option could reduce the frequency of this error" This change is a joint effort by Peter 'Stig' Edwards thatsafunnyname and me. Closes https://github.com/facebook/rocksdb/pull/1458 Differential Revision: D4143791 Pulled By: reidHoruff fbshipit-source-id: 5a25033 --- db/db_impl.cc | 2 +- .../optimistic_transaction_test.cc | 43 +++++++++++++++++-- 2 files changed, 41 insertions(+), 4 deletions(-) diff --git a/db/db_impl.cc b/db/db_impl.cc index a2798b8bc..f202d1fa6 100644 --- a/db/db_impl.cc +++ b/db/db_impl.cc @@ -1721,7 +1721,7 @@ Status DBImpl::RecoverLogFiles(const std::vector& log_numbers, flushed = true; cfd->CreateNewMemtable(*cfd->GetLatestMutableCFOptions(), - *next_sequence); + versions_->LastSequence()); } } diff --git a/utilities/transactions/optimistic_transaction_test.cc b/utilities/transactions/optimistic_transaction_test.cc index fd90f2423..0b540471d 100644 --- a/utilities/transactions/optimistic_transaction_test.cc +++ b/utilities/transactions/optimistic_transaction_test.cc @@ -34,14 +34,24 @@ class OptimisticTransactionTest : public testing::Test { dbname = test::TmpDir() + "/optimistic_transaction_testdb"; DestroyDB(dbname, options); - Status s = OptimisticTransactionDB::Open(options, dbname, &txn_db); - assert(s.ok()); - db = txn_db->GetBaseDB(); + Open(); } ~OptimisticTransactionTest() { delete txn_db; DestroyDB(dbname, options); } + + void Reopen() { + delete txn_db; + Open(); + } + +private: + void Open() { + Status s = OptimisticTransactionDB::Open(options, dbname, &txn_db); + assert(s.ok()); + db = txn_db->GetBaseDB(); + } }; TEST_F(OptimisticTransactionTest, SuccessTest) { @@ -1338,6 +1348,33 @@ TEST_F(OptimisticTransactionTest, OptimisticTransactionStressTest) { ASSERT_OK(s); } +TEST_F(OptimisticTransactionTest, SequenceNumberAfterRecoverTest) { + WriteOptions write_options; + OptimisticTransactionOptions transaction_options; + + Transaction* transaction(txn_db->BeginTransaction(write_options, transaction_options)); + Status s = transaction->Put("foo", "val"); + ASSERT_OK(s); + s = transaction->Put("foo2", "val"); + ASSERT_OK(s); + s = transaction->Put("foo3", "val"); + ASSERT_OK(s); + s = transaction->Commit(); + ASSERT_OK(s); + delete transaction; + + Reopen(); + transaction = txn_db->BeginTransaction(write_options, transaction_options); + s = transaction->Put("bar", "val"); + ASSERT_OK(s); + s = transaction->Put("bar2", "val"); + ASSERT_OK(s); + s = transaction->Commit(); + ASSERT_OK(s); + + delete transaction; +} + } // namespace rocksdb int main(int argc, char** argv) {