OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "net/disk_cache/entry_impl.h" | 5 #include "net/disk_cache/entry_impl.h" |
6 | 6 |
7 #include "base/hash.h" | 7 #include "base/hash.h" |
8 #include "base/message_loop.h" | 8 #include "base/message_loop.h" |
9 #include "base/metrics/histogram.h" | 9 #include "base/metrics/histogram.h" |
10 #include "base/string_util.h" | 10 #include "base/string_util.h" |
11 #include "net/base/io_buffer.h" | 11 #include "net/base/io_buffer.h" |
12 #include "net/base/net_errors.h" | 12 #include "net/base/net_errors.h" |
13 #include "net/disk_cache/backend_impl.h" | 13 #include "net/disk_cache/backend_impl.h" |
14 #include "net/disk_cache/bitmap.h" | 14 #include "net/disk_cache/bitmap.h" |
15 #include "net/disk_cache/cache_util.h" | 15 #include "net/disk_cache/cache_util.h" |
| 16 #include "net/disk_cache/disk_format.h" |
16 #include "net/disk_cache/histogram_macros.h" | 17 #include "net/disk_cache/histogram_macros.h" |
17 #include "net/disk_cache/net_log_parameters.h" | 18 #include "net/disk_cache/net_log_parameters.h" |
18 #include "net/disk_cache/sparse_control.h" | 19 #include "net/disk_cache/sparse_control.h" |
19 | 20 |
20 using base::Time; | 21 using base::Time; |
21 using base::TimeDelta; | 22 using base::TimeDelta; |
22 using base::TimeTicks; | 23 using base::TimeTicks; |
23 | 24 |
24 namespace { | 25 namespace { |
25 | 26 |
(...skipping 548 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
574 return false; | 575 return false; |
575 | 576 |
576 if (stored->reuse_count < 0 || stored->refetch_count < 0) | 577 if (stored->reuse_count < 0 || stored->refetch_count < 0) |
577 return false; | 578 return false; |
578 | 579 |
579 Addr rankings_addr(stored->rankings_node); | 580 Addr rankings_addr(stored->rankings_node); |
580 if (!rankings_addr.SanityCheckForRankings()) | 581 if (!rankings_addr.SanityCheckForRankings()) |
581 return false; | 582 return false; |
582 | 583 |
583 Addr next_addr(stored->next); | 584 Addr next_addr(stored->next); |
584 if (next_addr.is_initialized() && !next_addr.SanityCheckForEntry()) { | 585 if (next_addr.is_initialized() && !next_addr.SanityCheckForEntryV2()) { |
585 STRESS_NOTREACHED(); | 586 STRESS_NOTREACHED(); |
586 return false; | 587 return false; |
587 } | 588 } |
588 STRESS_DCHECK(next_addr.value() != entry_.address().value()); | 589 STRESS_DCHECK(next_addr.value() != entry_.address().value()); |
589 | 590 |
590 if (stored->state > ENTRY_DOOMED || stored->state < ENTRY_NORMAL) | 591 if (stored->state > ENTRY_DOOMED || stored->state < ENTRY_NORMAL) |
591 return false; | 592 return false; |
592 | 593 |
593 Addr key_addr(stored->long_key); | 594 Addr key_addr(stored->long_key); |
594 if ((stored->key_len <= kMaxInternalKeyLength && key_addr.is_initialized()) || | 595 if ((stored->key_len <= kMaxInternalKeyLength && key_addr.is_initialized()) || |
595 (stored->key_len > kMaxInternalKeyLength && !key_addr.is_initialized())) | 596 (stored->key_len > kMaxInternalKeyLength && !key_addr.is_initialized())) |
596 return false; | 597 return false; |
597 | 598 |
598 if (!key_addr.SanityCheck()) | 599 if (!key_addr.SanityCheckV2()) |
599 return false; | 600 return false; |
600 | 601 |
601 if (key_addr.is_initialized() && | 602 if (key_addr.is_initialized() && |
602 ((stored->key_len < kMaxBlockSize && key_addr.is_separate_file()) || | 603 ((stored->key_len < kMaxBlockSize && key_addr.is_separate_file()) || |
603 (stored->key_len >= kMaxBlockSize && key_addr.is_block_file()))) | 604 (stored->key_len >= kMaxBlockSize && key_addr.is_block_file()))) |
604 return false; | 605 return false; |
605 | 606 |
606 int num_blocks = NumBlocksForEntry(stored->key_len); | 607 int num_blocks = NumBlocksForEntry(stored->key_len); |
607 if (entry_.address().num_blocks() != num_blocks) | 608 if (entry_.address().num_blocks() != num_blocks) |
608 return false; | 609 return false; |
(...skipping 12 matching lines...) Expand all Loading... |
621 if (stored->hash != base::Hash(GetKey())) | 622 if (stored->hash != base::Hash(GetKey())) |
622 return false; | 623 return false; |
623 | 624 |
624 for (int i = 0; i < kNumStreams; i++) { | 625 for (int i = 0; i < kNumStreams; i++) { |
625 Addr data_addr(stored->data_addr[i]); | 626 Addr data_addr(stored->data_addr[i]); |
626 int data_size = stored->data_size[i]; | 627 int data_size = stored->data_size[i]; |
627 if (data_size < 0) | 628 if (data_size < 0) |
628 return false; | 629 return false; |
629 if (!data_size && data_addr.is_initialized()) | 630 if (!data_size && data_addr.is_initialized()) |
630 return false; | 631 return false; |
631 if (!data_addr.SanityCheck()) | 632 if (!data_addr.SanityCheckV2()) |
632 return false; | 633 return false; |
633 if (!data_size) | 634 if (!data_size) |
634 continue; | 635 continue; |
635 if (data_size <= kMaxBlockSize && data_addr.is_separate_file()) | 636 if (data_size <= kMaxBlockSize && data_addr.is_separate_file()) |
636 return false; | 637 return false; |
637 if (data_size > kMaxBlockSize && data_addr.is_block_file()) | 638 if (data_size > kMaxBlockSize && data_addr.is_block_file()) |
638 return false; | 639 return false; |
639 } | 640 } |
640 return true; | 641 return true; |
641 } | 642 } |
642 | 643 |
643 void EntryImpl::FixForDelete() { | 644 void EntryImpl::FixForDelete() { |
644 EntryStore* stored = entry_.Data(); | 645 EntryStore* stored = entry_.Data(); |
645 Addr key_addr(stored->long_key); | 646 Addr key_addr(stored->long_key); |
646 | 647 |
647 if (!key_addr.is_initialized()) | 648 if (!key_addr.is_initialized()) |
648 stored->key[stored->key_len] = '\0'; | 649 stored->key[stored->key_len] = '\0'; |
649 | 650 |
650 for (int i = 0; i < kNumStreams; i++) { | 651 for (int i = 0; i < kNumStreams; i++) { |
651 Addr data_addr(stored->data_addr[i]); | 652 Addr data_addr(stored->data_addr[i]); |
652 int data_size = stored->data_size[i]; | 653 int data_size = stored->data_size[i]; |
653 if (data_addr.is_initialized()) { | 654 if (data_addr.is_initialized()) { |
654 if ((data_size <= kMaxBlockSize && data_addr.is_separate_file()) || | 655 if ((data_size <= kMaxBlockSize && data_addr.is_separate_file()) || |
655 (data_size > kMaxBlockSize && data_addr.is_block_file()) || | 656 (data_size > kMaxBlockSize && data_addr.is_block_file()) || |
656 !data_addr.SanityCheck()) { | 657 !data_addr.SanityCheckV2()) { |
657 STRESS_NOTREACHED(); | 658 STRESS_NOTREACHED(); |
658 // The address is weird so don't attempt to delete it. | 659 // The address is weird so don't attempt to delete it. |
659 stored->data_addr[i] = 0; | 660 stored->data_addr[i] = 0; |
660 // In general, trust the stored size as it should be in sync with the | 661 // In general, trust the stored size as it should be in sync with the |
661 // total size tracked by the backend. | 662 // total size tracked by the backend. |
662 } | 663 } |
663 } | 664 } |
664 if (data_size < 0) | 665 if (data_size < 0) |
665 stored->data_size[i] = 0; | 666 stored->data_size[i] = 0; |
666 } | 667 } |
(...skipping 507 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1174 if (!backend_) | 1175 if (!backend_) |
1175 return false; | 1176 return false; |
1176 | 1177 |
1177 FileType file_type = Addr::RequiredFileType(size); | 1178 FileType file_type = Addr::RequiredFileType(size); |
1178 if (EXTERNAL == file_type) { | 1179 if (EXTERNAL == file_type) { |
1179 if (size > backend_->MaxFileSize()) | 1180 if (size > backend_->MaxFileSize()) |
1180 return false; | 1181 return false; |
1181 if (!backend_->CreateExternalFile(address)) | 1182 if (!backend_->CreateExternalFile(address)) |
1182 return false; | 1183 return false; |
1183 } else { | 1184 } else { |
1184 int num_blocks = (size + Addr::BlockSizeForFileType(file_type) - 1) / | 1185 int num_blocks = Addr::RequiredBlocks(size, file_type); |
1185 Addr::BlockSizeForFileType(file_type); | |
1186 | 1186 |
1187 if (!backend_->CreateBlock(file_type, num_blocks, address)) | 1187 if (!backend_->CreateBlock(file_type, num_blocks, address)) |
1188 return false; | 1188 return false; |
1189 } | 1189 } |
1190 return true; | 1190 return true; |
1191 } | 1191 } |
1192 | 1192 |
1193 // Note that this method may end up modifying a block file so upon return the | 1193 // Note that this method may end up modifying a block file so upon return the |
1194 // involved block will be free, and could be reused for something else. If there | 1194 // involved block will be free, and could be reused for something else. If there |
1195 // is a crash after that point (and maybe before returning to the caller), the | 1195 // is a crash after that point (and maybe before returning to the caller), the |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1282 | 1282 |
1283 if (!user_buffers_[index].get() && offset < kMaxBlockSize) { | 1283 if (!user_buffers_[index].get() && offset < kMaxBlockSize) { |
1284 // We are about to create a buffer for the first 16KB, make sure that we | 1284 // We are about to create a buffer for the first 16KB, make sure that we |
1285 // preserve existing data. | 1285 // preserve existing data. |
1286 if (!CopyToLocalBuffer(index)) | 1286 if (!CopyToLocalBuffer(index)) |
1287 return false; | 1287 return false; |
1288 } | 1288 } |
1289 } | 1289 } |
1290 | 1290 |
1291 if (!user_buffers_[index].get()) | 1291 if (!user_buffers_[index].get()) |
1292 user_buffers_[index].reset(new UserBuffer(backend_)); | 1292 user_buffers_[index].reset(new UserBuffer(backend_.get())); |
1293 | 1293 |
1294 return PrepareBuffer(index, offset, buf_len); | 1294 return PrepareBuffer(index, offset, buf_len); |
1295 } | 1295 } |
1296 | 1296 |
1297 // We get to this function with some data already stored. If there is a | 1297 // We get to this function with some data already stored. If there is a |
1298 // truncation that results on data stored internally, we'll explicitly | 1298 // truncation that results on data stored internally, we'll explicitly |
1299 // handle the case here. | 1299 // handle the case here. |
1300 bool EntryImpl::HandleTruncation(int index, int offset, int buf_len) { | 1300 bool EntryImpl::HandleTruncation(int index, int offset, int buf_len) { |
1301 Addr address(entry_.Data()->data_addr[index]); | 1301 Addr address(entry_.Data()->data_addr[index]); |
1302 | 1302 |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1353 | 1353 |
1354 return ImportSeparateFile(index, offset + buf_len); | 1354 return ImportSeparateFile(index, offset + buf_len); |
1355 } | 1355 } |
1356 | 1356 |
1357 bool EntryImpl::CopyToLocalBuffer(int index) { | 1357 bool EntryImpl::CopyToLocalBuffer(int index) { |
1358 Addr address(entry_.Data()->data_addr[index]); | 1358 Addr address(entry_.Data()->data_addr[index]); |
1359 DCHECK(!user_buffers_[index].get()); | 1359 DCHECK(!user_buffers_[index].get()); |
1360 DCHECK(address.is_initialized()); | 1360 DCHECK(address.is_initialized()); |
1361 | 1361 |
1362 int len = std::min(entry_.Data()->data_size[index], kMaxBlockSize); | 1362 int len = std::min(entry_.Data()->data_size[index], kMaxBlockSize); |
1363 user_buffers_[index].reset(new UserBuffer(backend_)); | 1363 user_buffers_[index].reset(new UserBuffer(backend_.get())); |
1364 user_buffers_[index]->Write(len, NULL, 0); | 1364 user_buffers_[index]->Write(len, NULL, 0); |
1365 | 1365 |
1366 File* file = GetBackingFile(address, index); | 1366 File* file = GetBackingFile(address, index); |
1367 int offset = 0; | 1367 int offset = 0; |
1368 | 1368 |
1369 if (address.is_block_file()) | 1369 if (address.is_block_file()) |
1370 offset = address.start_block() * address.BlockSize() + kBlockHeaderSize; | 1370 offset = address.start_block() * address.BlockSize() + kBlockHeaderSize; |
1371 | 1371 |
1372 if (!file || | 1372 if (!file || |
1373 !file->Read(user_buffers_[index]->Data(), len, offset, NULL, NULL)) { | 1373 !file->Read(user_buffers_[index]->Data(), len, offset, NULL, NULL)) { |
(...skipping 167 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1541 Trace("%s 0x%p 0x%x 0x%x", msg, reinterpret_cast<void*>(this), | 1541 Trace("%s 0x%p 0x%x 0x%x", msg, reinterpret_cast<void*>(this), |
1542 entry_.address().value(), node_.address().value()); | 1542 entry_.address().value(), node_.address().value()); |
1543 | 1543 |
1544 Trace(" data: 0x%x 0x%x 0x%x", entry_.Data()->data_addr[0], | 1544 Trace(" data: 0x%x 0x%x 0x%x", entry_.Data()->data_addr[0], |
1545 entry_.Data()->data_addr[1], entry_.Data()->long_key); | 1545 entry_.Data()->data_addr[1], entry_.Data()->long_key); |
1546 | 1546 |
1547 Trace(" doomed: %d 0x%x", doomed_, dirty); | 1547 Trace(" doomed: %d 0x%x", doomed_, dirty); |
1548 } | 1548 } |
1549 | 1549 |
1550 } // namespace disk_cache | 1550 } // namespace disk_cache |
OLD | NEW |