]> git.proxmox.com Git - ceph.git/blame - ceph/src/rocksdb/utilities/simulator_cache/cache_simulator_test.cc
update ceph source to reef 18.1.2
[ceph.git] / ceph / src / rocksdb / utilities / simulator_cache / cache_simulator_test.cc
CommitLineData
f67539c2
TL
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#include "utilities/simulator_cache/cache_simulator.h"
7
8#include <cstdlib>
1e59de90 9
f67539c2 10#include "rocksdb/env.h"
1e59de90 11#include "rocksdb/trace_record.h"
f67539c2
TL
12#include "test_util/testharness.h"
13#include "test_util/testutil.h"
14
15namespace ROCKSDB_NAMESPACE {
16namespace {
17const std::string kBlockKeyPrefix = "test-block-";
18const std::string kRefKeyPrefix = "test-get-";
19const std::string kRefKeySequenceNumber = std::string(8, 'c');
20const uint64_t kGetId = 1;
21const uint64_t kGetBlockId = 100;
22const uint64_t kCompactionBlockId = 1000;
23const uint64_t kCacheSize = 1024 * 1024 * 1024;
24const uint64_t kGhostCacheSize = 1024 * 1024;
25} // namespace
26
27class CacheSimulatorTest : public testing::Test {
28 public:
29 const size_t kNumBlocks = 5;
30 const size_t kValueSize = 1000;
31
32 CacheSimulatorTest() { env_ = ROCKSDB_NAMESPACE::Env::Default(); }
33
34 BlockCacheTraceRecord GenerateGetRecord(uint64_t getid) {
35 BlockCacheTraceRecord record;
36 record.block_type = TraceType::kBlockTraceDataBlock;
37 record.block_size = 4096;
38 record.block_key = kBlockKeyPrefix + std::to_string(kGetBlockId);
39 record.access_timestamp = env_->NowMicros();
40 record.cf_id = 0;
41 record.cf_name = "test";
42 record.caller = TableReaderCaller::kUserGet;
43 record.level = 6;
44 record.sst_fd_number = 0;
45 record.get_id = getid;
1e59de90
TL
46 record.is_cache_hit = false;
47 record.no_insert = false;
f67539c2
TL
48 record.referenced_key =
49 kRefKeyPrefix + std::to_string(kGetId) + kRefKeySequenceNumber;
1e59de90 50 record.referenced_key_exist_in_block = true;
f67539c2
TL
51 record.referenced_data_size = 100;
52 record.num_keys_in_block = 300;
53 return record;
54 }
55
56 BlockCacheTraceRecord GenerateCompactionRecord() {
57 BlockCacheTraceRecord record;
58 record.block_type = TraceType::kBlockTraceDataBlock;
59 record.block_size = 4096;
60 record.block_key = kBlockKeyPrefix + std::to_string(kCompactionBlockId);
61 record.access_timestamp = env_->NowMicros();
62 record.cf_id = 0;
63 record.cf_name = "test";
64 record.caller = TableReaderCaller::kCompaction;
65 record.level = 6;
66 record.sst_fd_number = kCompactionBlockId;
1e59de90
TL
67 record.is_cache_hit = false;
68 record.no_insert = true;
f67539c2
TL
69 return record;
70 }
71
72 void AssertCache(std::shared_ptr<Cache> sim_cache,
73 const MissRatioStats& miss_ratio_stats,
74 uint64_t expected_usage, uint64_t expected_num_accesses,
75 uint64_t expected_num_misses,
76 std::vector<std::string> blocks,
77 std::vector<std::string> keys) {
78 EXPECT_EQ(expected_usage, sim_cache->GetUsage());
79 EXPECT_EQ(expected_num_accesses, miss_ratio_stats.total_accesses());
80 EXPECT_EQ(expected_num_misses, miss_ratio_stats.total_misses());
81 for (auto const& block : blocks) {
82 auto handle = sim_cache->Lookup(block);
83 EXPECT_NE(nullptr, handle);
84 sim_cache->Release(handle);
85 }
86 for (auto const& key : keys) {
87 std::string row_key = kRefKeyPrefix + key + kRefKeySequenceNumber;
88 auto handle =
89 sim_cache->Lookup("0_" + ExtractUserKey(row_key).ToString());
90 EXPECT_NE(nullptr, handle);
91 sim_cache->Release(handle);
92 }
93 }
94
95 Env* env_;
96};
97
98TEST_F(CacheSimulatorTest, GhostCache) {
99 const std::string key1 = "test1";
100 const std::string key2 = "test2";
101 std::unique_ptr<GhostCache> ghost_cache(new GhostCache(
102 NewLRUCache(/*capacity=*/kGhostCacheSize, /*num_shard_bits=*/1,
103 /*strict_capacity_limit=*/false,
104 /*high_pri_pool_ratio=*/0)));
105 EXPECT_FALSE(ghost_cache->Admit(key1));
106 EXPECT_TRUE(ghost_cache->Admit(key1));
107 EXPECT_TRUE(ghost_cache->Admit(key1));
108 EXPECT_FALSE(ghost_cache->Admit(key2));
109 EXPECT_TRUE(ghost_cache->Admit(key2));
110}
111
112TEST_F(CacheSimulatorTest, CacheSimulator) {
113 const BlockCacheTraceRecord& access = GenerateGetRecord(kGetId);
114 const BlockCacheTraceRecord& compaction_access = GenerateCompactionRecord();
115 std::shared_ptr<Cache> sim_cache =
116 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
117 /*strict_capacity_limit=*/false,
118 /*high_pri_pool_ratio=*/0);
119 std::unique_ptr<CacheSimulator> cache_simulator(
120 new CacheSimulator(nullptr, sim_cache));
121 cache_simulator->Access(access);
122 cache_simulator->Access(access);
123 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().total_accesses());
124 ASSERT_EQ(50, cache_simulator->miss_ratio_stats().miss_ratio());
125 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().user_accesses());
126 ASSERT_EQ(50, cache_simulator->miss_ratio_stats().user_miss_ratio());
127
128 cache_simulator->Access(compaction_access);
129 cache_simulator->Access(compaction_access);
130 ASSERT_EQ(4, cache_simulator->miss_ratio_stats().total_accesses());
131 ASSERT_EQ(75, cache_simulator->miss_ratio_stats().miss_ratio());
132 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().user_accesses());
133 ASSERT_EQ(50, cache_simulator->miss_ratio_stats().user_miss_ratio());
134
135 cache_simulator->reset_counter();
136 ASSERT_EQ(0, cache_simulator->miss_ratio_stats().total_accesses());
137 ASSERT_EQ(-1, cache_simulator->miss_ratio_stats().miss_ratio());
138 auto handle = sim_cache->Lookup(access.block_key);
139 ASSERT_NE(nullptr, handle);
140 sim_cache->Release(handle);
141 handle = sim_cache->Lookup(compaction_access.block_key);
142 ASSERT_EQ(nullptr, handle);
143}
144
145TEST_F(CacheSimulatorTest, GhostCacheSimulator) {
146 const BlockCacheTraceRecord& access = GenerateGetRecord(kGetId);
147 std::unique_ptr<GhostCache> ghost_cache(new GhostCache(
148 NewLRUCache(/*capacity=*/kGhostCacheSize, /*num_shard_bits=*/1,
149 /*strict_capacity_limit=*/false,
150 /*high_pri_pool_ratio=*/0)));
151 std::unique_ptr<CacheSimulator> cache_simulator(new CacheSimulator(
152 std::move(ghost_cache),
153 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
154 /*strict_capacity_limit=*/false,
155 /*high_pri_pool_ratio=*/0)));
156 cache_simulator->Access(access);
157 cache_simulator->Access(access);
158 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().total_accesses());
159 // Both of them will be miss since we have a ghost cache.
160 ASSERT_EQ(100, cache_simulator->miss_ratio_stats().miss_ratio());
161}
162
163TEST_F(CacheSimulatorTest, PrioritizedCacheSimulator) {
164 const BlockCacheTraceRecord& access = GenerateGetRecord(kGetId);
165 std::shared_ptr<Cache> sim_cache =
166 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
167 /*strict_capacity_limit=*/false,
168 /*high_pri_pool_ratio=*/0);
169 std::unique_ptr<PrioritizedCacheSimulator> cache_simulator(
170 new PrioritizedCacheSimulator(nullptr, sim_cache));
171 cache_simulator->Access(access);
172 cache_simulator->Access(access);
173 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().total_accesses());
174 ASSERT_EQ(50, cache_simulator->miss_ratio_stats().miss_ratio());
175
176 auto handle = sim_cache->Lookup(access.block_key);
177 ASSERT_NE(nullptr, handle);
178 sim_cache->Release(handle);
179}
180
181TEST_F(CacheSimulatorTest, GhostPrioritizedCacheSimulator) {
182 const BlockCacheTraceRecord& access = GenerateGetRecord(kGetId);
183 std::unique_ptr<GhostCache> ghost_cache(new GhostCache(
184 NewLRUCache(/*capacity=*/kGhostCacheSize, /*num_shard_bits=*/1,
185 /*strict_capacity_limit=*/false,
186 /*high_pri_pool_ratio=*/0)));
187 std::unique_ptr<PrioritizedCacheSimulator> cache_simulator(
188 new PrioritizedCacheSimulator(
189 std::move(ghost_cache),
190 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
191 /*strict_capacity_limit=*/false,
192 /*high_pri_pool_ratio=*/0)));
193 cache_simulator->Access(access);
194 cache_simulator->Access(access);
195 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().total_accesses());
196 // Both of them will be miss since we have a ghost cache.
197 ASSERT_EQ(100, cache_simulator->miss_ratio_stats().miss_ratio());
198}
199
200TEST_F(CacheSimulatorTest, HybridRowBlockCacheSimulator) {
201 uint64_t block_id = 100;
202 BlockCacheTraceRecord first_get = GenerateGetRecord(kGetId);
1e59de90 203 first_get.get_from_user_specified_snapshot = true;
f67539c2
TL
204 BlockCacheTraceRecord second_get = GenerateGetRecord(kGetId + 1);
205 second_get.referenced_data_size = 0;
1e59de90
TL
206 second_get.referenced_key_exist_in_block = false;
207 second_get.get_from_user_specified_snapshot = true;
f67539c2
TL
208 BlockCacheTraceRecord third_get = GenerateGetRecord(kGetId + 2);
209 third_get.referenced_data_size = 0;
1e59de90 210 third_get.referenced_key_exist_in_block = false;
f67539c2
TL
211 third_get.referenced_key = kRefKeyPrefix + "third_get";
212 // We didn't find the referenced key in the third get.
1e59de90 213 third_get.referenced_key_exist_in_block = false;
f67539c2
TL
214 third_get.referenced_data_size = 0;
215 std::shared_ptr<Cache> sim_cache =
216 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
217 /*strict_capacity_limit=*/false,
218 /*high_pri_pool_ratio=*/0);
219 std::unique_ptr<HybridRowBlockCacheSimulator> cache_simulator(
220 new HybridRowBlockCacheSimulator(
221 nullptr, sim_cache, /*insert_blocks_row_kvpair_misses=*/true));
222 // The first get request accesses 10 blocks. We should only report 10 accesses
223 // and 100% miss.
224 for (uint32_t i = 0; i < 10; i++) {
225 first_get.block_key = kBlockKeyPrefix + std::to_string(block_id);
226 cache_simulator->Access(first_get);
227 block_id++;
228 }
229
230 ASSERT_EQ(10, cache_simulator->miss_ratio_stats().total_accesses());
231 ASSERT_EQ(100, cache_simulator->miss_ratio_stats().miss_ratio());
232 ASSERT_EQ(10, cache_simulator->miss_ratio_stats().user_accesses());
233 ASSERT_EQ(100, cache_simulator->miss_ratio_stats().user_miss_ratio());
234 auto handle =
235 sim_cache->Lookup(std::to_string(first_get.sst_fd_number) + "_" +
236 ExtractUserKey(first_get.referenced_key).ToString());
237 ASSERT_NE(nullptr, handle);
238 sim_cache->Release(handle);
239 for (uint32_t i = 100; i < block_id; i++) {
240 handle = sim_cache->Lookup(kBlockKeyPrefix + std::to_string(i));
241 ASSERT_NE(nullptr, handle);
242 sim_cache->Release(handle);
243 }
244
245 // The second get request accesses the same key. We should report 15
246 // access and 66% miss, 10 misses with 15 accesses.
247 // We do not consider these 5 block lookups as misses since the row hits the
248 // cache.
249 for (uint32_t i = 0; i < 5; i++) {
250 second_get.block_key = kBlockKeyPrefix + std::to_string(block_id);
251 cache_simulator->Access(second_get);
252 block_id++;
253 }
254 ASSERT_EQ(15, cache_simulator->miss_ratio_stats().total_accesses());
255 ASSERT_EQ(66, static_cast<uint64_t>(
256 cache_simulator->miss_ratio_stats().miss_ratio()));
257 ASSERT_EQ(15, cache_simulator->miss_ratio_stats().user_accesses());
258 ASSERT_EQ(66, static_cast<uint64_t>(
259 cache_simulator->miss_ratio_stats().user_miss_ratio()));
260 handle =
261 sim_cache->Lookup(std::to_string(second_get.sst_fd_number) + "_" +
262 ExtractUserKey(second_get.referenced_key).ToString());
263 ASSERT_NE(nullptr, handle);
264 sim_cache->Release(handle);
265 for (uint32_t i = 100; i < block_id; i++) {
266 handle = sim_cache->Lookup(kBlockKeyPrefix + std::to_string(i));
267 if (i < 110) {
268 ASSERT_NE(nullptr, handle) << i;
269 sim_cache->Release(handle);
270 } else {
271 ASSERT_EQ(nullptr, handle) << i;
272 }
273 }
274
275 // The third get on a different key and does not have a size.
276 // This key should not be inserted into the cache.
277 for (uint32_t i = 0; i < 5; i++) {
278 third_get.block_key = kBlockKeyPrefix + std::to_string(block_id);
279 cache_simulator->Access(third_get);
280 block_id++;
281 }
282 ASSERT_EQ(20, cache_simulator->miss_ratio_stats().total_accesses());
283 ASSERT_EQ(75, static_cast<uint64_t>(
284 cache_simulator->miss_ratio_stats().miss_ratio()));
285 ASSERT_EQ(20, cache_simulator->miss_ratio_stats().user_accesses());
286 ASSERT_EQ(75, static_cast<uint64_t>(
287 cache_simulator->miss_ratio_stats().user_miss_ratio()));
288 // Assert that the third key is not inserted into the cache.
289 handle = sim_cache->Lookup(std::to_string(third_get.sst_fd_number) + "_" +
290 third_get.referenced_key);
291 ASSERT_EQ(nullptr, handle);
292 for (uint32_t i = 100; i < block_id; i++) {
293 if (i < 110 || i >= 115) {
294 handle = sim_cache->Lookup(kBlockKeyPrefix + std::to_string(i));
295 ASSERT_NE(nullptr, handle) << i;
296 sim_cache->Release(handle);
297 } else {
298 handle = sim_cache->Lookup(kBlockKeyPrefix + std::to_string(i));
299 ASSERT_EQ(nullptr, handle) << i;
300 }
301 }
302}
303
304TEST_F(CacheSimulatorTest, HybridRowBlockCacheSimulatorGetTest) {
305 BlockCacheTraceRecord get = GenerateGetRecord(kGetId);
306 get.block_size = 1;
307 get.referenced_data_size = 0;
308 get.access_timestamp = 0;
309 get.block_key = "1";
310 get.get_id = 1;
1e59de90 311 get.get_from_user_specified_snapshot = false;
f67539c2
TL
312 get.referenced_key =
313 kRefKeyPrefix + std::to_string(1) + kRefKeySequenceNumber;
1e59de90 314 get.no_insert = false;
f67539c2 315 get.sst_fd_number = 0;
1e59de90 316 get.get_from_user_specified_snapshot = false;
f67539c2
TL
317
318 LRUCacheOptions co;
319 co.capacity = 16;
320 co.num_shard_bits = 1;
321 co.strict_capacity_limit = false;
322 co.high_pri_pool_ratio = 0;
323 co.metadata_charge_policy = kDontChargeCacheMetadata;
324 std::shared_ptr<Cache> sim_cache = NewLRUCache(co);
325 std::unique_ptr<HybridRowBlockCacheSimulator> cache_simulator(
326 new HybridRowBlockCacheSimulator(
327 nullptr, sim_cache, /*insert_blocks_row_kvpair_misses=*/true));
328 // Expect a miss and does not insert the row key-value pair since it does not
329 // have size.
330 cache_simulator->Access(get);
331 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 1, 1, 1, {"1"},
332 {});
333 get.access_timestamp += 1;
334 get.referenced_data_size = 1;
335 get.block_key = "2";
336 cache_simulator->Access(get);
337 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 3, 2, 2,
338 {"1", "2"}, {"1"});
339 get.access_timestamp += 1;
340 get.block_key = "3";
341 // K1 should not inserted again.
342 cache_simulator->Access(get);
343 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 4, 3, 3,
344 {"1", "2", "3"}, {"1"});
345
346 // A second get request referencing the same key.
347 get.access_timestamp += 1;
348 get.get_id = 2;
349 get.block_key = "4";
350 get.referenced_data_size = 0;
351 cache_simulator->Access(get);
352 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 4, 4, 3,
353 {"1", "2", "3"}, {"1"});
354
355 // A third get request searches three files, three different keys.
356 // And the second key observes a hit.
357 get.access_timestamp += 1;
358 get.referenced_data_size = 1;
359 get.get_id = 3;
360 get.block_key = "3";
361 get.referenced_key = kRefKeyPrefix + "2" + kRefKeySequenceNumber;
362 // K2 should observe a miss. Block 3 observes a hit.
363 cache_simulator->Access(get);
364 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 5, 5, 3,
365 {"1", "2", "3"}, {"1", "2"});
366
367 get.access_timestamp += 1;
368 get.referenced_data_size = 1;
369 get.get_id = 3;
370 get.block_key = "4";
371 get.referenced_data_size = 1;
372 get.referenced_key = kRefKeyPrefix + "1" + kRefKeySequenceNumber;
373 // K1 should observe a hit.
374 cache_simulator->Access(get);
375 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 5, 6, 3,
376 {"1", "2", "3"}, {"1", "2"});
377
378 get.access_timestamp += 1;
379 get.referenced_data_size = 1;
380 get.get_id = 3;
381 get.block_key = "4";
382 get.referenced_data_size = 1;
383 get.referenced_key = kRefKeyPrefix + "3" + kRefKeySequenceNumber;
384 // K3 should observe a miss.
385 // However, as the get already complete, we should not access k3 any more.
386 cache_simulator->Access(get);
387 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 5, 7, 3,
388 {"1", "2", "3"}, {"1", "2"});
389
390 // A fourth get request searches one file and two blocks. One row key.
391 get.access_timestamp += 1;
392 get.get_id = 4;
393 get.block_key = "5";
394 get.referenced_key = kRefKeyPrefix + "4" + kRefKeySequenceNumber;
395 get.referenced_data_size = 1;
396 cache_simulator->Access(get);
397 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 7, 8, 4,
398 {"1", "2", "3", "5"}, {"1", "2", "4"});
399 for (auto const& key : {"1", "2", "4"}) {
400 auto handle = sim_cache->Lookup("0_" + kRefKeyPrefix + key);
401 ASSERT_NE(nullptr, handle);
402 sim_cache->Release(handle);
403 }
404
405 // A bunch of insertions which evict cached row keys.
406 for (uint32_t i = 6; i < 100; i++) {
407 get.access_timestamp += 1;
408 get.get_id = 0;
409 get.block_key = std::to_string(i);
410 cache_simulator->Access(get);
411 }
412
413 get.get_id = 4;
414 // A different block.
415 get.block_key = "100";
416 // Same row key and should not be inserted again.
417 get.referenced_key = kRefKeyPrefix + "4" + kRefKeySequenceNumber;
418 get.referenced_data_size = 1;
419 cache_simulator->Access(get);
420 AssertCache(sim_cache, cache_simulator->miss_ratio_stats(), 16, 103, 99, {},
421 {});
422 for (auto const& key : {"1", "2", "4"}) {
423 auto handle = sim_cache->Lookup("0_" + kRefKeyPrefix + key);
424 ASSERT_EQ(nullptr, handle);
425 }
426}
427
428TEST_F(CacheSimulatorTest, HybridRowBlockNoInsertCacheSimulator) {
429 uint64_t block_id = 100;
430 BlockCacheTraceRecord first_get = GenerateGetRecord(kGetId);
431 std::shared_ptr<Cache> sim_cache =
432 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
433 /*strict_capacity_limit=*/false,
434 /*high_pri_pool_ratio=*/0);
435 std::unique_ptr<HybridRowBlockCacheSimulator> cache_simulator(
436 new HybridRowBlockCacheSimulator(
437 nullptr, sim_cache, /*insert_blocks_row_kvpair_misses=*/false));
438 for (uint32_t i = 0; i < 9; i++) {
439 first_get.block_key = kBlockKeyPrefix + std::to_string(block_id);
440 cache_simulator->Access(first_get);
441 block_id++;
442 }
443 auto handle =
444 sim_cache->Lookup(std::to_string(first_get.sst_fd_number) + "_" +
445 ExtractUserKey(first_get.referenced_key).ToString());
446 ASSERT_NE(nullptr, handle);
447 sim_cache->Release(handle);
448 // All blocks are missing from the cache since insert_blocks_row_kvpair_misses
449 // is set to false.
450 for (uint32_t i = 100; i < block_id; i++) {
451 handle = sim_cache->Lookup(kBlockKeyPrefix + std::to_string(i));
452 ASSERT_EQ(nullptr, handle);
453 }
454}
455
456TEST_F(CacheSimulatorTest, GhostHybridRowBlockCacheSimulator) {
457 std::unique_ptr<GhostCache> ghost_cache(new GhostCache(
458 NewLRUCache(/*capacity=*/kGhostCacheSize, /*num_shard_bits=*/1,
459 /*strict_capacity_limit=*/false,
460 /*high_pri_pool_ratio=*/0)));
461 const BlockCacheTraceRecord& first_get = GenerateGetRecord(kGetId);
462 const BlockCacheTraceRecord& second_get = GenerateGetRecord(kGetId + 1);
463 const BlockCacheTraceRecord& third_get = GenerateGetRecord(kGetId + 2);
464 std::unique_ptr<HybridRowBlockCacheSimulator> cache_simulator(
465 new HybridRowBlockCacheSimulator(
466 std::move(ghost_cache),
467 NewLRUCache(/*capacity=*/kCacheSize, /*num_shard_bits=*/1,
468 /*strict_capacity_limit=*/false,
469 /*high_pri_pool_ratio=*/0),
470 /*insert_blocks_row_kvpair_misses=*/false));
471 // Two get requests access the same key.
472 cache_simulator->Access(first_get);
473 cache_simulator->Access(second_get);
474 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().total_accesses());
475 ASSERT_EQ(100, cache_simulator->miss_ratio_stats().miss_ratio());
476 ASSERT_EQ(2, cache_simulator->miss_ratio_stats().user_accesses());
477 ASSERT_EQ(100, cache_simulator->miss_ratio_stats().user_miss_ratio());
478 // We insert the key-value pair upon the second get request. A third get
479 // request should observe a hit.
480 for (uint32_t i = 0; i < 10; i++) {
481 cache_simulator->Access(third_get);
482 }
483 ASSERT_EQ(12, cache_simulator->miss_ratio_stats().total_accesses());
484 ASSERT_EQ(16, static_cast<uint64_t>(
485 cache_simulator->miss_ratio_stats().miss_ratio()));
486 ASSERT_EQ(12, cache_simulator->miss_ratio_stats().user_accesses());
487 ASSERT_EQ(16, static_cast<uint64_t>(
488 cache_simulator->miss_ratio_stats().user_miss_ratio()));
489}
490
491} // namespace ROCKSDB_NAMESPACE
492
493int main(int argc, char** argv) {
1e59de90 494 ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
f67539c2
TL
495 ::testing::InitGoogleTest(&argc, argv);
496 return RUN_ALL_TESTS();
497}