| OLD | NEW | 
|---|
| 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 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/histogram.h" | 7 #include "base/histogram.h" | 
| 8 #include "base/message_loop.h" | 8 #include "base/message_loop.h" | 
| 9 #include "base/string_util.h" | 9 #include "base/string_util.h" | 
| 10 #include "net/base/io_buffer.h" | 10 #include "net/base/io_buffer.h" | 
| (...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 71 | 71 | 
| 72 }  // namespace | 72 }  // namespace | 
| 73 | 73 | 
| 74 namespace disk_cache { | 74 namespace disk_cache { | 
| 75 | 75 | 
| 76 EntryImpl::EntryImpl(BackendImpl* backend, Addr address) | 76 EntryImpl::EntryImpl(BackendImpl* backend, Addr address) | 
| 77     : entry_(NULL, Addr(0)), node_(NULL, Addr(0)) { | 77     : entry_(NULL, Addr(0)), node_(NULL, Addr(0)) { | 
| 78   entry_.LazyInit(backend->File(address), address); | 78   entry_.LazyInit(backend->File(address), address); | 
| 79   doomed_ = false; | 79   doomed_ = false; | 
| 80   backend_ = backend; | 80   backend_ = backend; | 
| 81   for (int i = 0; i < NUM_STREAMS; i++) | 81   for (int i = 0; i < NUM_STREAMS; i++) { | 
| 82     unreported_size_[i] = 0; | 82     unreported_size_[i] = 0; | 
|  | 83     need_file_[i] = false; | 
|  | 84   } | 
| 83 } | 85 } | 
| 84 | 86 | 
| 85 // When an entry is deleted from the cache, we clean up all the data associated | 87 // When an entry is deleted from the cache, we clean up all the data associated | 
| 86 // with it for two reasons: to simplify the reuse of the block (we know that any | 88 // with it for two reasons: to simplify the reuse of the block (we know that any | 
| 87 // unused block is filled with zeros), and to simplify the handling of write / | 89 // unused block is filled with zeros), and to simplify the handling of write / | 
| 88 // read partial information from an entry (don't have to worry about returning | 90 // read partial information from an entry (don't have to worry about returning | 
| 89 // data related to a previous cache entry because the range was not fully | 91 // data related to a previous cache entry because the range was not fully | 
| 90 // written before). | 92 // written before). | 
| 91 EntryImpl::~EntryImpl() { | 93 EntryImpl::~EntryImpl() { | 
| 92   if (doomed_) { | 94   if (doomed_) { | 
| (...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 311       } else { | 313       } else { | 
| 312         // Nothing to truncate. | 314         // Nothing to truncate. | 
| 313         truncate = false; | 315         truncate = false; | 
| 314       } | 316       } | 
| 315   } | 317   } | 
| 316 | 318 | 
| 317   UpdateRank(true); | 319   UpdateRank(true); | 
| 318 | 320 | 
| 319   backend_->OnEvent(Stats::WRITE_DATA); | 321   backend_->OnEvent(Stats::WRITE_DATA); | 
| 320 | 322 | 
| 321   if (user_buffers_[index].get()) { | 323   // If we have prepared the cache as an external file, we should never use | 
|  | 324   // user_buffers_ and always write to file directly. | 
|  | 325   if (!need_file_[index] && user_buffers_[index].get()) { | 
| 322     // Complete the operation locally. | 326     // Complete the operation locally. | 
| 323     if (!buf_len) | 327     if (!buf_len) | 
| 324       return 0; | 328       return 0; | 
| 325 | 329 | 
| 326     DCHECK(kMaxBlockSize >= offset + buf_len); | 330     DCHECK(kMaxBlockSize >= offset + buf_len); | 
| 327     memcpy(user_buffers_[index].get() + offset, buf->data(), buf_len); | 331     memcpy(user_buffers_[index].get() + offset, buf->data(), buf_len); | 
| 328     stats.AddTime(Time::Now() - start); | 332     stats.AddTime(Time::Now() - start); | 
| 329     return buf_len; | 333     return buf_len; | 
| 330   } | 334   } | 
| 331 | 335 | 
| (...skipping 26 matching lines...) Expand all  Loading... | 
| 358     return net::ERR_FAILED; | 362     return net::ERR_FAILED; | 
| 359   } | 363   } | 
| 360 | 364 | 
| 361   if (io_callback && completed) | 365   if (io_callback && completed) | 
| 362     io_callback->Discard(); | 366     io_callback->Discard(); | 
| 363 | 367 | 
| 364   stats.AddTime(Time::Now() - start); | 368   stats.AddTime(Time::Now() - start); | 
| 365   return (completed || !completion_callback) ? buf_len : net::ERR_IO_PENDING; | 369   return (completed || !completion_callback) ? buf_len : net::ERR_IO_PENDING; | 
| 366 } | 370 } | 
| 367 | 371 | 
|  | 372 base::PlatformFile EntryImpl::UseExternalFile(int index) { | 
|  | 373   DCHECK(index >= 0 && index < NUM_STREAMS); | 
|  | 374 | 
|  | 375   Addr address(entry_.Data()->data_addr[index]); | 
|  | 376 | 
|  | 377   // We will not prepare the cache file since the entry is already initialized, | 
|  | 378   // just return the platform file backing the cache. | 
|  | 379   if (address.is_initialized()) | 
|  | 380     return GetPlatformFile(index); | 
|  | 381 | 
|  | 382   if (!backend_->CreateExternalFile(&address)) | 
|  | 383     return base::kInvalidPlatformFileValue; | 
|  | 384 | 
|  | 385   entry_.Data()->data_addr[index] = address.value(); | 
|  | 386   entry_.Store(); | 
|  | 387 | 
|  | 388   // Set the flag for this stream so we never use user_buffer_. | 
|  | 389   // TODO(hclam): do we need to save this information to EntryStore? | 
|  | 390   need_file_[index] = true; | 
|  | 391 | 
|  | 392   return GetPlatformFile(index); | 
|  | 393 } | 
|  | 394 | 
|  | 395 base::PlatformFile EntryImpl::GetPlatformFile(int index) { | 
|  | 396   DCHECK(index >= 0 && index < NUM_STREAMS); | 
|  | 397 | 
|  | 398   Addr address(entry_.Data()->data_addr[index]); | 
|  | 399   if (!address.is_initialized() || !address.is_separate_file()) | 
|  | 400     return base::kInvalidPlatformFileValue; | 
|  | 401 | 
|  | 402   File* cache_file = GetExternalFile(address, index); | 
|  | 403   if (!cache_file) | 
|  | 404     return base::kInvalidPlatformFileValue; | 
|  | 405 | 
|  | 406   return cache_file->platform_file(); | 
|  | 407 } | 
|  | 408 | 
| 368 uint32 EntryImpl::GetHash() { | 409 uint32 EntryImpl::GetHash() { | 
| 369   return entry_.Data()->hash; | 410   return entry_.Data()->hash; | 
| 370 } | 411 } | 
| 371 | 412 | 
| 372 bool EntryImpl::CreateEntry(Addr node_address, const std::string& key, | 413 bool EntryImpl::CreateEntry(Addr node_address, const std::string& key, | 
| 373                             uint32 hash) { | 414                             uint32 hash) { | 
| 374   Trace("Create entry In"); | 415   Trace("Create entry In"); | 
| 375   EntryStore* entry_store = entry_.Data(); | 416   EntryStore* entry_store = entry_.Data(); | 
| 376   RankingsNode* node = node_.Data(); | 417   RankingsNode* node = node_.Data(); | 
| 377   memset(entry_store, 0, sizeof(EntryStore) * entry_.address().num_blocks()); | 418   memset(entry_store, 0, sizeof(EntryStore) * entry_.address().num_blocks()); | 
| (...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 596     scoped_refptr<File> file(new File(kKeyFileIndex == index)); | 637     scoped_refptr<File> file(new File(kKeyFileIndex == index)); | 
| 597     if (file->Init(backend_->GetFileName(address))) | 638     if (file->Init(backend_->GetFileName(address))) | 
| 598       files_[index].swap(file); | 639       files_[index].swap(file); | 
| 599   } | 640   } | 
| 600   return files_[index].get(); | 641   return files_[index].get(); | 
| 601 } | 642 } | 
| 602 | 643 | 
| 603 bool EntryImpl::PrepareTarget(int index, int offset, int buf_len, | 644 bool EntryImpl::PrepareTarget(int index, int offset, int buf_len, | 
| 604                               bool truncate) { | 645                               bool truncate) { | 
| 605   Addr address(entry_.Data()->data_addr[index]); | 646   Addr address(entry_.Data()->data_addr[index]); | 
|  | 647 | 
|  | 648   // If we are instructed to use an external file, we should never buffer when | 
|  | 649   // writing. We are done with preparation of the target automatically, since | 
|  | 650   // we have already created the external file for writing. | 
|  | 651   if (need_file_[index]) { | 
|  | 652     // Make sure the stream is initialized and is kept in an external file. | 
|  | 653     DCHECK(address.is_initialized() && address.is_separate_file()); | 
|  | 654     return true; | 
|  | 655   } | 
|  | 656 | 
| 606   if (address.is_initialized() || user_buffers_[index].get()) | 657   if (address.is_initialized() || user_buffers_[index].get()) | 
| 607     return GrowUserBuffer(index, offset, buf_len, truncate); | 658     return GrowUserBuffer(index, offset, buf_len, truncate); | 
| 608 | 659 | 
| 609   if (offset + buf_len > kMaxBlockSize) | 660   if (offset + buf_len > kMaxBlockSize) | 
| 610     return CreateDataBlock(index, offset + buf_len); | 661     return CreateDataBlock(index, offset + buf_len); | 
| 611 | 662 | 
| 612   user_buffers_[index].reset(new char[kMaxBlockSize]); | 663   user_buffers_[index].reset(new char[kMaxBlockSize]); | 
| 613 | 664 | 
| 614   // Overwrite the parts of the buffer that are not going to be written | 665   // Overwrite the parts of the buffer that are not going to be written | 
| 615   // by the current operation (and yes, let's assume that nothing is going | 666   // by the current operation (and yes, let's assume that nothing is going | 
| (...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 778   Trace("%s 0x%p 0x%x 0x%x", msg, reinterpret_cast<void*>(this), | 829   Trace("%s 0x%p 0x%x 0x%x", msg, reinterpret_cast<void*>(this), | 
| 779         entry_.address().value(), node_.address().value()); | 830         entry_.address().value(), node_.address().value()); | 
| 780 | 831 | 
| 781   Trace("  data: 0x%x 0x%x 0x%x", entry_.Data()->data_addr[0], | 832   Trace("  data: 0x%x 0x%x 0x%x", entry_.Data()->data_addr[0], | 
| 782         entry_.Data()->data_addr[1], entry_.Data()->long_key); | 833         entry_.Data()->data_addr[1], entry_.Data()->long_key); | 
| 783 | 834 | 
| 784   Trace("  doomed: %d 0x%p 0x%x", doomed_, pointer, dirty); | 835   Trace("  doomed: %d 0x%p 0x%x", doomed_, pointer, dirty); | 
| 785 } | 836 } | 
| 786 | 837 | 
| 787 }  // namespace disk_cache | 838 }  // namespace disk_cache | 
| OLD | NEW | 
|---|