/Users/deen/code/yugabyte-db/src/yb/rocksdb/table/fixed_size_filter_block.cc
Line | Count | Source (jump to first uncovered line) |
1 | | // Copyright (c) YugaByte, Inc. |
2 | | // |
3 | | // Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except |
4 | | // in compliance with the License. You may obtain a copy of the License at |
5 | | // |
6 | | // http://www.apache.org/licenses/LICENSE-2.0 |
7 | | // |
8 | | // Unless required by applicable law or agreed to in writing, software distributed under the License |
9 | | // is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express |
10 | | // or implied. See the License for the specific language governing permissions and limitations |
11 | | // under the License. |
12 | | // |
13 | | // |
14 | | // Copyright (c) 2012 The LevelDB Authors. All rights reserved. |
15 | | // Use of this source code is governed by a BSD-style license that can be |
16 | | // found in the LICENSE file. See the AUTHORS file for names of contributors. |
17 | | |
18 | | #include "yb/rocksdb/table/fixed_size_filter_block.h" |
19 | | |
20 | | #include "yb/rocksdb/filter_policy.h" |
21 | | #include "yb/rocksdb/util/perf_context_imp.h" |
22 | | |
23 | | namespace rocksdb { |
24 | | |
25 | | namespace { |
26 | | |
27 | | void AppendItem(std::string* props, const std::string& key, |
28 | 0 | const std::string& value) { |
29 | 0 | char cspace = ' '; |
30 | 0 | std::string value_str(""); |
31 | 0 | size_t i = 0; |
32 | 0 | const size_t dataLength = 64; |
33 | 0 | const size_t tabLength = 2; |
34 | 0 | const size_t offLength = 16; |
35 | |
|
36 | 0 | value_str.append(&value[i], std::min(size_t(dataLength), value.size())); |
37 | 0 | i += dataLength; |
38 | 0 | while (i < value.size()) { |
39 | 0 | value_str.append("\n"); |
40 | 0 | value_str.append(offLength, cspace); |
41 | 0 | value_str.append(&value[i], std::min(size_t(dataLength), value.size() - i)); |
42 | 0 | i += dataLength; |
43 | 0 | } |
44 | |
|
45 | 0 | std::string result(""); |
46 | 0 | if (key.size() < (offLength - tabLength)) |
47 | 0 | result.append(size_t((offLength - tabLength)) - key.size(), cspace); |
48 | 0 | result.append(key); |
49 | |
|
50 | 0 | props->append(result + ": " + value_str + "\n"); |
51 | 0 | } |
52 | | |
53 | | template <class TKey> |
54 | | void AppendItem(std::string* props, const TKey& key, const std::string& value) { |
55 | | std::string key_str = rocksdb::ToString(key); |
56 | | AppendItem(props, key_str, value); |
57 | | } |
58 | | } // namespace |
59 | | |
60 | | |
61 | | // See doc/table_format.txt for an explanation of the filter block format. |
62 | | |
63 | | // Generate new filter for fixed number of keys |
64 | | FixedSizeFilterBlockBuilder::FixedSizeFilterBlockBuilder( |
65 | | const SliceTransform* prefix_extractor, |
66 | | const BlockBasedTableOptions& table_opt) |
67 | | : policy_(table_opt.filter_policy.get()), |
68 | | prefix_extractor_(prefix_extractor), |
69 | | whole_key_filtering_(table_opt.whole_key_filtering), |
70 | 3.11k | bits_builder_(nullptr) { |
71 | 3.11k | } |
72 | | |
73 | 3.18k | void FixedSizeFilterBlockBuilder::StartBlock(uint64_t block_offset) { |
74 | 3.18k | assert(policy_); |
75 | 3.18k | assert(!bits_builder_); |
76 | 3.18k | FilterBitsBuilder* filter_bits_builder_ = policy_->GetFilterBitsBuilder(); |
77 | 3.18k | assert(filter_bits_builder_); |
78 | 3.18k | bits_builder_.reset(filter_bits_builder_); |
79 | 3.18k | } |
80 | | |
81 | 5.83M | void FixedSizeFilterBlockBuilder::Add(const Slice& key) { |
82 | 5.83M | if (prefix_extractor_ && prefix_extractor_->InDomain(key)) { |
83 | 201 | AddPrefix(key); |
84 | 201 | } |
85 | | |
86 | 5.83M | if (whole_key_filtering_) { |
87 | 5.83M | AddKey(key); |
88 | 5.83M | } |
89 | 5.83M | } |
90 | | |
91 | 5.83M | void FixedSizeFilterBlockBuilder::AddKey(const Slice& key) { |
92 | 5.83M | assert(bits_builder_); |
93 | 5.83M | bits_builder_->AddKey(key); |
94 | 5.83M | } |
95 | | |
96 | 201 | void FixedSizeFilterBlockBuilder::AddPrefix(const Slice& key) { |
97 | 201 | assert(bits_builder_); |
98 | 201 | Slice prefix = prefix_extractor_->Transform(key); |
99 | 201 | bits_builder_->AddKey(prefix); |
100 | 201 | } |
101 | | |
102 | 5.83M | bool FixedSizeFilterBlockBuilder::ShouldFlush() const { |
103 | 5.83M | assert(bits_builder_); |
104 | 5.83M | return bits_builder_->IsFull(); |
105 | 5.83M | } |
106 | | |
107 | 3.18k | Slice FixedSizeFilterBlockBuilder::Finish() { |
108 | 3.18k | assert(bits_builder_); |
109 | 3.18k | Slice finished_slice = bits_builder_->Finish(&active_block_data_); |
110 | 3.18k | bits_builder_.reset(); |
111 | 3.18k | results_.push_back(std::move(active_block_data_)); |
112 | 3.18k | return finished_slice; |
113 | 3.18k | } |
114 | | |
115 | | FixedSizeFilterBlockReader::FixedSizeFilterBlockReader( |
116 | | const SliceTransform* prefix_extractor, |
117 | | const BlockBasedTableOptions& table_opt, |
118 | | bool whole_key_filtering, |
119 | | BlockContents&& contents) |
120 | | : policy_(table_opt.filter_policy.get()), |
121 | | prefix_extractor_(prefix_extractor), |
122 | | whole_key_filtering_(whole_key_filtering), |
123 | 1.37k | contents_(std::move(contents)) { |
124 | 1.37k | assert(policy_); |
125 | 1.37k | reader_.reset(policy_->GetFilterBitsReader(contents_.data)); |
126 | 1.37k | } |
127 | | |
128 | 4.55M | bool FixedSizeFilterBlockReader::KeyMayMatch(const Slice& key, uint64_t block_offset) { |
129 | 4.55M | return whole_key_filtering_ ? MayMatch(key) : true; |
130 | 4.55M | } |
131 | | |
132 | 1 | bool FixedSizeFilterBlockReader::PrefixMayMatch(const Slice& prefix, uint64_t block_offset) { |
133 | 1 | return prefix_extractor_ ? MayMatch(prefix) : true; |
134 | 1 | } |
135 | | |
136 | 4.55M | bool FixedSizeFilterBlockReader::MayMatch(const Slice& entry) { |
137 | 4.55M | if (reader_->MayMatch(entry)) { |
138 | 1.76M | PERF_COUNTER_ADD(bloom_sst_hit_count, 1); |
139 | 1.76M | return true; |
140 | 2.79M | } else { |
141 | 2.79M | PERF_COUNTER_ADD(bloom_sst_miss_count, 1); |
142 | 2.79M | return false; |
143 | 2.79M | } |
144 | 4.55M | } |
145 | | |
146 | 0 | size_t FixedSizeFilterBlockReader::ApproximateMemoryUsage() const { |
147 | 0 | return contents_.data.size(); |
148 | 0 | } |
149 | | |
150 | 0 | std::string FixedSizeFilterBlockReader::ToString() const { |
151 | 0 | std::string result; |
152 | 0 | result.reserve(contents_.data.size() * 2); |
153 | 0 | AppendItem(&result, std::string("Filter block"), contents_.data.ToString(true)); |
154 | 0 | return result; |
155 | 0 | } |
156 | | } // namespace rocksdb |