Commit 9a61fe16 authored by rvargas@google.com's avatar rvargas@google.com

Disk cache: Update Addr to handle file format version 3.

Basically three new file block types appear: One for normal
entries, one for deleted entries and one for keeping track
of external files.

BUG=241277
TEST=net_unittests
R=gavinp@chromium.org

Review URL: https://codereview.chromium.org/16837003

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@207870 0039d316-1c4b-4281-b951-d872f2087c98
parent bce6de46
...@@ -26,22 +26,35 @@ bool Addr::SetFileNumber(int file_number) { ...@@ -26,22 +26,35 @@ bool Addr::SetFileNumber(int file_number) {
return true; return true;
} }
bool Addr::SanityCheck() const { bool Addr::SanityCheckV2() const {
if (!is_initialized()) if (!is_initialized())
return !value_; return !value_;
if (((value_ & kFileTypeMask) >> kFileTypeOffset) > 4) if (file_type() > BLOCK_4K)
return false; return false;
if (is_separate_file()) if (is_separate_file())
return true; return true;
const uint32 kReservedBitsMask = 0x0c000000; return !reserved_bits();
return !(value_ & kReservedBitsMask); }
bool Addr::SanityCheckV3() const {
if (!is_initialized())
return !value_;
// For actual entries, SanityCheckForEntryV3 should be used.
if (file_type() > BLOCK_FILES)
return false;
if (is_separate_file())
return true;
return !reserved_bits();
} }
bool Addr::SanityCheckForEntryV2() const { bool Addr::SanityCheckForEntryV2() const {
if (!SanityCheck() || !is_initialized()) if (!SanityCheckV2() || !is_initialized())
return false; return false;
if (is_separate_file() || file_type() != BLOCK_256) if (is_separate_file() || file_type() != BLOCK_256)
...@@ -50,8 +63,24 @@ bool Addr::SanityCheckForEntryV2() const { ...@@ -50,8 +63,24 @@ bool Addr::SanityCheckForEntryV2() const {
return true; return true;
} }
bool Addr::SanityCheckForEntryV3() const {
if (!is_initialized())
return false;
if (reserved_bits())
return false;
if (file_type() != BLOCK_ENTRIES && file_type() != BLOCK_EVICTED)
return false;
if (num_blocks() != 1)
return false;
return true;
}
bool Addr::SanityCheckForRankings() const { bool Addr::SanityCheckForRankings() const {
if (!SanityCheck() || !is_initialized()) if (!SanityCheckV2() || !is_initialized())
return false; return false;
if (is_separate_file() || file_type() != RANKINGS || num_blocks() != 1) if (is_separate_file() || file_type() != RANKINGS || num_blocks() != 1)
......
...@@ -16,15 +16,19 @@ namespace disk_cache { ...@@ -16,15 +16,19 @@ namespace disk_cache {
enum FileType { enum FileType {
EXTERNAL = 0, EXTERNAL = 0,
RANKINGS = 1, RANKINGS = 1,
BLOCK_256, BLOCK_256 = 2,
BLOCK_1K, BLOCK_1K = 3,
BLOCK_4K, BLOCK_4K = 4,
BLOCK_FILES = 5,
BLOCK_ENTRIES = 6,
BLOCK_EVICTED = 7
}; };
const int kMaxBlockSize = 4096 * 4; const int kMaxBlockSize = 4096 * 4;
const int kMaxBlockFile = 255; const int kMaxBlockFile = 255;
const int kMaxNumBlocks = 4; const int kMaxNumBlocks = 4;
const int kFirstAdditionalBlockFile = 4; const int kFirstAdditionalBlockFile = 4;
const int kFirstAdditionalBlockFileV3 = 7;
// Defines a storage address for a cache record // Defines a storage address for a cache record
// //
...@@ -38,6 +42,9 @@ const int kFirstAdditionalBlockFile = 4; ...@@ -38,6 +42,9 @@ const int kFirstAdditionalBlockFile = 4;
// 2 = 256 byte block file // 2 = 256 byte block file
// 3 = 1k byte block file // 3 = 1k byte block file
// 4 = 4k byte block file // 4 = 4k byte block file
// 5 = external files block file
// 6 = active entries block file
// 7 = evicted entries block file
// //
// If separate file: // If separate file:
// 0000 1111 1111 1111 1111 1111 1111 1111 : file# 0 - 268,435,456 (2^28) // 0000 1111 1111 1111 1111 1111 1111 1111 : file# 0 - 268,435,456 (2^28)
...@@ -101,6 +108,14 @@ class NET_EXPORT_PRIVATE Addr { ...@@ -101,6 +108,14 @@ class NET_EXPORT_PRIVATE Addr {
return value_ != other.value_; return value_ != other.value_;
} }
static Addr FromEntryAddress(uint32 value) {
return Addr(kInitializedMask + (BLOCK_ENTRIES << kFileTypeOffset) + value);
}
static Addr FromEvictedAddress(uint32 value) {
return Addr(kInitializedMask + (BLOCK_EVICTED << kFileTypeOffset) + value);
}
static int BlockSizeForFileType(FileType file_type) { static int BlockSizeForFileType(FileType file_type) {
switch (file_type) { switch (file_type) {
case RANKINGS: case RANKINGS:
...@@ -111,6 +126,12 @@ class NET_EXPORT_PRIVATE Addr { ...@@ -111,6 +126,12 @@ class NET_EXPORT_PRIVATE Addr {
return 1024; return 1024;
case BLOCK_4K: case BLOCK_4K:
return 4096; return 4096;
case BLOCK_FILES:
return 8;
case BLOCK_ENTRIES:
return 104;
case BLOCK_EVICTED:
return 48;
default: default:
return 0; return 0;
} }
...@@ -133,14 +154,21 @@ class NET_EXPORT_PRIVATE Addr { ...@@ -133,14 +154,21 @@ class NET_EXPORT_PRIVATE Addr {
} }
// Returns true if this address looks like a valid one. // Returns true if this address looks like a valid one.
bool SanityCheck() const; bool SanityCheckV2() const;
bool SanityCheckV3() const;
bool SanityCheckForEntryV2() const; bool SanityCheckForEntryV2() const;
bool SanityCheckForEntryV3() const;
bool SanityCheckForRankings() const; bool SanityCheckForRankings() const;
private: private:
uint32 reserved_bits() const {
return value_ & kReservedBitsMask;
}
static const uint32 kInitializedMask = 0x80000000; static const uint32 kInitializedMask = 0x80000000;
static const uint32 kFileTypeMask = 0x70000000; static const uint32 kFileTypeMask = 0x70000000;
static const uint32 kFileTypeOffset = 28; static const uint32 kFileTypeOffset = 28;
static const uint32 kReservedBitsMask = 0x0c000000;
static const uint32 kNumBlocksMask = 0x03000000; static const uint32 kNumBlocksMask = 0x03000000;
static const uint32 kNumBlocksOffset = 24; static const uint32 kNumBlocksOffset = 24;
static const uint32 kFileSelectorMask = 0x00ff0000; static const uint32 kFileSelectorMask = 0x00ff0000;
......
...@@ -36,22 +36,24 @@ TEST_F(DiskCacheTest, CacheAddr_InvalidValues) { ...@@ -36,22 +36,24 @@ TEST_F(DiskCacheTest, CacheAddr_InvalidValues) {
TEST_F(DiskCacheTest, CacheAddr_SanityCheck) { TEST_F(DiskCacheTest, CacheAddr_SanityCheck) {
// First a few valid values. // First a few valid values.
EXPECT_TRUE(Addr(0).SanityCheck()); EXPECT_TRUE(Addr(0).SanityCheckV2());
EXPECT_TRUE(Addr(0x80001000).SanityCheck()); EXPECT_TRUE(Addr(0x80001000).SanityCheckV2());
EXPECT_TRUE(Addr(0xC3FFFFFF).SanityCheck()); EXPECT_TRUE(Addr(0xC3FFFFFF).SanityCheckV2());
EXPECT_TRUE(Addr(0xC0FFFFFF).SanityCheck()); EXPECT_TRUE(Addr(0xC0FFFFFF).SanityCheckV2());
EXPECT_TRUE(Addr(0xD0001000).SanityCheckV3());
// Not initialized. // Not initialized.
EXPECT_FALSE(Addr(0x20).SanityCheck()); EXPECT_FALSE(Addr(0x20).SanityCheckV2());
EXPECT_FALSE(Addr(0x10001000).SanityCheck()); EXPECT_FALSE(Addr(0x10001000).SanityCheckV2());
// Invalid file type. // Invalid file type.
EXPECT_FALSE(Addr(0xD0001000).SanityCheck()); EXPECT_FALSE(Addr(0xD0001000).SanityCheckV2());
EXPECT_FALSE(Addr(0xF0000000).SanityCheck()); EXPECT_FALSE(Addr(0xE0001000).SanityCheckV3());
EXPECT_FALSE(Addr(0xF0000000).SanityCheckV2());
// Reserved bits. // Reserved bits.
EXPECT_FALSE(Addr(0x14000000).SanityCheck()); EXPECT_FALSE(Addr(0x14000000).SanityCheckV2());
EXPECT_FALSE(Addr(0x18000000).SanityCheck()); EXPECT_FALSE(Addr(0x18000000).SanityCheckV2());
} }
} // namespace disk_cache } // namespace disk_cache
...@@ -596,7 +596,7 @@ bool EntryImpl::SanityCheck() { ...@@ -596,7 +596,7 @@ bool EntryImpl::SanityCheck() {
(stored->key_len > kMaxInternalKeyLength && !key_addr.is_initialized())) (stored->key_len > kMaxInternalKeyLength && !key_addr.is_initialized()))
return false; return false;
if (!key_addr.SanityCheck()) if (!key_addr.SanityCheckV2())
return false; return false;
if (key_addr.is_initialized() && if (key_addr.is_initialized() &&
...@@ -629,7 +629,7 @@ bool EntryImpl::DataSanityCheck() { ...@@ -629,7 +629,7 @@ bool EntryImpl::DataSanityCheck() {
return false; return false;
if (!data_size && data_addr.is_initialized()) if (!data_size && data_addr.is_initialized())
return false; return false;
if (!data_addr.SanityCheck()) if (!data_addr.SanityCheckV2())
return false; return false;
if (!data_size) if (!data_size)
continue; continue;
...@@ -654,7 +654,7 @@ void EntryImpl::FixForDelete() { ...@@ -654,7 +654,7 @@ void EntryImpl::FixForDelete() {
if (data_addr.is_initialized()) { if (data_addr.is_initialized()) {
if ((data_size <= kMaxBlockSize && data_addr.is_separate_file()) || if ((data_size <= kMaxBlockSize && data_addr.is_separate_file()) ||
(data_size > kMaxBlockSize && data_addr.is_block_file()) || (data_size > kMaxBlockSize && data_addr.is_block_file()) ||
!data_addr.SanityCheck()) { !data_addr.SanityCheckV2()) {
STRESS_NOTREACHED(); STRESS_NOTREACHED();
// The address is weird so don't attempt to delete it. // The address is weird so don't attempt to delete it.
stored->data_addr[i] = 0; stored->data_addr[i] = 0;
......
...@@ -533,8 +533,8 @@ bool Rankings::SanityCheck(CacheRankingsBlock* node, bool from_list) const { ...@@ -533,8 +533,8 @@ bool Rankings::SanityCheck(CacheRankingsBlock* node, bool from_list) const {
Addr next_addr(data->next); Addr next_addr(data->next);
Addr prev_addr(data->prev); Addr prev_addr(data->prev);
if (!next_addr.SanityCheck() || next_addr.file_type() != RANKINGS || if (!next_addr.SanityCheckV2() || next_addr.file_type() != RANKINGS ||
!prev_addr.SanityCheck() || prev_addr.file_type() != RANKINGS) !prev_addr.SanityCheckV2() || prev_addr.file_type() != RANKINGS)
return false; return false;
return true; return true;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment