From b70967aac75aad7bb664cac0426c746bc4e408e9 Mon Sep 17 00:00:00 2001 From: Yi Wu Date: Mon, 15 Apr 2019 10:49:47 -0700 Subject: [PATCH] db_bench: support seek to non-exist prefix (#5163) Summary: Add `--seek_missing_prefix` flag to db_bench to allow benchmarking seeking to non-existing prefix. Usage example: ``` ./db_bench --db=/dev/shm/db_bench --use_existing_db=false --benchmarks=fillrandom --num=100000000 --prefix_size=9 --keys_per_prefix=10 ./db_bench --db=/dev/shm/db_bench --use_existing_db=true --benchmarks=seekrandom --disable_auto_compactions=true --num=100000000 --prefix_size=9 --keys_per_prefix=10 --reads=1000 --prefix_same_as_start=true --seek_missing_prefix=true ``` Also adding `--total_order_seek` and `--prefix_same_as_start` flags. Pull Request resolved: https://github.com/facebook/rocksdb/pull/5163 Differential Revision: D14935724 Pulled By: riversand963 fbshipit-source-id: 7c41023f007febe373eb1589861f215432a9e18a --- tools/db_bench_tool.cc | 30 +++++++++++++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/tools/db_bench_tool.cc b/tools/db_bench_tool.cc index 77d54fcfa..2b2289405 100644 --- a/tools/db_bench_tool.cc +++ b/tools/db_bench_tool.cc @@ -1090,11 +1090,20 @@ static bool ValidatePrefixSize(const char* flagname, int32_t value) { } return true; } + DEFINE_int32(prefix_size, 0, "control the prefix size for HashSkipList and " "plain table"); DEFINE_int64(keys_per_prefix, 0, "control average number of keys generated " "per prefix, 0 means no special handling of the prefix, " "i.e. use the prefix comes with the generated random number."); +DEFINE_bool(total_order_seek, false, + "Enable total order seek regardless of index format."); +DEFINE_bool(prefix_same_as_start, false, + "Enforce iterator to return keys with prefix same as seek key."); +DEFINE_bool( + seek_missing_prefix, false, + "Iterator seek to keys with non-exist prefixes. Require prefix_size > 8"); + DEFINE_int32(memtable_insert_with_hint_prefix_size, 0, "If non-zero, enable " "memtable insert with hint with the given prefix size."); @@ -2529,6 +2538,17 @@ class Benchmark { } } + void GenerateKeyFromIntForSeek(uint64_t v, int64_t num_keys, Slice* key) { + GenerateKeyFromInt(v, num_keys, key); + if (FLAGS_seek_missing_prefix) { + assert(prefix_size_ > 8); + char* key_ptr = const_cast(key->data()); + // This rely on GenerateKeyFromInt filling paddings with '0's. + // Putting a '1' will create a non-existing prefix. + key_ptr[8] = '1'; + } + } + std::string GetPathForMultiple(std::string base_name, size_t id) { if (!base_name.empty()) { #ifndef OS_WIN @@ -4964,6 +4984,8 @@ void VerifyDBFromDB(std::string& truth_db_name) { int64_t found = 0; int64_t bytes = 0; ReadOptions options(FLAGS_verify_checksum, true); + options.total_order_seek = FLAGS_total_order_seek; + options.prefix_same_as_start = FLAGS_prefix_same_as_start; options.tailing = FLAGS_use_tailing_iterator; Iterator* single_iter = nullptr; @@ -4988,7 +5010,8 @@ void VerifyDBFromDB(std::string& truth_db_name) { char value_buffer[256]; while (!duration.Done(1)) { int64_t seek_pos = thread->rand.Next() % FLAGS_num; - GenerateKeyFromInt((uint64_t)seek_pos, FLAGS_num, &key); + GenerateKeyFromIntForSeek(static_cast(seek_pos), FLAGS_num, + &key); if (FLAGS_max_scan_distance != 0) { if (FLAGS_reverse_iterator) { GenerateKeyFromInt( @@ -6256,6 +6279,11 @@ int db_bench_tool(int argc, char** argv) { FLAGS_stats_interval = 1000; } + if (FLAGS_seek_missing_prefix && FLAGS_prefix_size <= 8) { + fprintf(stderr, "prefix_size > 8 required by --seek_missing_prefix\n"); + exit(1); + } + rocksdb::Benchmark benchmark; benchmark.Run();