reader_common.cc 2.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364
  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. #include "table/block_based/reader_common.h"
  10. #include "monitoring/perf_context_imp.h"
  11. #include "rocksdb/table.h"
  12. #include "table/format.h"
  13. #include "util/coding.h"
  14. #include "util/crc32c.h"
  15. #include "util/string_util.h"
  16. namespace ROCKSDB_NAMESPACE {
  17. void ForceReleaseCachedEntry(void* arg, void* h) {
  18. Cache* cache = static_cast<Cache*>(arg);
  19. Cache::Handle* handle = static_cast<Cache::Handle*>(h);
  20. cache->Release(handle, true /* erase_if_last_ref */);
  21. }
  22. // WART: this is specific to block-based table
  23. Status VerifyBlockChecksum(const Footer& footer, const char* data,
  24. size_t block_size, const std::string& file_name,
  25. uint64_t offset) {
  26. PERF_TIMER_GUARD(block_checksum_time);
  27. assert(footer.GetBlockTrailerSize() == 5);
  28. ChecksumType type = footer.checksum_type();
  29. // After block_size bytes is compression type (1 byte), which is part of
  30. // the checksummed section.
  31. size_t len = block_size + 1;
  32. // And then the stored checksum value (4 bytes).
  33. uint32_t stored = DecodeFixed32(data + len);
  34. uint32_t computed = ComputeBuiltinChecksum(type, data, len);
  35. // Unapply context to 'stored' rather than apply to 'computed, for people
  36. // who might look for reference crc value in error message
  37. uint32_t modifier =
  38. ChecksumModifierForContext(footer.base_context_checksum(), offset);
  39. stored -= modifier;
  40. if (stored == computed) {
  41. return Status::OK();
  42. } else {
  43. // Unmask for people who might look for reference crc value
  44. if (type == kCRC32c) {
  45. stored = crc32c::Unmask(stored);
  46. computed = crc32c::Unmask(computed);
  47. }
  48. return Status::Corruption(
  49. "block checksum mismatch: stored" +
  50. std::string(modifier ? "(context removed)" : "") + " = " +
  51. std::to_string(stored) + ", computed = " + std::to_string(computed) +
  52. ", type = " + std::to_string(type) + " in " + file_name + " offset " +
  53. std::to_string(offset) + " size " + std::to_string(block_size));
  54. }
  55. }
  56. } // namespace ROCKSDB_NAMESPACE