Skip to content

Commit

Permalink
memory leak resolved. All ut-s pass. stress test passes
Browse files Browse the repository at this point in the history
  • Loading branch information
udi-speedb committed Mar 5, 2024
1 parent a9eb2dd commit a6ab0e9
Show file tree
Hide file tree
Showing 3 changed files with 128 additions and 28 deletions.
7 changes: 7 additions & 0 deletions db/db_impl/spdb_db_gs_del_list.cc
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,13 @@ void GlobalDelList::InsertBefore(Iterator& pos, const DelElement& del_elem) {
void GlobalDelList::InsertBeforeAndSetIterOnInserted(
Iterator& pos, const DelElement& del_elem) {
pos.del_list_iter_ = del_list_.insert(pos.del_list_iter_, del_elem);
auto valid = true;
if (!Valid()) {
// printf("INVALID: del_elem=|%s|, upper_bound=|%s|\n",
// del_elem.ToString().c_str(), upper_bound_.ToString().c_str());
valid = Valid();
}
assert(valid);
assert(Valid());
}

Expand Down
67 changes: 53 additions & 14 deletions db/db_impl/spdb_db_gs_impl.cc
Original file line number Diff line number Diff line change
Expand Up @@ -81,17 +81,34 @@ class LevelFilesItersMngr {
}

invalid_file_idx_ = last_file_idx_within_bounds_ + 1;
empty_ = false;
} else {
last_file_idx_within_bounds_ = NumFiles();
invalid_file_idx_ = NumFiles();
curr_internal_iter_idx_ = NumFiles();
curr_range_ts_iter_idx_ = NumFiles();
empty_ = true;
}

assert(first_file_idx_within_bounds_ <= last_file_idx_within_bounds_);
}

~LevelFilesItersMngr() = default;
~LevelFilesItersMngr() {
for (auto i = 0U; i < files_iters_.size(); ++i) {
if (files_iters_[i] != nullptr) {
auto& file_iters = files_iters_[i];
if (file_iters->table_iter != nullptr) {
file_iters->table_iter->~InternalIterator();
file_iters->table_iter = nullptr;
}

delete file_iters->range_ts_iter;
file_iters->range_ts_iter = nullptr;
}
}
}

bool IsEmpty() const { return empty_; }

bool HasNextInternalIter() const {
return (curr_internal_iter_idx_ < last_file_idx_within_bounds_);
Expand All @@ -116,6 +133,10 @@ class LevelFilesItersMngr {
}

InternalIterator* AdvanceInternalIterToFileContainingKey(const Slice& key) {
if (IsEmpty()) {
return nullptr;
}

auto new_iter_idx =
FindFileForwardContainingKey(key, curr_internal_iter_idx_);
if (new_iter_idx != curr_internal_iter_idx_) {
Expand All @@ -131,6 +152,10 @@ class LevelFilesItersMngr {

TruncatedRangeDelIterator* AdvanceRangeTsIterToFileContainingKey(
const Slice& key) {
if (IsEmpty()) {
return nullptr;
}

auto new_iter_idx =
FindFileForwardContainingKey(key, curr_range_ts_iter_idx_);
if (new_iter_idx != curr_range_ts_iter_idx_) {
Expand Down Expand Up @@ -277,6 +302,7 @@ class LevelFilesItersMngr {
Slice lower_bound_;
Slice upper_bound_;

bool empty_ = true;
int first_file_idx_within_bounds_ = -1;
int last_file_idx_within_bounds_ = -1;
int invalid_file_idx_ = -1;
Expand Down Expand Up @@ -328,13 +354,13 @@ class InternalIteratorWrapper: public InternalIteratorWrapperBase {
: wrapped_iter_(wrapped_iter_ptr),
comparator_(comparator),
upper_bound_(upper_bound),
is_iter_owner_(is_iter_owner) {
iter_owner_(is_iter_owner) {
assert(wrapped_iter_ != nullptr);
assert(comparator != nullptr);
}

~InternalIteratorWrapper() {
if (is_iter_owner_) {
if (iter_owner_) {
wrapped_iter_->~InternalIterator();
}
wrapped_iter_ = nullptr;
Expand Down Expand Up @@ -411,7 +437,7 @@ class InternalIteratorWrapper: public InternalIteratorWrapperBase {
InternalIterator* wrapped_iter_ = nullptr;
const Comparator* comparator_ = nullptr;
Slice upper_bound_;
bool is_iter_owner_ = false;
bool iter_owner_ = false;
bool valid_ = false;
};

Expand Down Expand Up @@ -444,6 +470,10 @@ class InternalLevelIteratorWrapper : public InternalIteratorWrapperBase {
}

void SeekForward(const Slice& target) override {
if (level_iters_mngr_.IsEmpty()) {
return;
}

auto new_internal_iter =
level_iters_mngr_.AdvanceInternalIterToFileContainingKey(target);

Expand Down Expand Up @@ -501,11 +531,12 @@ class InternalLevelIteratorWrapper : public InternalIteratorWrapperBase {

private:
void InitFileIterWrapper(InternalIterator* wrapped_iter) {
assert(wrapped_iter != nullptr);
file_iter_wrapper_.reset(new InternalIteratorWrapper(
wrapped_iter, comparator_, upper_bound_, false /* is_iter_owner */));
}

void CleanupFileIterWrapper() { file_iter_wrapper_.release(); }
void CleanupFileIterWrapper() { file_iter_wrapper_.reset(); }

void UpdateValidity() {
valid_ = (file_iter_wrapper_ != nullptr) && (file_iter_wrapper_->Valid());
Expand All @@ -516,8 +547,12 @@ class InternalLevelIteratorWrapper : public InternalIteratorWrapperBase {
((file_iter_wrapper_ == nullptr) ||
(file_iter_wrapper_->Valid() == false))) {
auto next_internal_iter = level_iters_mngr_.NextInternalIter();
InitFileIterWrapper(next_internal_iter);
file_iter_wrapper_->SeekToFirst();
if (next_internal_iter != nullptr) {
InitFileIterWrapper(next_internal_iter);
file_iter_wrapper_->SeekToFirst();
} else {
CleanupFileIterWrapper();
}
}
}

Expand All @@ -531,7 +566,7 @@ class InternalLevelIteratorWrapper : public InternalIteratorWrapperBase {

class TruncatedRangeDelIteratorWrapperBase {
public:
virtual ~TruncatedRangeDelIteratorWrapperBase() = default;
virtual ~TruncatedRangeDelIteratorWrapperBase() {}

virtual bool Valid() const = 0;

Expand Down Expand Up @@ -559,10 +594,10 @@ class TruncatedRangeDelIteratorWrapper
: wrapped_iter_(wrapped_iter_ptr),
comparator_(comparator),
upper_bound_(upper_bound),
is_iter_owner_(is_iter_owner) {}
iter_owner_(is_iter_owner) {}

~TruncatedRangeDelIteratorWrapper() {
if (is_iter_owner_) {
if (iter_owner_) {
delete wrapped_iter_;
}
wrapped_iter_ = nullptr;
Expand Down Expand Up @@ -676,7 +711,7 @@ class TruncatedRangeDelIteratorWrapper
TruncatedRangeDelIterator* wrapped_iter_ = nullptr;
const Comparator* comparator_ = nullptr;
Slice upper_bound_;
bool is_iter_owner_ = false;
bool iter_owner_ = false;
bool valid_ = false;
};

Expand All @@ -692,6 +727,8 @@ class TruncatedRangeDelLevelIteratorWrapper
assert(comparator != nullptr);
}

~TruncatedRangeDelLevelIteratorWrapper() {}

bool Valid() const override { return valid_; }

bool HasUpperBound() const override {
Expand Down Expand Up @@ -775,11 +812,12 @@ class TruncatedRangeDelLevelIteratorWrapper

private:
void InitFileIterWrapper(TruncatedRangeDelIterator* wrapped_iter) {
file_iter_wrapper_.reset(new TruncatedRangeDelIteratorWrapper(
wrapped_iter, comparator_, upper_bound_, false /* is_iter_owner */));
auto new_wrapper = new TruncatedRangeDelIteratorWrapper(
wrapped_iter, comparator_, upper_bound_, false /* is_iter_owner */);
file_iter_wrapper_.reset(new_wrapper);
}

void CleanupFileIterWrapper() { file_iter_wrapper_.release(); }
void CleanupFileIterWrapper() { file_iter_wrapper_.reset(); }

void UpdateValidity() {
valid_ = (file_iter_wrapper_ != nullptr) && (file_iter_wrapper_->Valid());
Expand Down Expand Up @@ -832,6 +870,7 @@ struct LevelContext {

~LevelContext() {
delete range_del_iter;
range_del_iter = nullptr;
}
};

Expand Down
82 changes: 68 additions & 14 deletions db/db_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -91,8 +91,9 @@
#include "util/string_util.h"
#include "utilities/merge_operators.h"

#define RUN_ALL_GS_TESTS 1
#define RUN_GS_STRESS 0
#define RUN_DEL_LIST_TESTS 0
#define RUN_GS_TESTS 0
#define RUN_GS_STRESS 1

extern bool gs_debug_prints;
extern bool gs_validate_iters_progress;
Expand Down Expand Up @@ -7634,7 +7635,7 @@ TEST_F(DBTest, StaticPinningLastLevelWithData) {
using DelElem = spdb_gs::DelElement;

// XXXXXXXXXXXXXXXXXXXXXXXXXXXXX
#if RUN_ALL_GS_TESTS
#if RUN_DEL_LIST_TESTS

// TODO: Write unit-tests for the gs-utils funtions
class GsUtilsTest : public ::testing::Test {};
Expand Down Expand Up @@ -7964,8 +7965,8 @@ class DBGsTest : public DBTest {
}
};

// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
#if RUN_ALL_GS_TESTS
// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
#if RUN_GS_TESTS

TEST_F(DBGsTest, GS_EmptyDB) {
ReopenNewDb();
Expand Down Expand Up @@ -8360,16 +8361,16 @@ TEST_F(DBGsTest, SingleRangeTsInL1) {
ReopenNewDb();
auto dflt_cfh = dbfull()->DefaultColumnFamily();

ASSERT_OK(dbfull()->DeleteRange(WriteOptions(), dflt_cfh, "a", "z"));
ASSERT_OK(dbfull()->DeleteRange(WriteOptions(), dflt_cfh, "b", "z"));
ASSERT_OK(db_->Flush(FlushOptions()));
MoveFilesToLevel(1);
ASSERT_EQ(0, NumTableFilesAtLevel(0));
ASSERT_EQ(1, NumTableFilesAtLevel(1));

CALL_WRAPPER(GetSmallestAndValidate(""));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("a", ""));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("z", ""));
}
// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
#endif

TEST_F(DBGsTest, TwoFilesInL1OneValuePerFile) {
constexpr int kOneKb = 1 << 10;
Expand All @@ -8383,11 +8384,11 @@ TEST_F(DBGsTest, TwoFilesInL1OneValuePerFile) {
Random rnd(301);
auto value = rnd.RandomString(kValueSize);

ASSERT_OK(Put("a", value));
ASSERT_OK(Put("c", value));
ASSERT_OK(Put("b", value));
ASSERT_OK(Put("d", value));
ASSERT_OK(db_->Flush(FlushOptions()));

ASSERT_OK(Put("e", value));
ASSERT_OK(Put("f", value));
ASSERT_OK(db_->Flush(FlushOptions()));

MoveFilesToLevel(1);
Expand All @@ -8397,10 +8398,63 @@ TEST_F(DBGsTest, TwoFilesInL1OneValuePerFile) {
ASSERT_EQ(0, NumTableFilesAtLevel(0));
ASSERT_EQ(2, NumTableFilesAtLevel(1));

CALL_WRAPPER(GetSmallestAndValidate("a"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("b", "c"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("d", "e"));
CALL_WRAPPER(GetSmallestAndValidate("b"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("a", "b"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("b", "b"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("c", "d"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("d", "d"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("e", "f"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("f", "f"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("g", ""));
}

TEST_F(DBGsTest, L1RangeTsCoveringSomeValues) {
constexpr int kOneKb = 1 << 10;
constexpr int kValueSize = (3 * kOneKb) / 2;
constexpr int kFileSize = 2 * kOneKb;

Options options;
options.target_file_size_base = kFileSize;
ReopenNewDb(&options);

auto dflt_cfh = dbfull()->DefaultColumnFamily();

Random rnd(301);
auto value = rnd.RandomString(kValueSize);

ASSERT_OK(Put("b", value));
ASSERT_OK(Put("d", value));
ASSERT_OK(db_->Flush(FlushOptions()));

ASSERT_OK(Put("f", value));
ASSERT_OK(Put("h", value));
ASSERT_OK(db_->Flush(FlushOptions()));

const Snapshot* snapshot = db_->GetSnapshot();

ASSERT_OK(dbfull()->DeleteRange(WriteOptions(), dflt_cfh, "d", "f"));
ASSERT_OK(db_->Flush(FlushOptions()));

MoveFilesToLevel(1);

std::vector<std::vector<FileMetaData>> files;
dbfull()->TEST_GetFilesMetaData(db_->DefaultColumnFamily(), &files);

CALL_WRAPPER(GetSmallestAndValidate("b"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("a", "b"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("b", "b"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("c", "f"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("d", "f"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("e", "f"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("f", "f"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("g", "h"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("g", "h"));
CALL_WRAPPER(GetSmallestAtOrAfterAndValidate("i", ""));

db_->ReleaseSnapshot(snapshot);
}
// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
#endif

// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
#if RUN_GS_STRESS
Expand Down

0 comments on commit a6ab0e9

Please sign in to comment.