blob_file_cache.cc 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111
  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. #include "db/blob/blob_file_cache.h"
  6. #include <cassert>
  7. #include <memory>
  8. #include "db/blob/blob_file_reader.h"
  9. #include "options/cf_options.h"
  10. #include "rocksdb/cache.h"
  11. #include "rocksdb/slice.h"
  12. #include "test_util/sync_point.h"
  13. #include "trace_replay/io_tracer.h"
  14. #include "util/hash.h"
  15. namespace ROCKSDB_NAMESPACE {
  16. BlobFileCache::BlobFileCache(Cache* cache,
  17. const ImmutableOptions* immutable_options,
  18. const FileOptions* file_options,
  19. uint32_t column_family_id,
  20. HistogramImpl* blob_file_read_hist,
  21. const std::shared_ptr<IOTracer>& io_tracer)
  22. : cache_(cache),
  23. mutex_(kNumberOfMutexStripes),
  24. immutable_options_(immutable_options),
  25. file_options_(file_options),
  26. column_family_id_(column_family_id),
  27. blob_file_read_hist_(blob_file_read_hist),
  28. io_tracer_(io_tracer) {
  29. assert(cache_);
  30. assert(immutable_options_);
  31. assert(file_options_);
  32. }
  33. Status BlobFileCache::GetBlobFileReader(
  34. const ReadOptions& read_options, uint64_t blob_file_number,
  35. CacheHandleGuard<BlobFileReader>* blob_file_reader) {
  36. assert(blob_file_reader);
  37. assert(blob_file_reader->IsEmpty());
  38. // NOTE: sharing same Cache with table_cache
  39. const Slice key = GetSliceForKey(&blob_file_number);
  40. assert(cache_);
  41. TypedHandle* handle = cache_.Lookup(key);
  42. if (handle) {
  43. *blob_file_reader = cache_.Guard(handle);
  44. return Status::OK();
  45. }
  46. TEST_SYNC_POINT("BlobFileCache::GetBlobFileReader:DoubleCheck");
  47. // Check again while holding mutex
  48. MutexLock lock(&mutex_.Get(key));
  49. handle = cache_.Lookup(key);
  50. if (handle) {
  51. *blob_file_reader = cache_.Guard(handle);
  52. return Status::OK();
  53. }
  54. assert(immutable_options_);
  55. Statistics* const statistics = immutable_options_->stats;
  56. RecordTick(statistics, NO_FILE_OPENS);
  57. std::unique_ptr<BlobFileReader> reader;
  58. {
  59. assert(file_options_);
  60. const Status s = BlobFileReader::Create(
  61. *immutable_options_, read_options, *file_options_, column_family_id_,
  62. blob_file_read_hist_, blob_file_number, io_tracer_, &reader);
  63. if (!s.ok()) {
  64. RecordTick(statistics, NO_FILE_ERRORS);
  65. return s;
  66. }
  67. }
  68. {
  69. constexpr size_t charge = 1;
  70. const Status s = cache_.Insert(key, reader.get(), charge, &handle);
  71. if (!s.ok()) {
  72. RecordTick(statistics, NO_FILE_ERRORS);
  73. return s;
  74. }
  75. }
  76. reader.release();
  77. *blob_file_reader = cache_.Guard(handle);
  78. return Status::OK();
  79. }
  80. void BlobFileCache::Evict(uint64_t blob_file_number) {
  81. // NOTE: sharing same Cache with table_cache
  82. const Slice key = GetSliceForKey(&blob_file_number);
  83. assert(cache_);
  84. cache_.get()->Erase(key);
  85. }
  86. } // namespace ROCKSDB_NAMESPACE