LCOV - code coverage report
Current view: top level - src/leveldb/db - version_edit.cc (source / functions) Coverage Total Hit
Test: test_bitcoin_coverage.info Lines: 69.2 % 146 101
Test Date: 2026-02-04 04:43:42 Functions: 83.3 % 6 5
Branches: 34.8 % 207 72

             Branch data     Line data    Source code
       1                 :             : // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
       2                 :             : // Use of this source code is governed by a BSD-style license that can be
       3                 :             : // found in the LICENSE file. See the AUTHORS file for names of contributors.
       4                 :             : 
       5                 :             : #include "db/version_edit.h"
       6                 :             : 
       7                 :             : #include "db/version_set.h"
       8                 :             : #include "util/coding.h"
       9                 :             : 
      10                 :             : namespace leveldb {
      11                 :             : 
      12                 :             : // Tag numbers for serialized VersionEdit.  These numbers are written to
      13                 :             : // disk and should not be changed.
      14                 :             : enum Tag {
      15                 :             :   kComparator = 1,
      16                 :             :   kLogNumber = 2,
      17                 :             :   kNextFileNumber = 3,
      18                 :             :   kLastSequence = 4,
      19                 :             :   kCompactPointer = 5,
      20                 :             :   kDeletedFile = 6,
      21                 :             :   kNewFile = 7,
      22                 :             :   // 8 was used for large value refs
      23                 :             :   kPrevLogNumber = 9
      24                 :             : };
      25                 :             : 
      26                 :        2540 : void VersionEdit::Clear() {
      27                 :        2540 :   comparator_.clear();
      28                 :        2540 :   log_number_ = 0;
      29                 :        2540 :   prev_log_number_ = 0;
      30                 :        2540 :   last_sequence_ = 0;
      31                 :        2540 :   next_file_number_ = 0;
      32                 :        2540 :   has_comparator_ = false;
      33                 :        2540 :   has_log_number_ = false;
      34                 :        2540 :   has_prev_log_number_ = false;
      35                 :        2540 :   has_next_file_number_ = false;
      36                 :        2540 :   has_last_sequence_ = false;
      37                 :        2540 :   deleted_files_.clear();
      38                 :        2540 :   new_files_.clear();
      39                 :        2540 : }
      40                 :             : 
      41                 :        1411 : void VersionEdit::EncodeTo(std::string* dst) const {
      42         [ +  + ]:        1411 :   if (has_comparator_) {
      43                 :         910 :     PutVarint32(dst, kComparator);
      44         [ -  + ]:         910 :     PutLengthPrefixedSlice(dst, comparator_);
      45                 :             :   }
      46         [ +  + ]:        1411 :   if (has_log_number_) {
      47                 :         922 :     PutVarint32(dst, kLogNumber);
      48                 :         922 :     PutVarint64(dst, log_number_);
      49                 :             :   }
      50         [ +  + ]:        1411 :   if (has_prev_log_number_) {
      51                 :         501 :     PutVarint32(dst, kPrevLogNumber);
      52                 :         501 :     PutVarint64(dst, prev_log_number_);
      53                 :             :   }
      54         [ +  + ]:        1411 :   if (has_next_file_number_) {
      55                 :         922 :     PutVarint32(dst, kNextFileNumber);
      56                 :         922 :     PutVarint64(dst, next_file_number_);
      57                 :             :   }
      58         [ +  + ]:        1411 :   if (has_last_sequence_) {
      59                 :         922 :     PutVarint32(dst, kLastSequence);
      60                 :         922 :     PutVarint64(dst, last_sequence_);
      61                 :             :   }
      62                 :             : 
      63   [ -  +  +  + ]:        1443 :   for (size_t i = 0; i < compact_pointers_.size(); i++) {
      64                 :          32 :     PutVarint32(dst, kCompactPointer);
      65                 :          32 :     PutVarint32(dst, compact_pointers_[i].first);  // level
      66                 :          32 :     PutLengthPrefixedSlice(dst, compact_pointers_[i].second.Encode());
      67                 :             :   }
      68                 :             : 
      69         [ +  + ]:        1455 :   for (const auto& deleted_file_kvp : deleted_files_) {
      70                 :          44 :     PutVarint32(dst, kDeletedFile);
      71                 :          44 :     PutVarint32(dst, deleted_file_kvp.first);   // level
      72                 :          44 :     PutVarint64(dst, deleted_file_kvp.second);  // file number
      73                 :             :   }
      74                 :             : 
      75   [ -  +  +  + ]:        1579 :   for (size_t i = 0; i < new_files_.size(); i++) {
      76                 :         168 :     const FileMetaData& f = new_files_[i].second;
      77                 :         168 :     PutVarint32(dst, kNewFile);
      78                 :         168 :     PutVarint32(dst, new_files_[i].first);  // level
      79                 :         168 :     PutVarint64(dst, f.number);
      80                 :         168 :     PutVarint64(dst, f.file_size);
      81                 :         168 :     PutLengthPrefixedSlice(dst, f.smallest.Encode());
      82                 :         168 :     PutLengthPrefixedSlice(dst, f.largest.Encode());
      83                 :             :   }
      84                 :        1411 : }
      85                 :             : 
      86                 :         276 : static bool GetInternalKey(Slice* input, InternalKey* dst) {
      87                 :         276 :   Slice str;
      88         [ +  - ]:         276 :   if (GetLengthPrefixedSlice(input, &str)) {
      89                 :         276 :     return dst->DecodeFrom(str);
      90                 :             :   } else {
      91                 :             :     return false;
      92                 :             :   }
      93                 :             : }
      94                 :             : 
      95                 :         181 : static bool GetLevel(Slice* input, int* level) {
      96                 :         181 :   uint32_t v;
      97   [ +  -  +  - ]:         181 :   if (GetVarint32(input, &v) && v < config::kNumLevels) {
      98                 :         181 :     *level = v;
      99                 :         181 :     return true;
     100                 :             :   } else {
     101                 :             :     return false;
     102                 :             :   }
     103                 :             : }
     104                 :             : 
     105                 :         564 : Status VersionEdit::DecodeFrom(const Slice& src) {
     106                 :         564 :   Clear();
     107                 :         564 :   Slice input = src;
     108                 :         564 :   const char* msg = nullptr;
     109                 :         564 :   uint32_t tag;
     110                 :             : 
     111                 :             :   // Temporary storage for parsing
     112                 :         564 :   int level;
     113                 :         564 :   uint64_t number;
     114                 :         564 :   FileMetaData f;
     115                 :         564 :   Slice str;
     116                 :         564 :   InternalKey key;
     117                 :             : 
     118   [ +  -  +  -  :        3361 :   while (msg == nullptr && GetVarint32(&input, &tag)) {
                   +  + ]
     119   [ +  +  +  +  :        2233 :     switch (tag) {
             +  +  +  +  
                      - ]
     120                 :         489 :       case kComparator:
     121   [ +  -  +  - ]:         489 :         if (GetLengthPrefixedSlice(&input, &str)) {
     122         [ +  - ]:         489 :           comparator_ = str.ToString();
     123                 :         489 :           has_comparator_ = true;
     124                 :             :         } else {
     125                 :             :           msg = "comparator name";
     126                 :             :         }
     127                 :             :         break;
     128                 :             : 
     129                 :         496 :       case kLogNumber:
     130   [ +  -  +  - ]:         496 :         if (GetVarint64(&input, &log_number_)) {
     131                 :         496 :           has_log_number_ = true;
     132                 :             :         } else {
     133                 :             :           msg = "log number";
     134                 :             :         }
     135                 :             :         break;
     136                 :             : 
     137                 :          75 :       case kPrevLogNumber:
     138   [ +  -  +  - ]:          75 :         if (GetVarint64(&input, &prev_log_number_)) {
     139                 :          75 :           has_prev_log_number_ = true;
     140                 :             :         } else {
     141                 :             :           msg = "previous log number";
     142                 :             :         }
     143                 :             :         break;
     144                 :             : 
     145                 :         496 :       case kNextFileNumber:
     146   [ +  -  +  - ]:         496 :         if (GetVarint64(&input, &next_file_number_)) {
     147                 :         496 :           has_next_file_number_ = true;
     148                 :             :         } else {
     149                 :             :           msg = "next file number";
     150                 :             :         }
     151                 :             :         break;
     152                 :             : 
     153                 :         496 :       case kLastSequence:
     154   [ +  -  +  - ]:         496 :         if (GetVarint64(&input, &last_sequence_)) {
     155                 :         496 :           has_last_sequence_ = true;
     156                 :             :         } else {
     157                 :             :           msg = "last sequence number";
     158                 :             :         }
     159                 :             :         break;
     160                 :             : 
     161                 :          24 :       case kCompactPointer:
     162   [ +  -  +  -  :          24 :         if (GetLevel(&input, &level) && GetInternalKey(&input, &key)) {
             +  -  +  - ]
     163   [ -  +  +  - ]:          48 :           compact_pointers_.push_back(std::make_pair(level, key));
     164                 :             :         } else {
     165                 :             :           msg = "compaction pointer";
     166                 :             :         }
     167                 :             :         break;
     168                 :             : 
     169                 :          31 :       case kDeletedFile:
     170   [ +  -  +  -  :          31 :         if (GetLevel(&input, &level) && GetVarint64(&input, &number)) {
             +  -  +  - ]
     171         [ +  - ]:          31 :           deleted_files_.insert(std::make_pair(level, number));
     172                 :             :         } else {
     173                 :             :           msg = "deleted file";
     174                 :             :         }
     175                 :             :         break;
     176                 :             : 
     177                 :         126 :       case kNewFile:
     178   [ +  -  +  -  :         378 :         if (GetLevel(&input, &level) && GetVarint64(&input, &f.number) &&
             +  -  +  - ]
     179   [ +  -  +  - ]:         252 :             GetVarint64(&input, &f.file_size) &&
     180   [ +  -  +  -  :         378 :             GetInternalKey(&input, &f.smallest) &&
                   +  - ]
     181         [ +  - ]:         126 :             GetInternalKey(&input, &f.largest)) {
     182   [ +  -  +  - ]:         378 :           new_files_.push_back(std::make_pair(level, f));
     183                 :             :         } else {
     184                 :             :           msg = "new-file entry";
     185                 :             :         }
     186                 :             :         break;
     187                 :             : 
     188                 :             :       default:
     189                 :             :         msg = "unknown tag";
     190                 :             :         break;
     191                 :             :     }
     192                 :             :   }
     193                 :             : 
     194   [ +  -  +  - ]:         564 :   if (msg == nullptr && !input.empty()) {
     195                 :           0 :     msg = "invalid tag";
     196                 :             :   }
     197                 :             : 
     198         [ -  + ]:         564 :   Status result;
     199         [ -  + ]:         564 :   if (msg != nullptr) {
     200   [ #  #  #  # ]:           0 :     result = Status::Corruption("VersionEdit", msg);
     201                 :             :   }
     202                 :         564 :   return result;
     203                 :        1128 : }
     204                 :             : 
     205                 :           0 : std::string VersionEdit::DebugString() const {
     206         [ #  # ]:           0 :   std::string r;
     207         [ #  # ]:           0 :   r.append("VersionEdit {");
     208         [ #  # ]:           0 :   if (has_comparator_) {
     209         [ #  # ]:           0 :     r.append("\n  Comparator: ");
     210         [ #  # ]:           0 :     r.append(comparator_);
     211                 :             :   }
     212         [ #  # ]:           0 :   if (has_log_number_) {
     213         [ #  # ]:           0 :     r.append("\n  LogNumber: ");
     214         [ #  # ]:           0 :     AppendNumberTo(&r, log_number_);
     215                 :             :   }
     216         [ #  # ]:           0 :   if (has_prev_log_number_) {
     217         [ #  # ]:           0 :     r.append("\n  PrevLogNumber: ");
     218         [ #  # ]:           0 :     AppendNumberTo(&r, prev_log_number_);
     219                 :             :   }
     220         [ #  # ]:           0 :   if (has_next_file_number_) {
     221         [ #  # ]:           0 :     r.append("\n  NextFile: ");
     222         [ #  # ]:           0 :     AppendNumberTo(&r, next_file_number_);
     223                 :             :   }
     224         [ #  # ]:           0 :   if (has_last_sequence_) {
     225         [ #  # ]:           0 :     r.append("\n  LastSeq: ");
     226         [ #  # ]:           0 :     AppendNumberTo(&r, last_sequence_);
     227                 :             :   }
     228   [ #  #  #  # ]:           0 :   for (size_t i = 0; i < compact_pointers_.size(); i++) {
     229         [ #  # ]:           0 :     r.append("\n  CompactPointer: ");
     230         [ #  # ]:           0 :     AppendNumberTo(&r, compact_pointers_[i].first);
     231         [ #  # ]:           0 :     r.append(" ");
     232         [ #  # ]:           0 :     r.append(compact_pointers_[i].second.DebugString());
     233                 :             :   }
     234         [ #  # ]:           0 :   for (const auto& deleted_files_kvp : deleted_files_) {
     235         [ #  # ]:           0 :     r.append("\n  DeleteFile: ");
     236         [ #  # ]:           0 :     AppendNumberTo(&r, deleted_files_kvp.first);
     237         [ #  # ]:           0 :     r.append(" ");
     238         [ #  # ]:           0 :     AppendNumberTo(&r, deleted_files_kvp.second);
     239                 :             :   }
     240   [ #  #  #  # ]:           0 :   for (size_t i = 0; i < new_files_.size(); i++) {
     241         [ #  # ]:           0 :     const FileMetaData& f = new_files_[i].second;
     242         [ #  # ]:           0 :     r.append("\n  AddFile: ");
     243         [ #  # ]:           0 :     AppendNumberTo(&r, new_files_[i].first);
     244         [ #  # ]:           0 :     r.append(" ");
     245         [ #  # ]:           0 :     AppendNumberTo(&r, f.number);
     246         [ #  # ]:           0 :     r.append(" ");
     247         [ #  # ]:           0 :     AppendNumberTo(&r, f.file_size);
     248         [ #  # ]:           0 :     r.append(" ");
     249         [ #  # ]:           0 :     r.append(f.smallest.DebugString());
     250         [ #  # ]:           0 :     r.append(" .. ");
     251         [ #  # ]:           0 :     r.append(f.largest.DebugString());
     252                 :             :   }
     253         [ #  # ]:           0 :   r.append("\n}\n");
     254                 :           0 :   return r;
     255                 :           0 : }
     256                 :             : 
     257                 :             : }  // namespace leveldb
        

Generated by: LCOV version 2.0-1