10225501448 李度 10225101546 陈胤遒 10215501422 高宇菲
25개 이상의 토픽을 선택하실 수 없습니다. Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

109 lines
2.6 KiB

#include "kv_sep/kvlog.h"
#include "db/dbformat.h"
#include "db/filename.h"
#include "db/write_batch_internal.h"
#include <cstdint>
#include "leveldb/env.h"
#include "leveldb/slice.h"
#include "leveldb/status.h"
#include "util/coding.h"
namespace leveldb {
void EncodeFP(const struct FilePointer &fp, char *scratch) {
EncodeFixed64(scratch, fp.FileNumber);
EncodeFixed64(scratch + 8, fp.FileOffset);
EncodeFixed64(scratch + 16, fp.Size);
}
void DecodeFp(struct FilePointer &fp, char *src) {
fp.FileNumber = DecodeFixed64(src);
fp.FileOffset = DecodeFixed64(src + 8);
fp.Size = DecodeFixed64(src + 16);
}
KVLog::KVLog(WritableFile *dest,uint64_t file_number):
dest_(dest),pos_(0),file_number(file_number) {}
KVLog::KVLog(WritableFile *dest, uint64_t dest_length,uint64_t file_number):
dest_(dest),pos_(dest_length),file_number(file_number) {}
Status KVLog::AddRecord(const Slice &slice, FilePointer &fp) {
//写入slice大小
EncodeFixed64(buf, slice.size());
Status s = dest_->Append(Slice(buf,8));
pos_ += 8;
//写入slice
fp.FileNumber = file_number;
fp.FileOffset = pos_;
fp.Size = slice.size();
s = dest_->Append(slice);
pos_ += slice.size();
if(s.ok()) {
s = dest_->Flush();
}
return s;
}
void KVLogReader::Next() {
if(input.empty()) {
NextWriteBatch();
if(!Valid()) return;
}
NextKV();
}
void KVLogReader::NextWriteBatch() {
Slice num;
file->Read(8, &num, number);
if(num.size() !=8) {
valid = false;
return;
}
uint64_t batch_size = DecodeFixed64(number);
if(batch_size > rep_size) {
delete[] rep_;
rep_ = new char[batch_size];
rep_size = batch_size;
}
input.clear();
file->Read(batch_size,&input,rep_);
if(input.size() != batch_size) {
valid = false;
return;
}
seq = DecodeFixed64(input.data()) - 1;//-1是为了和后面的nextkv的实现对齐
input.remove_prefix(12); //remove writebatch header
}
void KVLogReader::NextKV() {
seq++;
type = (ValueType)input[0];
input.remove_prefix(1);
switch (type) {
case kTypeValue:
if(GetLengthPrefixedSlice(&input, &key) &&
GetLengthPrefixedSlice(&input, &value)) {
} else {
valid = false;
return;
}
break;
case kTypeDeletion:
if(GetLengthPrefixedSlice(&input, &key)) {
} else {
valid = false;
return;
}
break;
default:
valid = false;
return;
}
}
}