// Pick tables to flush
list.PickMemtablesToFlush(
std::numeric_limits<uint64_t>::max() /* memtable_id */, &to_flush);
- // Should pick 4 of 5 since 1 table has been picked in to_flush2
- ASSERT_EQ(4, to_flush.size());
+ // Picks three oldest memtables. The fourth oldest is picked in `to_flush2` so
+ // must be excluded. The newest (fifth oldest) is non-consecutive with the
+ // three oldest due to omitting the fourth oldest so must not be picked.
+ ASSERT_EQ(3, to_flush.size());
ASSERT_EQ(5, list.NumNotFlushed());
ASSERT_FALSE(list.IsFlushPending());
- ASSERT_FALSE(list.imm_flush_needed.load(std::memory_order_acquire));
+ ASSERT_TRUE(list.imm_flush_needed.load(std::memory_order_acquire));
// Pick tables to flush again
autovector<MemTable*> to_flush3;
list.PickMemtablesToFlush(
std::numeric_limits<uint64_t>::max() /* memtable_id */, &to_flush3);
- ASSERT_EQ(0, to_flush3.size()); // nothing not in progress of being flushed
+ // Picks newest (fifth oldest)
+ ASSERT_EQ(1, to_flush3.size());
+ ASSERT_EQ(5, list.NumNotFlushed());
+ ASSERT_FALSE(list.IsFlushPending());
+ ASSERT_FALSE(list.imm_flush_needed.load(std::memory_order_acquire));
+
+ // Nothing left to flush
+ autovector<MemTable*> to_flush4;
+ list.PickMemtablesToFlush(
+ std::numeric_limits<uint64_t>::max() /* memtable_id */, &to_flush4);
+ ASSERT_EQ(0, to_flush4.size());
ASSERT_EQ(5, list.NumNotFlushed());
ASSERT_FALSE(list.IsFlushPending());
ASSERT_FALSE(list.imm_flush_needed.load(std::memory_order_acquire));
- // Flush the 4 memtables that were picked in to_flush
+ // Flush the 3 memtables that were picked in to_flush
s = Mock_InstallMemtableFlushResults(&list, mutable_cf_options, to_flush,
&to_delete);
ASSERT_OK(s);
- // Note: now to_flush contains tables[0,1,2,4]. to_flush2 contains
- // tables[3].
+ // Note: now to_flush contains tables[0,1,2]. to_flush2 contains
+ // tables[3]. to_flush3 contains tables[4].
// Current implementation will only commit memtables in the order they were
// created. So TryInstallMemtableFlushResults will install the first 3 tables
// in to_flush and stop when it encounters a table not yet flushed.
ASSERT_FALSE(list.IsFlushPending());
ASSERT_FALSE(list.imm_flush_needed.load(std::memory_order_acquire));
- // Flush the 1 memtable that was picked in to_flush2
+ // Flush the 1 memtable (tables[4]) that was picked in to_flush3
+ s = MemTableListTest::Mock_InstallMemtableFlushResults(
+ &list, mutable_cf_options, to_flush3, &to_delete);
+ ASSERT_OK(s);
+
+ // This will install 0 tables since tables[4] flushed while tables[3] has not
+ // yet flushed.
+ ASSERT_EQ(2, list.NumNotFlushed());
+ ASSERT_EQ(0, to_delete.size());
+
+ // Flush the 1 memtable (tables[3]) that was picked in to_flush2
s = MemTableListTest::Mock_InstallMemtableFlushResults(
&list, mutable_cf_options, to_flush2, &to_delete);
ASSERT_OK(s);
memtable_id = 4;
// Pick tables to flush. The tables to pick must have ID smaller than or
// equal to 4. Therefore, no table will be selected in this case.
- autovector<MemTable*> to_flush4;
+ autovector<MemTable*> to_flush5;
list.FlushRequested();
ASSERT_TRUE(list.HasFlushRequested());
- list.PickMemtablesToFlush(memtable_id, &to_flush4);
- ASSERT_TRUE(to_flush4.empty());
+ list.PickMemtablesToFlush(memtable_id, &to_flush5);
+ ASSERT_TRUE(to_flush5.empty());
ASSERT_EQ(1, list.NumNotFlushed());
ASSERT_TRUE(list.imm_flush_needed.load(std::memory_order_acquire));
ASSERT_FALSE(list.IsFlushPending());
// equal to 5. Therefore, only tables[5] will be selected.
memtable_id = 5;
list.FlushRequested();
- list.PickMemtablesToFlush(memtable_id, &to_flush4);
- ASSERT_EQ(1, static_cast<int>(to_flush4.size()));
+ list.PickMemtablesToFlush(memtable_id, &to_flush5);
+ ASSERT_EQ(1, static_cast<int>(to_flush5.size()));
ASSERT_EQ(1, list.NumNotFlushed());
ASSERT_FALSE(list.imm_flush_needed.load(std::memory_order_acquire));
ASSERT_FALSE(list.IsFlushPending());