]> git.proxmox.com Git - ceph.git/blob - ceph/src/rocksdb/tools/db_bench_tool_test.cc
import quincy beta 17.1.0
[ceph.git] / ceph / src / rocksdb / tools / db_bench_tool_test.cc
1 // Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
2 // This source code is licensed under both the GPLv2 (found in the
3 // COPYING file in the root directory) and Apache 2.0 License
4 // (found in the LICENSE.Apache file in the root directory).
5 //
6 // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
7 // Use of this source code is governed by a BSD-style license that can be
8 // found in the LICENSE file. See the AUTHORS file for names of contributors.
9
10 #include "rocksdb/db_bench_tool.h"
11
12 #include "db/db_impl/db_impl.h"
13 #include "options/options_parser.h"
14 #include "rocksdb/utilities/options_util.h"
15 #include "test_util/testharness.h"
16 #include "test_util/testutil.h"
17 #include "util/random.h"
18
19 #ifdef GFLAGS
20 #include "util/gflags_compat.h"
21
22 namespace ROCKSDB_NAMESPACE {
23 namespace {
24 static const int kMaxArgCount = 100;
25 static const size_t kArgBufferSize = 100000;
26 } // namespace
27
28 class DBBenchTest : public testing::Test {
29 public:
30 DBBenchTest() : rnd_(0xFB) {
31 test_path_ = test::PerThreadDBPath("db_bench_test");
32 Env::Default()->CreateDir(test_path_);
33 db_path_ = test_path_ + "/db";
34 wal_path_ = test_path_ + "/wal";
35 fs_.reset(new LegacyFileSystemWrapper(Env::Default()));
36 }
37
38 ~DBBenchTest() {
39 // DestroyDB(db_path_, Options());
40 }
41
42 void ResetArgs() {
43 argc_ = 0;
44 cursor_ = 0;
45 memset(arg_buffer_, 0, kArgBufferSize);
46 }
47
48 void AppendArgs(const std::vector<std::string>& args) {
49 for (const auto& arg : args) {
50 ASSERT_LE(cursor_ + arg.size() + 1, kArgBufferSize);
51 ASSERT_LE(argc_ + 1, kMaxArgCount);
52 snprintf(arg_buffer_ + cursor_, arg.size() + 1, "%s", arg.c_str());
53
54 argv_[argc_++] = arg_buffer_ + cursor_;
55 cursor_ += arg.size() + 1;
56 }
57 }
58
59 // Gets the default options for this test/db_bench.
60 // Note that db_bench may change some of the default option values and that
61 // the database might as well. The options changed by db_bench are
62 // specified here; the ones by the DB are set via SanitizeOptions
63 Options GetDefaultOptions(CompactionStyle style = kCompactionStyleLevel,
64 int levels = 7) const {
65 Options opt;
66
67 opt.create_if_missing = true;
68 opt.max_open_files = 256;
69 opt.max_background_compactions = 10;
70 opt.dump_malloc_stats = true; // db_bench uses a different default
71 opt.compaction_style = style;
72 opt.num_levels = levels;
73 opt.compression = kNoCompression;
74 opt.arena_block_size = 8388608;
75
76 return SanitizeOptions(db_path_, opt);
77 }
78
79 void RunDbBench(const std::string& options_file_name) {
80 AppendArgs({"./db_bench", "--benchmarks=fillseq", "--use_existing_db=0",
81 "--num=1000", "--compression_type=none",
82 std::string(std::string("--db=") + db_path_).c_str(),
83 std::string(std::string("--wal_dir=") + wal_path_).c_str(),
84 std::string(std::string("--options_file=") + options_file_name)
85 .c_str()});
86 ASSERT_EQ(0, db_bench_tool(argc(), argv()));
87 }
88
89 void VerifyOptions(const Options& opt) {
90 DBOptions loaded_db_opts;
91 std::vector<ColumnFamilyDescriptor> cf_descs;
92 ASSERT_OK(LoadLatestOptions(db_path_, Env::Default(), &loaded_db_opts,
93 &cf_descs));
94
95 ConfigOptions exact;
96 exact.input_strings_escaped = false;
97 exact.sanity_level = ConfigOptions::kSanityLevelExactMatch;
98 ASSERT_OK(RocksDBOptionsParser::VerifyDBOptions(exact, DBOptions(opt),
99 loaded_db_opts));
100 ASSERT_OK(RocksDBOptionsParser::VerifyCFOptions(
101 exact, ColumnFamilyOptions(opt), cf_descs[0].options));
102
103 // check with the default rocksdb options and expect failure
104 ASSERT_NOK(RocksDBOptionsParser::VerifyDBOptions(exact, DBOptions(),
105 loaded_db_opts));
106 ASSERT_NOK(RocksDBOptionsParser::VerifyCFOptions(
107 exact, ColumnFamilyOptions(), cf_descs[0].options));
108 }
109
110 char** argv() { return argv_; }
111
112 int argc() { return argc_; }
113
114 std::string db_path_;
115 std::string test_path_;
116 std::string wal_path_;
117 std::unique_ptr<LegacyFileSystemWrapper> fs_;
118
119 char arg_buffer_[kArgBufferSize];
120 char* argv_[kMaxArgCount];
121 int argc_ = 0;
122 int cursor_ = 0;
123 Random rnd_;
124 };
125
126 namespace {} // namespace
127
128 TEST_F(DBBenchTest, OptionsFile) {
129 const std::string kOptionsFileName = test_path_ + "/OPTIONS_test";
130 Options opt = GetDefaultOptions();
131 ASSERT_OK(PersistRocksDBOptions(DBOptions(opt), {"default"},
132 {ColumnFamilyOptions()}, kOptionsFileName,
133 fs_.get()));
134
135 // override the following options as db_bench will not take these
136 // options from the options file
137 opt.wal_dir = wal_path_;
138
139 RunDbBench(kOptionsFileName);
140 opt.delayed_write_rate = 16 * 1024 * 1024; // Set by SanitizeOptions
141
142 VerifyOptions(opt);
143 }
144
145 TEST_F(DBBenchTest, OptionsFileUniversal) {
146 const std::string kOptionsFileName = test_path_ + "/OPTIONS_test";
147
148 Options opt = GetDefaultOptions(kCompactionStyleUniversal, 1);
149
150 ASSERT_OK(PersistRocksDBOptions(DBOptions(opt), {"default"},
151 {ColumnFamilyOptions(opt)}, kOptionsFileName,
152 fs_.get()));
153
154 // override the following options as db_bench will not take these
155 // options from the options file
156 opt.wal_dir = wal_path_;
157 RunDbBench(kOptionsFileName);
158
159 VerifyOptions(opt);
160 }
161
162 TEST_F(DBBenchTest, OptionsFileMultiLevelUniversal) {
163 const std::string kOptionsFileName = test_path_ + "/OPTIONS_test";
164
165 Options opt = GetDefaultOptions(kCompactionStyleUniversal, 12);
166
167 ASSERT_OK(PersistRocksDBOptions(DBOptions(opt), {"default"},
168 {ColumnFamilyOptions(opt)}, kOptionsFileName,
169 fs_.get()));
170
171 // override the following options as db_bench will not take these
172 // options from the options file
173 opt.wal_dir = wal_path_;
174
175 RunDbBench(kOptionsFileName);
176 VerifyOptions(opt);
177 }
178
179 const std::string options_file_content = R"OPTIONS_FILE(
180 [Version]
181 rocksdb_version=4.3.1
182 options_file_version=1.1
183
184 [DBOptions]
185 wal_bytes_per_sync=1048576
186 delete_obsolete_files_period_micros=0
187 WAL_ttl_seconds=0
188 WAL_size_limit_MB=0
189 db_write_buffer_size=0
190 max_subcompactions=1
191 table_cache_numshardbits=4
192 max_open_files=-1
193 max_file_opening_threads=10
194 max_background_compactions=5
195 use_fsync=false
196 use_adaptive_mutex=false
197 max_total_wal_size=18446744073709551615
198 compaction_readahead_size=0
199 new_table_reader_for_compaction_inputs=false
200 keep_log_file_num=10
201 skip_stats_update_on_db_open=false
202 max_manifest_file_size=18446744073709551615
203 db_log_dir=
204 skip_log_error_on_recovery=false
205 writable_file_max_buffer_size=1048576
206 paranoid_checks=true
207 is_fd_close_on_exec=true
208 bytes_per_sync=1048576
209 enable_thread_tracking=true
210 recycle_log_file_num=0
211 create_missing_column_families=false
212 log_file_time_to_roll=0
213 max_background_flushes=1
214 create_if_missing=true
215 error_if_exists=false
216 delayed_write_rate=1048576
217 manifest_preallocation_size=4194304
218 allow_mmap_reads=false
219 allow_mmap_writes=false
220 use_direct_reads=false
221 use_direct_io_for_flush_and_compaction=false
222 stats_dump_period_sec=600
223 allow_fallocate=true
224 max_log_file_size=83886080
225 random_access_max_buffer_size=1048576
226 advise_random_on_open=true
227 dump_malloc_stats=true
228
229 [CFOptions "default"]
230 compaction_filter_factory=nullptr
231 table_factory=BlockBasedTable
232 prefix_extractor=nullptr
233 comparator=leveldb.BytewiseComparator
234 compression_per_level=
235 max_bytes_for_level_base=104857600
236 bloom_locality=0
237 target_file_size_base=10485760
238 memtable_huge_page_size=0
239 max_successive_merges=1000
240 max_sequential_skip_in_iterations=8
241 arena_block_size=52428800
242 target_file_size_multiplier=1
243 source_compaction_factor=1
244 min_write_buffer_number_to_merge=1
245 max_write_buffer_number=2
246 write_buffer_size=419430400
247 max_grandparent_overlap_factor=10
248 max_bytes_for_level_multiplier=10
249 memtable_factory=SkipListFactory
250 compression=kNoCompression
251 min_partial_merge_operands=2
252 level0_stop_writes_trigger=100
253 num_levels=1
254 level0_slowdown_writes_trigger=50
255 level0_file_num_compaction_trigger=10
256 expanded_compaction_factor=25
257 soft_rate_limit=0.000000
258 max_write_buffer_number_to_maintain=0
259 max_write_buffer_size_to_maintain=0
260 verify_checksums_in_compaction=true
261 merge_operator=nullptr
262 memtable_prefix_bloom_bits=0
263 memtable_whole_key_filtering=true
264 paranoid_file_checks=false
265 inplace_update_num_locks=10000
266 optimize_filters_for_hits=false
267 level_compaction_dynamic_level_bytes=false
268 inplace_update_support=false
269 compaction_style=kCompactionStyleUniversal
270 memtable_prefix_bloom_probes=6
271 purge_redundant_kvs_while_flush=true
272 filter_deletes=false
273 hard_pending_compaction_bytes_limit=0
274 disable_auto_compactions=false
275 compaction_measure_io_stats=false
276
277 [TableOptions/BlockBasedTable "default"]
278 format_version=0
279 skip_table_builder_flush=false
280 cache_index_and_filter_blocks=false
281 flush_block_policy_factory=FlushBlockBySizePolicyFactory
282 hash_index_allow_collision=true
283 index_type=kBinarySearch
284 whole_key_filtering=true
285 checksum=kCRC32c
286 no_block_cache=false
287 block_size=32768
288 block_size_deviation=10
289 block_restart_interval=16
290 filter_policy=rocksdb.BuiltinBloomFilter
291 )OPTIONS_FILE";
292
293 TEST_F(DBBenchTest, OptionsFileFromFile) {
294 const std::string kOptionsFileName = test_path_ + "/OPTIONS_flash";
295 std::unique_ptr<WritableFile> writable;
296 ASSERT_OK(Env::Default()->NewWritableFile(kOptionsFileName, &writable,
297 EnvOptions()));
298 ASSERT_OK(writable->Append(options_file_content));
299 ASSERT_OK(writable->Close());
300
301 DBOptions db_opt;
302 std::vector<ColumnFamilyDescriptor> cf_descs;
303 ASSERT_OK(LoadOptionsFromFile(kOptionsFileName, Env::Default(), &db_opt,
304 &cf_descs));
305 Options opt(db_opt, cf_descs[0].options);
306 opt.create_if_missing = true;
307
308 // override the following options as db_bench will not take these
309 // options from the options file
310 opt.wal_dir = wal_path_;
311
312 RunDbBench(kOptionsFileName);
313
314 VerifyOptions(SanitizeOptions(db_path_, opt));
315 }
316
317 } // namespace ROCKSDB_NAMESPACE
318
319 int main(int argc, char** argv) {
320 ::testing::InitGoogleTest(&argc, argv);
321 google::ParseCommandLineFlags(&argc, &argv, true);
322 return RUN_ALL_TESTS();
323 }
324
325 #else
326
327 int main(int argc, char** argv) {
328 printf("Skip db_bench_tool_test as the required library GFLAG is missing.");
329 }
330 #endif // #ifdef GFLAGS