#include #include "leveldb/env.h" #include "leveldb/merge_operator.h" #include "leveldb/slice.h" #include "util/coding.h" #include "utilities/merge_operators.h" using namespace leveldb; namespace { // anonymous namespace // A 'model' merge operator with uint64 addition semantics class UInt64AddOperator : public MergeOperator { public: virtual void Merge(const Slice& key, const Slice* existing_value, const Slice& value, std::string* new_value, Logger* logger) const override { // assuming 0 if no existing value uint64_t existing = 0; if (existing_value) { if (existing_value->size() == sizeof(uint64_t)) { existing = DecodeFixed64(existing_value->data()); } else { // if existing_value is corrupted, treat it as 0 Log(logger, "existing value corruption, size: %zu > %zu", existing_value->size(), sizeof(uint64_t)); existing = 0; } } uint64_t operand; if (value.size() == sizeof(uint64_t)) { operand = DecodeFixed64(value.data()); } else { // if operand is corrupted, treat it as 0 Log(logger, "operand value corruption, size: %zu > %zu", value.size(), sizeof(uint64_t)); operand = 0; } new_value->resize(sizeof(uint64_t)); EncodeFixed64(&(*new_value)[0], existing + operand); return; } virtual const char* Name() const override { return "UInt64AddOperator"; } }; } namespace leveldb { std::shared_ptr MergeOperators::CreateUInt64AddOperator() { return std::make_shared(); } }