| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428 |
- // Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
- // This source code is licensed under both the GPLv2 (found in the
- // COPYING file in the root directory) and Apache 2.0 License
- // (found in the LICENSE.Apache file in the root directory).
- //
- // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
- // Use of this source code is governed by a BSD-style license that can be
- // found in the LICENSE file. See the AUTHORS file for names of contributors.
- #include "db/version_edit.h"
- #include "db/blob/blob_index.h"
- #include "db/version_set.h"
- #include "logging/event_logger.h"
- #include "rocksdb/slice.h"
- #include "table/unique_id_impl.h"
- #include "test_util/sync_point.h"
- #include "util/coding.h"
- #include "util/string_util.h"
- namespace ROCKSDB_NAMESPACE {
- namespace {} // anonymous namespace
- uint64_t PackFileNumberAndPathId(uint64_t number, uint64_t path_id) {
- assert(number <= kFileNumberMask);
- return number | (path_id * (kFileNumberMask + 1));
- }
- Status FileMetaData::UpdateBoundaries(const Slice& key, const Slice& value,
- SequenceNumber seqno,
- ValueType value_type) {
- if (value_type == kTypeBlobIndex) {
- BlobIndex blob_index;
- const Status s = blob_index.DecodeFrom(value);
- if (!s.ok()) {
- return s;
- }
- if (!blob_index.IsInlined() && !blob_index.HasTTL()) {
- if (blob_index.file_number() == kInvalidBlobFileNumber) {
- return Status::Corruption("Invalid blob file number");
- }
- if (oldest_blob_file_number == kInvalidBlobFileNumber ||
- oldest_blob_file_number > blob_index.file_number()) {
- oldest_blob_file_number = blob_index.file_number();
- }
- }
- }
- if (smallest.size() == 0) {
- smallest.DecodeFrom(key);
- }
- largest.DecodeFrom(key);
- fd.smallest_seqno = std::min(fd.smallest_seqno, seqno);
- fd.largest_seqno = std::max(fd.largest_seqno, seqno);
- return Status::OK();
- }
- void VersionEdit::Clear() { *this = VersionEdit(); }
- bool VersionEdit::EncodeTo(std::string* dst,
- std::optional<size_t> ts_sz) const {
- assert(!IsNoManifestWriteDummy());
- if (has_db_id_) {
- PutVarint32(dst, kDbId);
- PutLengthPrefixedSlice(dst, db_id_);
- }
- if (has_comparator_) {
- assert(has_persist_user_defined_timestamps_);
- PutVarint32(dst, kComparator);
- PutLengthPrefixedSlice(dst, comparator_);
- }
- if (has_log_number_) {
- PutVarint32Varint64(dst, kLogNumber, log_number_);
- }
- if (has_prev_log_number_) {
- PutVarint32Varint64(dst, kPrevLogNumber, prev_log_number_);
- }
- if (has_next_file_number_) {
- PutVarint32Varint64(dst, kNextFileNumber, next_file_number_);
- }
- if (has_max_column_family_) {
- PutVarint32Varint32(dst, kMaxColumnFamily, max_column_family_);
- }
- if (has_min_log_number_to_keep_) {
- PutVarint32Varint64(dst, kMinLogNumberToKeep, min_log_number_to_keep_);
- }
- if (has_last_sequence_) {
- PutVarint32Varint64(dst, kLastSequence, last_sequence_);
- }
- for (size_t i = 0; i < compact_cursors_.size(); i++) {
- if (compact_cursors_[i].second.Valid()) {
- PutVarint32(dst, kCompactCursor);
- PutVarint32(dst, compact_cursors_[i].first); // level
- PutLengthPrefixedSlice(dst, compact_cursors_[i].second.Encode());
- }
- }
- for (const auto& deleted : deleted_files_) {
- PutVarint32Varint32Varint64(dst, kDeletedFile, deleted.first /* level */,
- deleted.second /* file number */);
- }
- bool min_log_num_written = false;
- assert(new_files_.empty() || ts_sz.has_value());
- for (size_t i = 0; i < new_files_.size(); i++) {
- const FileMetaData& f = new_files_[i].second;
- if (!f.smallest.Valid() || !f.largest.Valid() ||
- f.epoch_number == kUnknownEpochNumber) {
- return false;
- }
- EncodeToNewFile4(f, new_files_[i].first, ts_sz.value(),
- has_min_log_number_to_keep_, min_log_number_to_keep_,
- min_log_num_written, dst);
- }
- for (const auto& blob_file_addition : blob_file_additions_) {
- PutVarint32(dst, kBlobFileAddition);
- blob_file_addition.EncodeTo(dst);
- }
- for (const auto& blob_file_garbage : blob_file_garbages_) {
- PutVarint32(dst, kBlobFileGarbage);
- blob_file_garbage.EncodeTo(dst);
- }
- for (const auto& wal_addition : wal_additions_) {
- PutVarint32(dst, kWalAddition2);
- std::string encoded;
- wal_addition.EncodeTo(&encoded);
- PutLengthPrefixedSlice(dst, encoded);
- }
- if (!wal_deletion_.IsEmpty()) {
- PutVarint32(dst, kWalDeletion2);
- std::string encoded;
- wal_deletion_.EncodeTo(&encoded);
- PutLengthPrefixedSlice(dst, encoded);
- }
- // 0 is default and does not need to be explicitly written
- if (column_family_ != 0) {
- PutVarint32Varint32(dst, kColumnFamily, column_family_);
- }
- if (is_column_family_add_) {
- PutVarint32(dst, kColumnFamilyAdd);
- PutLengthPrefixedSlice(dst, Slice(column_family_name_));
- }
- if (is_column_family_drop_) {
- PutVarint32(dst, kColumnFamilyDrop);
- }
- if (is_in_atomic_group_) {
- PutVarint32(dst, kInAtomicGroup);
- PutVarint32(dst, remaining_entries_);
- }
- if (HasFullHistoryTsLow()) {
- PutVarint32(dst, kFullHistoryTsLow);
- PutLengthPrefixedSlice(dst, full_history_ts_low_);
- }
- if (HasPersistUserDefinedTimestamps()) {
- // persist_user_defined_timestamps flag should be logged in the same
- // VersionEdit as the user comparator name.
- assert(has_comparator_);
- PutVarint32(dst, kPersistUserDefinedTimestamps);
- char p = static_cast<char>(persist_user_defined_timestamps_);
- PutLengthPrefixedSlice(dst, Slice(&p, 1));
- }
- if (HasSubcompactionProgress()) {
- PutVarint32(dst, kSubcompactionProgress);
- std::string progress_data;
- subcompaction_progress_.EncodeTo(&progress_data);
- PutLengthPrefixedSlice(dst, progress_data);
- }
- return true;
- }
- void VersionEdit::EncodeToNewFile4(const FileMetaData& f, int level,
- size_t ts_sz,
- bool has_min_log_number_to_keep,
- uint64_t min_log_number_to_keep,
- bool& min_log_num_written,
- std::string* dst) {
- PutVarint32(dst, kNewFile4);
- PutVarint32Varint64(dst, level, f.fd.GetNumber());
- PutVarint64(dst, f.fd.GetFileSize());
- EncodeFileBoundaries(dst, f, ts_sz);
- PutVarint64Varint64(dst, f.fd.smallest_seqno, f.fd.largest_seqno);
- // Customized fields' format:
- // +-----------------------------+
- // | 1st field's tag (varint32) |
- // +-----------------------------+
- // | 1st field's size (varint32) |
- // +-----------------------------+
- // | bytes for 1st field |
- // | (based on size decoded) |
- // +-----------------------------+
- // | |
- // | ...... |
- // | |
- // +-----------------------------+
- // | last field's size (varint32)|
- // +-----------------------------+
- // | bytes for last field |
- // | (based on size decoded) |
- // +-----------------------------+
- // | terminating tag (varint32) |
- // +-----------------------------+
- //
- // Customized encoding for fields:
- // tag kPathId: 1 byte as path_id
- // tag kNeedCompaction:
- // now only can take one char value 1 indicating need-compaction
- //
- PutVarint32(dst, NewFileCustomTag::kOldestAncesterTime);
- std::string varint_oldest_ancester_time;
- PutVarint64(&varint_oldest_ancester_time, f.oldest_ancester_time);
- TEST_SYNC_POINT_CALLBACK("VersionEdit::EncodeTo:VarintOldestAncesterTime",
- &varint_oldest_ancester_time);
- PutLengthPrefixedSlice(dst, Slice(varint_oldest_ancester_time));
- PutVarint32(dst, NewFileCustomTag::kFileCreationTime);
- std::string varint_file_creation_time;
- PutVarint64(&varint_file_creation_time, f.file_creation_time);
- TEST_SYNC_POINT_CALLBACK("VersionEdit::EncodeTo:VarintFileCreationTime",
- &varint_file_creation_time);
- PutLengthPrefixedSlice(dst, Slice(varint_file_creation_time));
- PutVarint32(dst, NewFileCustomTag::kEpochNumber);
- std::string varint_epoch_number;
- PutVarint64(&varint_epoch_number, f.epoch_number);
- PutLengthPrefixedSlice(dst, Slice(varint_epoch_number));
- if (f.file_checksum_func_name != kUnknownFileChecksumFuncName) {
- PutVarint32(dst, NewFileCustomTag::kFileChecksum);
- PutLengthPrefixedSlice(dst, Slice(f.file_checksum));
- PutVarint32(dst, NewFileCustomTag::kFileChecksumFuncName);
- PutLengthPrefixedSlice(dst, Slice(f.file_checksum_func_name));
- }
- if (f.fd.GetPathId() != 0) {
- PutVarint32(dst, NewFileCustomTag::kPathId);
- char p = static_cast<char>(f.fd.GetPathId());
- PutLengthPrefixedSlice(dst, Slice(&p, 1));
- }
- if (f.temperature != Temperature::kUnknown) {
- PutVarint32(dst, NewFileCustomTag::kTemperature);
- char p = static_cast<char>(f.temperature);
- PutLengthPrefixedSlice(dst, Slice(&p, 1));
- }
- if (f.marked_for_compaction) {
- PutVarint32(dst, NewFileCustomTag::kNeedCompaction);
- char p = static_cast<char>(1);
- PutLengthPrefixedSlice(dst, Slice(&p, 1));
- }
- if (has_min_log_number_to_keep && !min_log_num_written) {
- PutVarint32(dst, NewFileCustomTag::kMinLogNumberToKeepHack);
- std::string varint_log_number;
- PutFixed64(&varint_log_number, min_log_number_to_keep);
- PutLengthPrefixedSlice(dst, Slice(varint_log_number));
- min_log_num_written = true;
- }
- if (f.oldest_blob_file_number != kInvalidBlobFileNumber) {
- PutVarint32(dst, NewFileCustomTag::kOldestBlobFileNumber);
- std::string oldest_blob_file_number;
- PutVarint64(&oldest_blob_file_number, f.oldest_blob_file_number);
- PutLengthPrefixedSlice(dst, Slice(oldest_blob_file_number));
- }
- UniqueId64x2 unique_id = f.unique_id;
- TEST_SYNC_POINT_CALLBACK("VersionEdit::EncodeTo:UniqueId", &unique_id);
- if (unique_id != kNullUniqueId64x2) {
- PutVarint32(dst, NewFileCustomTag::kUniqueId);
- std::string unique_id_str = EncodeUniqueIdBytes(&unique_id);
- PutLengthPrefixedSlice(dst, Slice(unique_id_str));
- }
- if (f.compensated_range_deletion_size) {
- PutVarint32(dst, NewFileCustomTag::kCompensatedRangeDeletionSize);
- std::string compensated_range_deletion_size;
- PutVarint64(&compensated_range_deletion_size,
- f.compensated_range_deletion_size);
- PutLengthPrefixedSlice(dst, Slice(compensated_range_deletion_size));
- }
- if (f.tail_size) {
- PutVarint32(dst, NewFileCustomTag::kTailSize);
- std::string varint_tail_size;
- PutVarint64(&varint_tail_size, f.tail_size);
- PutLengthPrefixedSlice(dst, Slice(varint_tail_size));
- }
- if (!f.user_defined_timestamps_persisted) {
- // The default value for the flag is true, it's only explicitly persisted
- // when it's false. We are putting 0 as the value here to signal false
- // (i.e. UDTS not persisted).
- PutVarint32(dst, NewFileCustomTag::kUserDefinedTimestampsPersisted);
- char p = static_cast<char>(0);
- PutLengthPrefixedSlice(dst, Slice(&p, 1));
- }
- TEST_SYNC_POINT_CALLBACK("VersionEdit::EncodeTo:NewFile4:CustomizeFields",
- dst);
- PutVarint32(dst, NewFileCustomTag::kTerminate);
- }
- static bool GetInternalKey(Slice* input, InternalKey* dst) {
- Slice str;
- if (GetLengthPrefixedSlice(input, &str)) {
- dst->DecodeFrom(str);
- return dst->Valid();
- } else {
- return false;
- }
- }
- bool VersionEdit::GetLevel(Slice* input, int* level, int& max_level) {
- uint32_t v = 0;
- if (GetVarint32(input, &v)) {
- *level = v;
- if (max_level < *level) {
- max_level = *level;
- }
- return true;
- } else {
- return false;
- }
- }
- const char* VersionEdit::DecodeNewFile4From(Slice* input, int& max_level,
- uint64_t& min_log_number_to_keep,
- bool& has_min_log_number_to_keep,
- NewFiles& new_files,
- FileMetaData& f) {
- int level = 0;
- uint64_t number = 0;
- uint32_t path_id = 0;
- uint64_t file_size = 0;
- SequenceNumber smallest_seqno = 0;
- SequenceNumber largest_seqno = kMaxSequenceNumber;
- if (GetLevel(input, &level, max_level) && GetVarint64(input, &number) &&
- GetVarint64(input, &file_size) && GetInternalKey(input, &f.smallest) &&
- GetInternalKey(input, &f.largest) &&
- GetVarint64(input, &smallest_seqno) &&
- GetVarint64(input, &largest_seqno)) {
- // See comments in VersionEdit::EncodeTo() for format of customized fields
- while (true) {
- uint32_t custom_tag = 0;
- Slice field;
- if (!GetVarint32(input, &custom_tag)) {
- return "new-file4 custom field";
- }
- if (custom_tag == kTerminate) {
- break;
- }
- if (!GetLengthPrefixedSlice(input, &field)) {
- return "new-file4 custom field length prefixed slice error";
- }
- switch (custom_tag) {
- case kPathId:
- if (field.size() != 1) {
- return "path_id field wrong size";
- }
- path_id = field[0];
- if (path_id > 3) {
- return "path_id wrong vaue";
- }
- break;
- case kOldestAncesterTime:
- if (!GetVarint64(&field, &f.oldest_ancester_time)) {
- return "invalid oldest ancester time";
- }
- break;
- case kFileCreationTime:
- if (!GetVarint64(&field, &f.file_creation_time)) {
- return "invalid file creation time";
- }
- break;
- case kEpochNumber:
- if (!GetVarint64(&field, &f.epoch_number)) {
- return "invalid epoch number";
- }
- break;
- case kFileChecksum:
- f.file_checksum = field.ToString();
- break;
- case kFileChecksumFuncName:
- f.file_checksum_func_name = field.ToString();
- break;
- case kNeedCompaction:
- if (field.size() != 1) {
- return "need_compaction field wrong size";
- }
- f.marked_for_compaction = (field[0] == 1);
- break;
- case kMinLogNumberToKeepHack:
- // This is a hack to encode kMinLogNumberToKeep in a
- // forward-compatible fashion.
- if (!GetFixed64(&field, &min_log_number_to_keep)) {
- return "deleted log number malformatted";
- }
- has_min_log_number_to_keep = true;
- break;
- case kOldestBlobFileNumber:
- if (!GetVarint64(&field, &f.oldest_blob_file_number)) {
- return "invalid oldest blob file number";
- }
- break;
- case kTemperature:
- if (field.size() != 1) {
- return "temperature field wrong size";
- } else {
- Temperature casted_field = static_cast<Temperature>(field[0]);
- if (casted_field < Temperature::kLastTemperature) {
- f.temperature = casted_field;
- }
- }
- break;
- case kUniqueId:
- if (!DecodeUniqueIdBytes(field.ToString(), &f.unique_id).ok()) {
- f.unique_id = kNullUniqueId64x2;
- return "invalid unique id";
- }
- break;
- case kCompensatedRangeDeletionSize:
- if (!GetVarint64(&field, &f.compensated_range_deletion_size)) {
- return "Invalid compensated range deletion size";
- }
- break;
- case kTailSize:
- if (!GetVarint64(&field, &f.tail_size)) {
- return "invalid tail start offset";
- }
- break;
- case kUserDefinedTimestampsPersisted:
- if (field.size() != 1) {
- return "user-defined timestamps persisted field wrong size";
- }
- f.user_defined_timestamps_persisted = (field[0] == 1);
- break;
- default:
- if ((custom_tag & kCustomTagNonSafeIgnoreMask) != 0) {
- // Should not proceed if cannot understand it
- return "new-file4 custom field not supported";
- }
- break;
- }
- }
- } else {
- return "new-file4 entry";
- }
- f.fd =
- FileDescriptor(number, path_id, file_size, smallest_seqno, largest_seqno);
- new_files.emplace_back(level, f);
- return nullptr;
- }
- void VersionEdit::EncodeFileBoundaries(std::string* dst,
- const FileMetaData& meta, size_t ts_sz) {
- if (ts_sz == 0 || meta.user_defined_timestamps_persisted) {
- PutLengthPrefixedSlice(dst, meta.smallest.Encode());
- PutLengthPrefixedSlice(dst, meta.largest.Encode());
- return;
- }
- std::string smallest_buf;
- std::string largest_buf;
- StripTimestampFromInternalKey(&smallest_buf, meta.smallest.Encode(), ts_sz);
- StripTimestampFromInternalKey(&largest_buf, meta.largest.Encode(), ts_sz);
- PutLengthPrefixedSlice(dst, smallest_buf);
- PutLengthPrefixedSlice(dst, largest_buf);
- }
- Status VersionEdit::DecodeFrom(const Slice& src) {
- Clear();
- #ifndef NDEBUG
- bool ignore_ignorable_tags = false;
- TEST_SYNC_POINT_CALLBACK("VersionEdit::EncodeTo:IgnoreIgnorableTags",
- &ignore_ignorable_tags);
- #endif
- Slice input = src;
- const char* msg = nullptr;
- uint32_t tag = 0;
- // Temporary storage for parsing
- int level = 0;
- FileMetaData f;
- Slice str;
- InternalKey key;
- while (msg == nullptr && GetVarint32(&input, &tag)) {
- #ifndef NDEBUG
- if (ignore_ignorable_tags && tag > kTagSafeIgnoreMask) {
- tag = kTagSafeIgnoreMask;
- }
- #endif
- switch (tag) {
- case kDbId:
- if (GetLengthPrefixedSlice(&input, &str)) {
- db_id_ = str.ToString();
- has_db_id_ = true;
- } else {
- msg = "db id";
- }
- break;
- case kComparator:
- if (GetLengthPrefixedSlice(&input, &str)) {
- comparator_ = str.ToString();
- has_comparator_ = true;
- } else {
- msg = "comparator name";
- }
- break;
- case kLogNumber:
- if (GetVarint64(&input, &log_number_)) {
- has_log_number_ = true;
- } else {
- msg = "log number";
- }
- break;
- case kPrevLogNumber:
- if (GetVarint64(&input, &prev_log_number_)) {
- has_prev_log_number_ = true;
- } else {
- msg = "previous log number";
- }
- break;
- case kNextFileNumber:
- if (GetVarint64(&input, &next_file_number_)) {
- has_next_file_number_ = true;
- } else {
- msg = "next file number";
- }
- break;
- case kMaxColumnFamily:
- if (GetVarint32(&input, &max_column_family_)) {
- has_max_column_family_ = true;
- } else {
- msg = "max column family";
- }
- break;
- case kMinLogNumberToKeep:
- if (GetVarint64(&input, &min_log_number_to_keep_)) {
- has_min_log_number_to_keep_ = true;
- } else {
- msg = "min log number to kee";
- }
- break;
- case kLastSequence:
- if (GetVarint64(&input, &last_sequence_)) {
- has_last_sequence_ = true;
- } else {
- msg = "last sequence number";
- }
- break;
- case kCompactCursor:
- if (GetLevel(&input, &level, max_level_) &&
- GetInternalKey(&input, &key)) {
- // Here we re-use the output format of compact pointer in LevelDB
- // to persist compact_cursors_
- compact_cursors_.push_back(std::make_pair(level, key));
- } else {
- if (!msg) {
- msg = "compaction cursor";
- }
- }
- break;
- case kDeletedFile: {
- uint64_t number = 0;
- if (GetLevel(&input, &level, max_level_) &&
- GetVarint64(&input, &number)) {
- deleted_files_.insert(std::make_pair(level, number));
- } else {
- if (!msg) {
- msg = "deleted file";
- }
- }
- break;
- }
- case kNewFile: {
- uint64_t number = 0;
- uint64_t file_size = 0;
- if (GetLevel(&input, &level, max_level_) &&
- GetVarint64(&input, &number) && GetVarint64(&input, &file_size) &&
- GetInternalKey(&input, &f.smallest) &&
- GetInternalKey(&input, &f.largest)) {
- f.fd = FileDescriptor(number, 0, file_size);
- new_files_.push_back(std::make_pair(level, f));
- } else {
- if (!msg) {
- msg = "new-file entry";
- }
- }
- break;
- }
- case kNewFile2: {
- uint64_t number = 0;
- uint64_t file_size = 0;
- SequenceNumber smallest_seqno = 0;
- SequenceNumber largest_seqno = kMaxSequenceNumber;
- if (GetLevel(&input, &level, max_level_) &&
- GetVarint64(&input, &number) && GetVarint64(&input, &file_size) &&
- GetInternalKey(&input, &f.smallest) &&
- GetInternalKey(&input, &f.largest) &&
- GetVarint64(&input, &smallest_seqno) &&
- GetVarint64(&input, &largest_seqno)) {
- f.fd = FileDescriptor(number, 0, file_size, smallest_seqno,
- largest_seqno);
- new_files_.push_back(std::make_pair(level, f));
- } else {
- if (!msg) {
- msg = "new-file2 entry";
- }
- }
- break;
- }
- case kNewFile3: {
- uint64_t number = 0;
- uint32_t path_id = 0;
- uint64_t file_size = 0;
- SequenceNumber smallest_seqno = 0;
- SequenceNumber largest_seqno = kMaxSequenceNumber;
- if (GetLevel(&input, &level, max_level_) &&
- GetVarint64(&input, &number) && GetVarint32(&input, &path_id) &&
- GetVarint64(&input, &file_size) &&
- GetInternalKey(&input, &f.smallest) &&
- GetInternalKey(&input, &f.largest) &&
- GetVarint64(&input, &smallest_seqno) &&
- GetVarint64(&input, &largest_seqno)) {
- f.fd = FileDescriptor(number, path_id, file_size, smallest_seqno,
- largest_seqno);
- new_files_.push_back(std::make_pair(level, f));
- } else {
- if (!msg) {
- msg = "new-file3 entry";
- }
- }
- break;
- }
- case kNewFile4: {
- FileMetaData ignored_file;
- msg = DecodeNewFile4From(&input, max_level_, min_log_number_to_keep_,
- has_min_log_number_to_keep_, new_files_,
- ignored_file);
- break;
- }
- case kBlobFileAddition:
- case kBlobFileAddition_DEPRECATED: {
- BlobFileAddition blob_file_addition;
- const Status s = blob_file_addition.DecodeFrom(&input);
- if (!s.ok()) {
- return s;
- }
- AddBlobFile(std::move(blob_file_addition));
- break;
- }
- case kBlobFileGarbage:
- case kBlobFileGarbage_DEPRECATED: {
- BlobFileGarbage blob_file_garbage;
- const Status s = blob_file_garbage.DecodeFrom(&input);
- if (!s.ok()) {
- return s;
- }
- AddBlobFileGarbage(std::move(blob_file_garbage));
- break;
- }
- case kWalAddition: {
- WalAddition wal_addition;
- const Status s = wal_addition.DecodeFrom(&input);
- if (!s.ok()) {
- return s;
- }
- wal_additions_.emplace_back(std::move(wal_addition));
- break;
- }
- case kWalAddition2: {
- Slice encoded;
- if (!GetLengthPrefixedSlice(&input, &encoded)) {
- msg = "WalAddition not prefixed by length";
- break;
- }
- WalAddition wal_addition;
- const Status s = wal_addition.DecodeFrom(&encoded);
- if (!s.ok()) {
- return s;
- }
- wal_additions_.emplace_back(std::move(wal_addition));
- break;
- }
- case kWalDeletion: {
- WalDeletion wal_deletion;
- const Status s = wal_deletion.DecodeFrom(&input);
- if (!s.ok()) {
- return s;
- }
- wal_deletion_ = std::move(wal_deletion);
- break;
- }
- case kWalDeletion2: {
- Slice encoded;
- if (!GetLengthPrefixedSlice(&input, &encoded)) {
- msg = "WalDeletion not prefixed by length";
- break;
- }
- WalDeletion wal_deletion;
- const Status s = wal_deletion.DecodeFrom(&encoded);
- if (!s.ok()) {
- return s;
- }
- wal_deletion_ = std::move(wal_deletion);
- break;
- }
- case kColumnFamily:
- if (!GetVarint32(&input, &column_family_)) {
- if (!msg) {
- msg = "set column family id";
- }
- }
- break;
- case kColumnFamilyAdd:
- if (GetLengthPrefixedSlice(&input, &str)) {
- is_column_family_add_ = true;
- column_family_name_ = str.ToString();
- } else {
- if (!msg) {
- msg = "column family add";
- }
- }
- break;
- case kColumnFamilyDrop:
- is_column_family_drop_ = true;
- break;
- case kInAtomicGroup:
- is_in_atomic_group_ = true;
- if (!GetVarint32(&input, &remaining_entries_)) {
- if (!msg) {
- msg = "remaining entries";
- }
- }
- break;
- case kFullHistoryTsLow:
- if (!GetLengthPrefixedSlice(&input, &str)) {
- msg = "full_history_ts_low";
- } else if (str.empty()) {
- msg = "full_history_ts_low: empty";
- } else {
- full_history_ts_low_.assign(str.data(), str.size());
- }
- break;
- case kPersistUserDefinedTimestamps:
- if (!GetLengthPrefixedSlice(&input, &str)) {
- msg = "persist_user_defined_timestamps";
- } else if (str.size() != 1) {
- msg = "persist_user_defined_timestamps field wrong size";
- } else {
- persist_user_defined_timestamps_ = (str[0] == 1);
- has_persist_user_defined_timestamps_ = true;
- }
- break;
- case kSubcompactionProgress: {
- Slice encoded;
- if (!GetLengthPrefixedSlice(&input, &encoded)) {
- msg = "SubcompactionProgress not prefixed by length";
- break;
- }
- SubcompactionProgress progress;
- Status s = progress.DecodeFrom(&encoded);
- if (!s.ok()) {
- return s;
- }
- SetSubcompactionProgress(progress);
- break;
- }
- default:
- if (tag & kTagSafeIgnoreMask) {
- // Tag from future which can be safely ignored.
- // The next field must be the length of the entry.
- uint32_t field_len;
- if (!GetVarint32(&input, &field_len) ||
- static_cast<size_t>(field_len) > input.size()) {
- if (!msg) {
- msg = "safely ignoreable tag length error";
- }
- } else {
- input.remove_prefix(static_cast<size_t>(field_len));
- }
- } else {
- msg = "unknown tag";
- }
- break;
- }
- }
- if (msg == nullptr && !input.empty()) {
- msg = "invalid tag";
- }
- Status result;
- if (msg != nullptr) {
- result = Status::Corruption("VersionEdit", msg);
- }
- return result;
- }
- std::string VersionEdit::DebugString(bool hex_key) const {
- std::string r;
- r.append("VersionEdit {");
- if (has_db_id_) {
- r.append("\n DB ID: ");
- r.append(db_id_);
- }
- if (has_comparator_) {
- r.append("\n Comparator: ");
- r.append(comparator_);
- }
- if (has_persist_user_defined_timestamps_) {
- r.append("\n PersistUserDefinedTimestamps: ");
- r.append(persist_user_defined_timestamps_ ? "true" : "false");
- }
- if (has_log_number_) {
- r.append("\n LogNumber: ");
- AppendNumberTo(&r, log_number_);
- }
- if (has_prev_log_number_) {
- r.append("\n PrevLogNumber: ");
- AppendNumberTo(&r, prev_log_number_);
- }
- if (has_next_file_number_) {
- r.append("\n NextFileNumber: ");
- AppendNumberTo(&r, next_file_number_);
- }
- if (has_max_column_family_) {
- r.append("\n MaxColumnFamily: ");
- AppendNumberTo(&r, max_column_family_);
- }
- if (has_min_log_number_to_keep_) {
- r.append("\n MinLogNumberToKeep: ");
- AppendNumberTo(&r, min_log_number_to_keep_);
- }
- if (has_last_sequence_) {
- r.append("\n LastSeq: ");
- AppendNumberTo(&r, last_sequence_);
- }
- for (const auto& level_and_compact_cursor : compact_cursors_) {
- r.append("\n CompactCursor: ");
- AppendNumberTo(&r, level_and_compact_cursor.first);
- r.append(" ");
- r.append(level_and_compact_cursor.second.DebugString(hex_key));
- }
- for (const auto& deleted_file : deleted_files_) {
- r.append("\n DeleteFile: ");
- AppendNumberTo(&r, deleted_file.first);
- r.append(" ");
- AppendNumberTo(&r, deleted_file.second);
- }
- for (size_t i = 0; i < new_files_.size(); i++) {
- const FileMetaData& f = new_files_[i].second;
- r.append("\n AddFile: ");
- AppendNumberTo(&r, new_files_[i].first);
- r.append(" ");
- AppendNumberTo(&r, f.fd.GetNumber());
- r.append(" ");
- AppendNumberTo(&r, f.fd.GetFileSize());
- r.append(" ");
- r.append(f.smallest.DebugString(hex_key));
- r.append(" .. ");
- r.append(f.largest.DebugString(hex_key));
- if (f.oldest_blob_file_number != kInvalidBlobFileNumber) {
- r.append(" blob_file:");
- AppendNumberTo(&r, f.oldest_blob_file_number);
- }
- r.append(" oldest_ancester_time:");
- AppendNumberTo(&r, f.oldest_ancester_time);
- r.append(" file_creation_time:");
- AppendNumberTo(&r, f.file_creation_time);
- r.append(" epoch_number:");
- AppendNumberTo(&r, f.epoch_number);
- r.append(" file_checksum:");
- r.append(Slice(f.file_checksum).ToString(true));
- r.append(" file_checksum_func_name: ");
- r.append(f.file_checksum_func_name);
- if (f.temperature != Temperature::kUnknown) {
- r.append(" temperature: ");
- // Maybe change to human readable format whenthe feature becomes
- // permanent
- r.append(std::to_string(static_cast<int>(f.temperature)));
- }
- if (f.unique_id != kNullUniqueId64x2) {
- r.append(" unique_id(internal): ");
- UniqueId64x2 id = f.unique_id;
- r.append(InternalUniqueIdToHumanString(&id));
- r.append(" public_unique_id: ");
- InternalUniqueIdToExternal(&id);
- r.append(UniqueIdToHumanString(EncodeUniqueIdBytes(&id)));
- }
- r.append(" tail size: ");
- AppendNumberTo(&r, f.tail_size);
- r.append(" User-defined timestamps persisted: ");
- r.append(f.user_defined_timestamps_persisted ? "true" : "false");
- }
- for (const auto& blob_file_addition : blob_file_additions_) {
- r.append("\n BlobFileAddition: ");
- r.append(blob_file_addition.DebugString());
- }
- for (const auto& blob_file_garbage : blob_file_garbages_) {
- r.append("\n BlobFileGarbage: ");
- r.append(blob_file_garbage.DebugString());
- }
- for (const auto& wal_addition : wal_additions_) {
- r.append("\n WalAddition: ");
- r.append(wal_addition.DebugString());
- }
- if (!wal_deletion_.IsEmpty()) {
- r.append("\n WalDeletion: ");
- r.append(wal_deletion_.DebugString());
- }
- r.append("\n ColumnFamily: ");
- AppendNumberTo(&r, column_family_);
- if (is_column_family_add_) {
- r.append("\n ColumnFamilyAdd: ");
- r.append(column_family_name_);
- }
- if (is_column_family_drop_) {
- r.append("\n ColumnFamilyDrop");
- }
- if (is_in_atomic_group_) {
- r.append("\n AtomicGroup: ");
- AppendNumberTo(&r, remaining_entries_);
- r.append(" entries remains");
- }
- if (HasFullHistoryTsLow()) {
- r.append("\n FullHistoryTsLow: ");
- r.append(Slice(full_history_ts_low_).ToString(hex_key));
- }
- if (HasSubcompactionProgress()) {
- r.append("\n SubcompactionProgress: ");
- r.append(subcompaction_progress_.ToString());
- }
- r.append("\n}\n");
- return r;
- }
- std::string VersionEdit::DebugJSON(int edit_num, bool hex_key) const {
- JSONWriter jw;
- jw << "EditNumber" << edit_num;
- if (has_db_id_) {
- jw << "DB ID" << db_id_;
- }
- if (has_comparator_) {
- jw << "Comparator" << comparator_;
- }
- if (has_log_number_) {
- jw << "LogNumber" << log_number_;
- }
- if (has_prev_log_number_) {
- jw << "PrevLogNumber" << prev_log_number_;
- }
- if (has_next_file_number_) {
- jw << "NextFileNumber" << next_file_number_;
- }
- if (has_max_column_family_) {
- jw << "MaxColumnFamily" << max_column_family_;
- }
- if (has_min_log_number_to_keep_) {
- jw << "MinLogNumberToKeep" << min_log_number_to_keep_;
- }
- if (has_last_sequence_) {
- jw << "LastSeq" << last_sequence_;
- }
- if (!deleted_files_.empty()) {
- jw << "DeletedFiles";
- jw.StartArray();
- for (const auto& deleted_file : deleted_files_) {
- jw.StartArrayedObject();
- jw << "Level" << deleted_file.first;
- jw << "FileNumber" << deleted_file.second;
- jw.EndArrayedObject();
- }
- jw.EndArray();
- }
- if (!new_files_.empty()) {
- jw << "AddedFiles";
- jw.StartArray();
- for (size_t i = 0; i < new_files_.size(); i++) {
- jw.StartArrayedObject();
- jw << "Level" << new_files_[i].first;
- const FileMetaData& f = new_files_[i].second;
- jw << "FileNumber" << f.fd.GetNumber();
- jw << "FileSize" << f.fd.GetFileSize();
- jw << "SmallestIKey" << f.smallest.DebugString(hex_key);
- jw << "LargestIKey" << f.largest.DebugString(hex_key);
- jw << "OldestAncesterTime" << f.oldest_ancester_time;
- jw << "FileCreationTime" << f.file_creation_time;
- jw << "EpochNumber" << f.epoch_number;
- jw << "FileChecksum" << Slice(f.file_checksum).ToString(true);
- jw << "FileChecksumFuncName" << f.file_checksum_func_name;
- if (f.temperature != Temperature::kUnknown) {
- jw << "temperature" << std::to_string(static_cast<int>(f.temperature));
- }
- if (f.oldest_blob_file_number != kInvalidBlobFileNumber) {
- jw << "OldestBlobFile" << f.oldest_blob_file_number;
- }
- if (f.temperature != Temperature::kUnknown) {
- // Maybe change to human readable format whenthe feature becomes
- // permanent
- jw << "Temperature" << static_cast<int>(f.temperature);
- }
- jw << "TailSize" << f.tail_size;
- jw << "UserDefinedTimestampsPersisted"
- << f.user_defined_timestamps_persisted;
- jw.EndArrayedObject();
- }
- jw.EndArray();
- }
- if (!blob_file_additions_.empty()) {
- jw << "BlobFileAdditions";
- jw.StartArray();
- for (const auto& blob_file_addition : blob_file_additions_) {
- jw.StartArrayedObject();
- jw << blob_file_addition;
- jw.EndArrayedObject();
- }
- jw.EndArray();
- }
- if (!blob_file_garbages_.empty()) {
- jw << "BlobFileGarbages";
- jw.StartArray();
- for (const auto& blob_file_garbage : blob_file_garbages_) {
- jw.StartArrayedObject();
- jw << blob_file_garbage;
- jw.EndArrayedObject();
- }
- jw.EndArray();
- }
- if (!wal_additions_.empty()) {
- jw << "WalAdditions";
- jw.StartArray();
- for (const auto& wal_addition : wal_additions_) {
- jw.StartArrayedObject();
- jw << wal_addition;
- jw.EndArrayedObject();
- }
- jw.EndArray();
- }
- if (!wal_deletion_.IsEmpty()) {
- jw << "WalDeletion";
- jw.StartObject();
- jw << wal_deletion_;
- jw.EndObject();
- }
- jw << "ColumnFamily" << column_family_;
- if (is_column_family_add_) {
- jw << "ColumnFamilyAdd" << column_family_name_;
- }
- if (is_column_family_drop_) {
- jw << "ColumnFamilyDrop" << column_family_name_;
- }
- if (is_in_atomic_group_) {
- jw << "AtomicGroup" << remaining_entries_;
- }
- if (HasFullHistoryTsLow()) {
- jw << "FullHistoryTsLow" << Slice(full_history_ts_low_).ToString(hex_key);
- }
- if (HasSubcompactionProgress()) {
- jw << "SubcompactionProgress" << subcompaction_progress_.ToString();
- }
- jw.EndObject();
- return jw.Get();
- }
- void SubcompactionProgressPerLevel::EncodeTo(std::string* dst) const {
- if (num_processed_output_records_ > 0) {
- PutVarint32(
- dst,
- SubcompactionProgressPerLevelCustomTag::kNumProcessedOutputRecords);
- std::string varint_records;
- PutVarint64(&varint_records, num_processed_output_records_);
- PutLengthPrefixedSlice(dst, varint_records);
- }
- if (!output_files_.empty()) {
- PutVarint32(dst, SubcompactionProgressPerLevelCustomTag::kOutputFilesDelta);
- std::string files_data;
- EncodeOutputFiles(&files_data);
- PutLengthPrefixedSlice(dst, files_data);
- }
- PutVarint32(dst, SubcompactionProgressPerLevelCustomTag::
- kSubcompactionProgressPerLevelTerminate);
- }
- Status SubcompactionProgressPerLevel::DecodeFrom(Slice* input) {
- Clear();
- while (true) {
- uint32_t tag = 0;
- if (!GetVarint32(input, &tag)) {
- return Status::Corruption("SubcompactionProgressPerLevel", "tag error");
- }
- if (tag == SubcompactionProgressPerLevelCustomTag::
- kSubcompactionProgressPerLevelTerminate) {
- break;
- }
- Slice field;
- if (!GetLengthPrefixedSlice(input, &field)) {
- return Status::Corruption("SubcompactionProgressPerLevel",
- "field length prefixed slice error");
- }
- switch (tag) {
- case SubcompactionProgressPerLevelCustomTag::kNumProcessedOutputRecords: {
- if (!GetVarint64(&field, &num_processed_output_records_)) {
- return Status::Corruption("SubcompactionProgressPerLevel",
- "invalid num_processed_output_records_");
- }
- break;
- }
- case SubcompactionProgressPerLevelCustomTag::kOutputFilesDelta: {
- Status s = DecodeOutputFiles(&field, output_files_);
- if (!s.ok()) {
- return s;
- }
- break;
- }
- default:
- // Forward compatibility: Handle unknown tags
- if ((tag & SubcompactionProgressPerLevelCustomTag::
- kSubcompactionProgressPerLevelCustomTagSafeIgnoreMask) !=
- 0) {
- break;
- } else {
- return Status::NotSupported("SubcompactionProgress",
- "unsupported critical custom field");
- }
- }
- }
- return Status::OK();
- }
- void SubcompactionProgressPerLevel::EncodeOutputFiles(std::string* dst) const {
- size_t new_files_count =
- output_files_.size() > last_persisted_output_files_count_
- ? output_files_.size() - last_persisted_output_files_count_
- : 0;
- assert(new_files_count > 0);
- PutVarint32(dst, static_cast<uint32_t>(new_files_count));
- for (size_t i = last_persisted_output_files_count_; i < output_files_.size();
- ++i) {
- std::string file_dst;
- bool ignored_min_log_written = false;
- VersionEdit::EncodeToNewFile4(
- output_files_[i], -1 /* level */, 0 /* ts_sz */,
- false /* has_min_log_number_to_keep */, 0 /* min_log_number_to_keep */,
- ignored_min_log_written, &file_dst);
- PutLengthPrefixedSlice(dst, file_dst);
- }
- }
- Status SubcompactionProgressPerLevel::DecodeOutputFiles(
- Slice* input, autovector<FileMetaData>& output_files) {
- uint32_t new_file_count = 0;
- if (!GetVarint32(input, &new_file_count)) {
- return Status::Corruption("SubcompactionProgressPerLevel",
- "new output file count");
- }
- assert(output_files.size() == 0);
- output_files.reserve(new_file_count);
- for (uint32_t i = 0; i < new_file_count; ++i) {
- Slice file_input;
- if (!GetLengthPrefixedSlice(input, &file_input)) {
- return Status::Corruption("SubcompactionProgressPerLevel",
- "output file metadata");
- }
- uint32_t tag = 0;
- if (!GetVarint32(&file_input, &tag) || tag != kNewFile4) {
- return Status::Corruption("SubcompactionProgressPerLevel",
- "expected kNewFile4 tag");
- }
- int ignored_max_level = -1;
- uint64_t ignored_min_log_number_to_keep = 0;
- bool ignored_has_min_log_number_to_keep = false;
- VersionEdit::NewFiles ignored_new_files;
- FileMetaData file;
- const char* err = VersionEdit::DecodeNewFile4From(
- &file_input, ignored_max_level, ignored_min_log_number_to_keep,
- ignored_has_min_log_number_to_keep, ignored_new_files, file);
- if (err != nullptr) {
- return Status::Corruption("SubcompactionProgressPerLevel", err);
- }
- output_files.push_back(std::move(file));
- }
- return Status::OK();
- }
- void SubcompactionProgress::EncodeTo(std::string* dst) const {
- if (!next_internal_key_to_compact.empty()) {
- PutVarint32(dst, SubcompactionProgressCustomTag::kNextInternalKeyToCompact);
- PutLengthPrefixedSlice(dst, next_internal_key_to_compact);
- }
- PutVarint32(dst, SubcompactionProgressCustomTag::kNumProcessedInputRecords);
- std::string varint_records;
- PutVarint64(&varint_records, num_processed_input_records);
- PutLengthPrefixedSlice(dst, varint_records);
- if (output_level_progress.GetOutputFiles().size() >
- output_level_progress.GetLastPersistedOutputFilesCount()) {
- PutVarint32(dst, SubcompactionProgressCustomTag::kOutputLevelProgress);
- std::string level_progress_data;
- output_level_progress.EncodeTo(&level_progress_data);
- PutLengthPrefixedSlice(dst, level_progress_data);
- }
- if (proximal_output_level_progress.GetOutputFiles().size() >
- proximal_output_level_progress.GetLastPersistedOutputFilesCount()) {
- PutVarint32(dst,
- SubcompactionProgressCustomTag::kProximalOutputLevelProgress);
- std::string level_progress_data;
- proximal_output_level_progress.EncodeTo(&level_progress_data);
- PutLengthPrefixedSlice(dst, level_progress_data);
- }
- PutVarint32(dst,
- SubcompactionProgressCustomTag::kSubcompactionProgressTerminate);
- }
- Status SubcompactionProgress::DecodeFrom(Slice* input) {
- Clear();
- while (true) {
- uint32_t custom_tag = 0;
- if (!GetVarint32(input, &custom_tag)) {
- return Status::Corruption("SubcompactionProgress",
- "custom field tag error");
- }
- if (custom_tag ==
- SubcompactionProgressCustomTag::kSubcompactionProgressTerminate) {
- break;
- }
- Slice field;
- if (!GetLengthPrefixedSlice(input, &field)) {
- return Status::Corruption("SubcompactionProgress",
- "custom field length prefixed slice error");
- }
- switch (custom_tag) {
- case SubcompactionProgressCustomTag::kNextInternalKeyToCompact:
- next_internal_key_to_compact = field.ToString();
- break;
- case SubcompactionProgressCustomTag::kNumProcessedInputRecords:
- if (!GetVarint64(&field, &num_processed_input_records)) {
- return Status::Corruption("SubcompactionProgress",
- "invalid num_processed_input_records");
- }
- break;
- case SubcompactionProgressCustomTag::kOutputLevelProgress: {
- Status s = output_level_progress.DecodeFrom(&field);
- if (!s.ok()) {
- return s;
- }
- break;
- }
- case SubcompactionProgressCustomTag::kProximalOutputLevelProgress: {
- Status s = proximal_output_level_progress.DecodeFrom(&field);
- if (!s.ok()) {
- return s;
- }
- break;
- }
- default:
- if ((custom_tag & SubcompactionProgressCustomTag::
- kSubcompactionProgressCustomTagSafeIgnoreMask) !=
- 0) {
- break;
- } else {
- return Status::NotSupported("SubcompactionProgress",
- "unsupported critical custom field");
- }
- }
- }
- return Status::OK();
- }
- bool SubcompactionProgressBuilder::ProcessVersionEdit(const VersionEdit& edit) {
- if (!edit.HasSubcompactionProgress()) {
- return false;
- }
- const SubcompactionProgress& progress = edit.GetSubcompactionProgress();
- MergeDeltaProgress(progress);
- has_subcompaction_progress_ = true;
- return true;
- }
- void SubcompactionProgressBuilder::MergeDeltaProgress(
- const SubcompactionProgress& delta_progress) {
- accumulated_subcompaction_progress_.next_internal_key_to_compact =
- delta_progress.next_internal_key_to_compact;
- accumulated_subcompaction_progress_.num_processed_input_records =
- delta_progress.num_processed_input_records;
- MaybeMergeDeltaProgressPerLevel(
- accumulated_subcompaction_progress_.output_level_progress,
- delta_progress.output_level_progress);
- MaybeMergeDeltaProgressPerLevel(
- accumulated_subcompaction_progress_.proximal_output_level_progress,
- delta_progress.proximal_output_level_progress);
- }
- void SubcompactionProgressBuilder::MaybeMergeDeltaProgressPerLevel(
- SubcompactionProgressPerLevel& accumulated_level_progress,
- const SubcompactionProgressPerLevel& delta_level_progress) {
- const auto& delta_files = delta_level_progress.GetOutputFiles();
- if (delta_files.empty()) {
- return;
- }
- for (const FileMetaData& file : delta_files) {
- accumulated_level_progress.AddToOutputFiles(file); // Stored as copy
- }
- accumulated_level_progress.SetNumProcessedOutputRecords(
- delta_level_progress.GetNumProcessedOutputRecords());
- }
- void SubcompactionProgressBuilder::Clear() {
- accumulated_subcompaction_progress_.Clear();
- has_subcompaction_progress_ = false;
- }
- } // namespace ROCKSDB_NAMESPACE
|