| OLD | NEW |
| 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2013 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/simple/simple_entry_impl.h" | 5 #include "net/disk_cache/simple/simple_entry_impl.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <cstring> | 8 #include <cstring> |
| 9 #include <vector> | 9 #include <vector> |
| 10 | 10 |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 62 enum HeaderSizeChange { | 62 enum HeaderSizeChange { |
| 63 HEADER_SIZE_CHANGE_INITIAL, | 63 HEADER_SIZE_CHANGE_INITIAL, |
| 64 HEADER_SIZE_CHANGE_SAME, | 64 HEADER_SIZE_CHANGE_SAME, |
| 65 HEADER_SIZE_CHANGE_INCREASE, | 65 HEADER_SIZE_CHANGE_INCREASE, |
| 66 HEADER_SIZE_CHANGE_DECREASE, | 66 HEADER_SIZE_CHANGE_DECREASE, |
| 67 HEADER_SIZE_CHANGE_UNEXPECTED_WRITE, | 67 HEADER_SIZE_CHANGE_UNEXPECTED_WRITE, |
| 68 HEADER_SIZE_CHANGE_MAX | 68 HEADER_SIZE_CHANGE_MAX |
| 69 }; | 69 }; |
| 70 | 70 |
| 71 void RecordReadResult(net::CacheType cache_type, ReadResult result) { | 71 void RecordReadResult(net::CacheType cache_type, ReadResult result) { |
| 72 SIMPLE_CACHE_UMA(ENUMERATION, | 72 SIMPLE_CACHE_UMA( |
| 73 "ReadResult", cache_type, result, READ_RESULT_MAX); | 73 ENUMERATION, "ReadResult", cache_type, result, READ_RESULT_MAX); |
| 74 } | 74 } |
| 75 | 75 |
| 76 void RecordWriteResult(net::CacheType cache_type, WriteResult result) { | 76 void RecordWriteResult(net::CacheType cache_type, WriteResult result) { |
| 77 SIMPLE_CACHE_UMA(ENUMERATION, | 77 SIMPLE_CACHE_UMA( |
| 78 "WriteResult2", cache_type, result, WRITE_RESULT_MAX); | 78 ENUMERATION, "WriteResult2", cache_type, result, WRITE_RESULT_MAX); |
| 79 } | 79 } |
| 80 | 80 |
| 81 // TODO(ttuttle): Consider removing this once we have a good handle on header | 81 // TODO(ttuttle): Consider removing this once we have a good handle on header |
| 82 // size changes. | 82 // size changes. |
| 83 void RecordHeaderSizeChange(net::CacheType cache_type, | 83 void RecordHeaderSizeChange(net::CacheType cache_type, |
| 84 int old_size, int new_size) { | 84 int old_size, |
| 85 int new_size) { |
| 85 HeaderSizeChange size_change; | 86 HeaderSizeChange size_change; |
| 86 | 87 |
| 87 SIMPLE_CACHE_UMA(COUNTS_10000, "HeaderSize", cache_type, new_size); | 88 SIMPLE_CACHE_UMA(COUNTS_10000, "HeaderSize", cache_type, new_size); |
| 88 | 89 |
| 89 if (old_size == 0) { | 90 if (old_size == 0) { |
| 90 size_change = HEADER_SIZE_CHANGE_INITIAL; | 91 size_change = HEADER_SIZE_CHANGE_INITIAL; |
| 91 } else if (new_size == old_size) { | 92 } else if (new_size == old_size) { |
| 92 size_change = HEADER_SIZE_CHANGE_SAME; | 93 size_change = HEADER_SIZE_CHANGE_SAME; |
| 93 } else if (new_size > old_size) { | 94 } else if (new_size > old_size) { |
| 94 int delta = new_size - old_size; | 95 int delta = new_size - old_size; |
| 95 SIMPLE_CACHE_UMA(COUNTS_10000, | 96 SIMPLE_CACHE_UMA( |
| 96 "HeaderSizeIncreaseAbsolute", cache_type, delta); | 97 COUNTS_10000, "HeaderSizeIncreaseAbsolute", cache_type, delta); |
| 97 SIMPLE_CACHE_UMA(PERCENTAGE, | 98 SIMPLE_CACHE_UMA(PERCENTAGE, |
| 98 "HeaderSizeIncreasePercentage", cache_type, | 99 "HeaderSizeIncreasePercentage", |
| 100 cache_type, |
| 99 delta * 100 / old_size); | 101 delta * 100 / old_size); |
| 100 size_change = HEADER_SIZE_CHANGE_INCREASE; | 102 size_change = HEADER_SIZE_CHANGE_INCREASE; |
| 101 } else { // new_size < old_size | 103 } else { // new_size < old_size |
| 102 int delta = old_size - new_size; | 104 int delta = old_size - new_size; |
| 103 SIMPLE_CACHE_UMA(COUNTS_10000, | 105 SIMPLE_CACHE_UMA( |
| 104 "HeaderSizeDecreaseAbsolute", cache_type, delta); | 106 COUNTS_10000, "HeaderSizeDecreaseAbsolute", cache_type, delta); |
| 105 SIMPLE_CACHE_UMA(PERCENTAGE, | 107 SIMPLE_CACHE_UMA(PERCENTAGE, |
| 106 "HeaderSizeDecreasePercentage", cache_type, | 108 "HeaderSizeDecreasePercentage", |
| 109 cache_type, |
| 107 delta * 100 / old_size); | 110 delta * 100 / old_size); |
| 108 size_change = HEADER_SIZE_CHANGE_DECREASE; | 111 size_change = HEADER_SIZE_CHANGE_DECREASE; |
| 109 } | 112 } |
| 110 | 113 |
| 111 SIMPLE_CACHE_UMA(ENUMERATION, | 114 SIMPLE_CACHE_UMA(ENUMERATION, |
| 112 "HeaderSizeChange", cache_type, | 115 "HeaderSizeChange", |
| 113 size_change, HEADER_SIZE_CHANGE_MAX); | 116 cache_type, |
| 117 size_change, |
| 118 HEADER_SIZE_CHANGE_MAX); |
| 114 } | 119 } |
| 115 | 120 |
| 116 void RecordUnexpectedStream0Write(net::CacheType cache_type) { | 121 void RecordUnexpectedStream0Write(net::CacheType cache_type) { |
| 117 SIMPLE_CACHE_UMA(ENUMERATION, | 122 SIMPLE_CACHE_UMA(ENUMERATION, |
| 118 "HeaderSizeChange", cache_type, | 123 "HeaderSizeChange", |
| 119 HEADER_SIZE_CHANGE_UNEXPECTED_WRITE, HEADER_SIZE_CHANGE_MAX); | 124 cache_type, |
| 125 HEADER_SIZE_CHANGE_UNEXPECTED_WRITE, |
| 126 HEADER_SIZE_CHANGE_MAX); |
| 120 } | 127 } |
| 121 | 128 |
| 122 int g_open_entry_count = 0; | 129 int g_open_entry_count = 0; |
| 123 | 130 |
| 124 void AdjustOpenEntryCountBy(net::CacheType cache_type, int offset) { | 131 void AdjustOpenEntryCountBy(net::CacheType cache_type, int offset) { |
| 125 g_open_entry_count += offset; | 132 g_open_entry_count += offset; |
| 126 SIMPLE_CACHE_UMA(COUNTS_10000, | 133 SIMPLE_CACHE_UMA( |
| 127 "GlobalOpenEntryCount", cache_type, g_open_entry_count); | 134 COUNTS_10000, "GlobalOpenEntryCount", cache_type, g_open_entry_count); |
| 128 } | 135 } |
| 129 | 136 |
| 130 void InvokeCallbackIfBackendIsAlive( | 137 void InvokeCallbackIfBackendIsAlive( |
| 131 const base::WeakPtr<SimpleBackendImpl>& backend, | 138 const base::WeakPtr<SimpleBackendImpl>& backend, |
| 132 const net::CompletionCallback& completion_callback, | 139 const net::CompletionCallback& completion_callback, |
| 133 int result) { | 140 int result) { |
| 134 DCHECK(!completion_callback.is_null()); | 141 DCHECK(!completion_callback.is_null()); |
| 135 if (!backend.get()) | 142 if (!backend.get()) |
| 136 return; | 143 return; |
| 137 completion_callback.Run(result); | 144 completion_callback.Run(result); |
| 138 } | 145 } |
| 139 | 146 |
| 140 } // namespace | 147 } // namespace |
| 141 | 148 |
| 142 using base::Closure; | 149 using base::Closure; |
| 143 using base::FilePath; | 150 using base::FilePath; |
| 144 using base::MessageLoopProxy; | 151 using base::MessageLoopProxy; |
| 145 using base::Time; | 152 using base::Time; |
| 146 using base::TaskRunner; | 153 using base::TaskRunner; |
| 147 | 154 |
| 148 // A helper class to insure that RunNextOperationIfNeeded() is called when | 155 // A helper class to insure that RunNextOperationIfNeeded() is called when |
| 149 // exiting the current stack frame. | 156 // exiting the current stack frame. |
| 150 class SimpleEntryImpl::ScopedOperationRunner { | 157 class SimpleEntryImpl::ScopedOperationRunner { |
| 151 public: | 158 public: |
| 152 explicit ScopedOperationRunner(SimpleEntryImpl* entry) : entry_(entry) { | 159 explicit ScopedOperationRunner(SimpleEntryImpl* entry) : entry_(entry) {} |
| 153 } | |
| 154 | 160 |
| 155 ~ScopedOperationRunner() { | 161 ~ScopedOperationRunner() { entry_->RunNextOperationIfNeeded(); } |
| 156 entry_->RunNextOperationIfNeeded(); | |
| 157 } | |
| 158 | 162 |
| 159 private: | 163 private: |
| 160 SimpleEntryImpl* const entry_; | 164 SimpleEntryImpl* const entry_; |
| 161 }; | 165 }; |
| 162 | 166 |
| 163 SimpleEntryImpl::SimpleEntryImpl(net::CacheType cache_type, | 167 SimpleEntryImpl::SimpleEntryImpl(net::CacheType cache_type, |
| 164 const FilePath& path, | 168 const FilePath& path, |
| 165 const uint64 entry_hash, | 169 const uint64 entry_hash, |
| 166 OperationsMode operations_mode, | 170 OperationsMode operations_mode, |
| 167 SimpleBackendImpl* backend, | 171 SimpleBackendImpl* backend, |
| 168 net::NetLog* net_log) | 172 net::NetLog* net_log) |
| 169 : backend_(backend->AsWeakPtr()), | 173 : backend_(backend->AsWeakPtr()), |
| 170 cache_type_(cache_type), | 174 cache_type_(cache_type), |
| 171 worker_pool_(backend->worker_pool()), | 175 worker_pool_(backend->worker_pool()), |
| 172 path_(path), | 176 path_(path), |
| 173 entry_hash_(entry_hash), | 177 entry_hash_(entry_hash), |
| 174 use_optimistic_operations_(operations_mode == OPTIMISTIC_OPERATIONS), | 178 use_optimistic_operations_(operations_mode == OPTIMISTIC_OPERATIONS), |
| 175 last_used_(Time::Now()), | 179 last_used_(Time::Now()), |
| 176 last_modified_(last_used_), | 180 last_modified_(last_used_), |
| 177 sparse_data_size_(0), | 181 sparse_data_size_(0), |
| 178 open_count_(0), | 182 open_count_(0), |
| 179 doomed_(false), | 183 doomed_(false), |
| 180 state_(STATE_UNINITIALIZED), | 184 state_(STATE_UNINITIALIZED), |
| 181 synchronous_entry_(NULL), | 185 synchronous_entry_(NULL), |
| 182 net_log_(net::BoundNetLog::Make( | 186 net_log_(net::BoundNetLog::Make(net_log, |
| 183 net_log, net::NetLog::SOURCE_DISK_CACHE_ENTRY)), | 187 net::NetLog::SOURCE_DISK_CACHE_ENTRY)), |
| 184 stream_0_data_(new net::GrowableIOBuffer()) { | 188 stream_0_data_(new net::GrowableIOBuffer()) { |
| 185 COMPILE_ASSERT(arraysize(data_size_) == arraysize(crc32s_end_offset_), | 189 COMPILE_ASSERT(arraysize(data_size_) == arraysize(crc32s_end_offset_), |
| 186 arrays_should_be_same_size); | 190 arrays_should_be_same_size); |
| 187 COMPILE_ASSERT(arraysize(data_size_) == arraysize(crc32s_), | 191 COMPILE_ASSERT(arraysize(data_size_) == arraysize(crc32s_), |
| 188 arrays_should_be_same_size); | 192 arrays_should_be_same_size); |
| 189 COMPILE_ASSERT(arraysize(data_size_) == arraysize(have_written_), | 193 COMPILE_ASSERT(arraysize(data_size_) == arraysize(have_written_), |
| 190 arrays_should_be_same_size); | 194 arrays_should_be_same_size); |
| 191 COMPILE_ASSERT(arraysize(data_size_) == arraysize(crc_check_state_), | 195 COMPILE_ASSERT(arraysize(data_size_) == arraysize(crc_check_state_), |
| 192 arrays_should_be_same_size); | 196 arrays_should_be_same_size); |
| 193 MakeUninitialized(); | 197 MakeUninitialized(); |
| 194 net_log_.BeginEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY, | 198 net_log_.BeginEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY, |
| 195 CreateNetLogSimpleEntryConstructionCallback(this)); | 199 CreateNetLogSimpleEntryConstructionCallback(this)); |
| 196 } | 200 } |
| 197 | 201 |
| 198 int SimpleEntryImpl::OpenEntry(Entry** out_entry, | 202 int SimpleEntryImpl::OpenEntry(Entry** out_entry, |
| 199 const CompletionCallback& callback) { | 203 const CompletionCallback& callback) { |
| 200 DCHECK(backend_.get()); | 204 DCHECK(backend_.get()); |
| 201 | 205 |
| 202 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_CALL); | 206 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_CALL); |
| 203 | 207 |
| 204 bool have_index = backend_->index()->initialized(); | 208 bool have_index = backend_->index()->initialized(); |
| 205 // This enumeration is used in histograms, add entries only at end. | 209 // This enumeration is used in histograms, add entries only at end. |
| 206 enum OpenEntryIndexEnum { | 210 enum OpenEntryIndexEnum { |
| 207 INDEX_NOEXIST = 0, | 211 INDEX_NOEXIST = 0, |
| 208 INDEX_MISS = 1, | 212 INDEX_MISS = 1, |
| 209 INDEX_HIT = 2, | 213 INDEX_HIT = 2, |
| 210 INDEX_MAX = 3, | 214 INDEX_MAX = 3, |
| 211 }; | 215 }; |
| 212 OpenEntryIndexEnum open_entry_index_enum = INDEX_NOEXIST; | 216 OpenEntryIndexEnum open_entry_index_enum = INDEX_NOEXIST; |
| 213 if (have_index) { | 217 if (have_index) { |
| 214 if (backend_->index()->Has(entry_hash_)) | 218 if (backend_->index()->Has(entry_hash_)) |
| 215 open_entry_index_enum = INDEX_HIT; | 219 open_entry_index_enum = INDEX_HIT; |
| 216 else | 220 else |
| 217 open_entry_index_enum = INDEX_MISS; | 221 open_entry_index_enum = INDEX_MISS; |
| 218 } | 222 } |
| 219 SIMPLE_CACHE_UMA(ENUMERATION, | 223 SIMPLE_CACHE_UMA(ENUMERATION, |
| 220 "OpenEntryIndexState", cache_type_, | 224 "OpenEntryIndexState", |
| 221 open_entry_index_enum, INDEX_MAX); | 225 cache_type_, |
| 226 open_entry_index_enum, |
| 227 INDEX_MAX); |
| 222 | 228 |
| 223 // If entry is not known to the index, initiate fast failover to the network. | 229 // If entry is not known to the index, initiate fast failover to the network. |
| 224 if (open_entry_index_enum == INDEX_MISS) { | 230 if (open_entry_index_enum == INDEX_MISS) { |
| 225 net_log_.AddEventWithNetErrorCode( | 231 net_log_.AddEventWithNetErrorCode( |
| 226 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_END, | 232 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_END, net::ERR_FAILED); |
| 227 net::ERR_FAILED); | |
| 228 return net::ERR_FAILED; | 233 return net::ERR_FAILED; |
| 229 } | 234 } |
| 230 | 235 |
| 231 pending_operations_.push(SimpleEntryOperation::OpenOperation( | 236 pending_operations_.push(SimpleEntryOperation::OpenOperation( |
| 232 this, have_index, callback, out_entry)); | 237 this, have_index, callback, out_entry)); |
| 233 RunNextOperationIfNeeded(); | 238 RunNextOperationIfNeeded(); |
| 234 return net::ERR_IO_PENDING; | 239 return net::ERR_IO_PENDING; |
| 235 } | 240 } |
| 236 | 241 |
| 237 int SimpleEntryImpl::CreateEntry(Entry** out_entry, | 242 int SimpleEntryImpl::CreateEntry(Entry** out_entry, |
| 238 const CompletionCallback& callback) { | 243 const CompletionCallback& callback) { |
| 239 DCHECK(backend_.get()); | 244 DCHECK(backend_.get()); |
| 240 DCHECK_EQ(entry_hash_, simple_util::GetEntryHashKey(key_)); | 245 DCHECK_EQ(entry_hash_, simple_util::GetEntryHashKey(key_)); |
| 241 | 246 |
| 242 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CREATE_CALL); | 247 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CREATE_CALL); |
| 243 | 248 |
| 244 bool have_index = backend_->index()->initialized(); | 249 bool have_index = backend_->index()->initialized(); |
| 245 int ret_value = net::ERR_FAILED; | 250 int ret_value = net::ERR_FAILED; |
| 246 if (use_optimistic_operations_ && | 251 if (use_optimistic_operations_ && state_ == STATE_UNINITIALIZED && |
| 247 state_ == STATE_UNINITIALIZED && pending_operations_.size() == 0) { | 252 pending_operations_.size() == 0) { |
| 248 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CREATE_OPTIMISTIC); | 253 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CREATE_OPTIMISTIC); |
| 249 | 254 |
| 250 ReturnEntryToCaller(out_entry); | 255 ReturnEntryToCaller(out_entry); |
| 251 pending_operations_.push(SimpleEntryOperation::CreateOperation( | 256 pending_operations_.push(SimpleEntryOperation::CreateOperation( |
| 252 this, have_index, CompletionCallback(), static_cast<Entry**>(NULL))); | 257 this, have_index, CompletionCallback(), static_cast<Entry**>(NULL))); |
| 253 ret_value = net::OK; | 258 ret_value = net::OK; |
| 254 } else { | 259 } else { |
| 255 pending_operations_.push(SimpleEntryOperation::CreateOperation( | 260 pending_operations_.push(SimpleEntryOperation::CreateOperation( |
| 256 this, have_index, callback, out_entry)); | 261 this, have_index, callback, out_entry)); |
| 257 ret_value = net::ERR_IO_PENDING; | 262 ret_value = net::ERR_IO_PENDING; |
| (...skipping 20 matching lines...) Expand all Loading... |
| 278 if (backend_.get()) | 283 if (backend_.get()) |
| 279 backend_->OnDoomStart(entry_hash_); | 284 backend_->OnDoomStart(entry_hash_); |
| 280 pending_operations_.push(SimpleEntryOperation::DoomOperation(this, callback)); | 285 pending_operations_.push(SimpleEntryOperation::DoomOperation(this, callback)); |
| 281 RunNextOperationIfNeeded(); | 286 RunNextOperationIfNeeded(); |
| 282 return net::ERR_IO_PENDING; | 287 return net::ERR_IO_PENDING; |
| 283 } | 288 } |
| 284 | 289 |
| 285 void SimpleEntryImpl::SetKey(const std::string& key) { | 290 void SimpleEntryImpl::SetKey(const std::string& key) { |
| 286 key_ = key; | 291 key_ = key; |
| 287 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_SET_KEY, | 292 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_SET_KEY, |
| 288 net::NetLog::StringCallback("key", &key)); | 293 net::NetLog::StringCallback("key", &key)); |
| 289 } | 294 } |
| 290 | 295 |
| 291 void SimpleEntryImpl::Doom() { | 296 void SimpleEntryImpl::Doom() { |
| 292 DoomEntry(CompletionCallback()); | 297 DoomEntry(CompletionCallback()); |
| 293 } | 298 } |
| 294 | 299 |
| 295 void SimpleEntryImpl::Close() { | 300 void SimpleEntryImpl::Close() { |
| 296 DCHECK(io_thread_checker_.CalledOnValidThread()); | 301 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 297 DCHECK_LT(0, open_count_); | 302 DCHECK_LT(0, open_count_); |
| 298 | 303 |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 333 | 338 |
| 334 int SimpleEntryImpl::ReadData(int stream_index, | 339 int SimpleEntryImpl::ReadData(int stream_index, |
| 335 int offset, | 340 int offset, |
| 336 net::IOBuffer* buf, | 341 net::IOBuffer* buf, |
| 337 int buf_len, | 342 int buf_len, |
| 338 const CompletionCallback& callback) { | 343 const CompletionCallback& callback) { |
| 339 DCHECK(io_thread_checker_.CalledOnValidThread()); | 344 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 340 | 345 |
| 341 if (net_log_.IsLogging()) { | 346 if (net_log_.IsLogging()) { |
| 342 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_CALL, | 347 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_CALL, |
| 343 CreateNetLogReadWriteDataCallback(stream_index, offset, buf_len, | 348 CreateNetLogReadWriteDataCallback( |
| 344 false)); | 349 stream_index, offset, buf_len, false)); |
| 345 } | 350 } |
| 346 | 351 |
| 347 if (stream_index < 0 || stream_index >= kSimpleEntryStreamCount || | 352 if (stream_index < 0 || stream_index >= kSimpleEntryStreamCount || |
| 348 buf_len < 0) { | 353 buf_len < 0) { |
| 349 if (net_log_.IsLogging()) { | 354 if (net_log_.IsLogging()) { |
| 350 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, | 355 net_log_.AddEvent( |
| 356 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, |
| 351 CreateNetLogReadWriteCompleteCallback(net::ERR_INVALID_ARGUMENT)); | 357 CreateNetLogReadWriteCompleteCallback(net::ERR_INVALID_ARGUMENT)); |
| 352 } | 358 } |
| 353 | 359 |
| 354 RecordReadResult(cache_type_, READ_RESULT_INVALID_ARGUMENT); | 360 RecordReadResult(cache_type_, READ_RESULT_INVALID_ARGUMENT); |
| 355 return net::ERR_INVALID_ARGUMENT; | 361 return net::ERR_INVALID_ARGUMENT; |
| 356 } | 362 } |
| 357 if (pending_operations_.empty() && (offset >= GetDataSize(stream_index) || | 363 if (pending_operations_.empty() && |
| 358 offset < 0 || !buf_len)) { | 364 (offset >= GetDataSize(stream_index) || offset < 0 || !buf_len)) { |
| 359 if (net_log_.IsLogging()) { | 365 if (net_log_.IsLogging()) { |
| 360 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, | 366 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, |
| 361 CreateNetLogReadWriteCompleteCallback(0)); | 367 CreateNetLogReadWriteCompleteCallback(0)); |
| 362 } | 368 } |
| 363 | 369 |
| 364 RecordReadResult(cache_type_, READ_RESULT_NONBLOCK_EMPTY_RETURN); | 370 RecordReadResult(cache_type_, READ_RESULT_NONBLOCK_EMPTY_RETURN); |
| 365 return 0; | 371 return 0; |
| 366 } | 372 } |
| 367 | 373 |
| 368 // TODO(clamy): return immediatly when reading from stream 0. | 374 // TODO(clamy): return immediatly when reading from stream 0. |
| 369 | 375 |
| 370 // TODO(felipeg): Optimization: Add support for truly parallel read | 376 // TODO(felipeg): Optimization: Add support for truly parallel read |
| 371 // operations. | 377 // operations. |
| 372 bool alone_in_queue = | 378 bool alone_in_queue = |
| 373 pending_operations_.size() == 0 && state_ == STATE_READY; | 379 pending_operations_.size() == 0 && state_ == STATE_READY; |
| 374 pending_operations_.push(SimpleEntryOperation::ReadOperation( | 380 pending_operations_.push(SimpleEntryOperation::ReadOperation( |
| 375 this, stream_index, offset, buf_len, buf, callback, alone_in_queue)); | 381 this, stream_index, offset, buf_len, buf, callback, alone_in_queue)); |
| 376 RunNextOperationIfNeeded(); | 382 RunNextOperationIfNeeded(); |
| 377 return net::ERR_IO_PENDING; | 383 return net::ERR_IO_PENDING; |
| 378 } | 384 } |
| 379 | 385 |
| 380 int SimpleEntryImpl::WriteData(int stream_index, | 386 int SimpleEntryImpl::WriteData(int stream_index, |
| 381 int offset, | 387 int offset, |
| 382 net::IOBuffer* buf, | 388 net::IOBuffer* buf, |
| 383 int buf_len, | 389 int buf_len, |
| 384 const CompletionCallback& callback, | 390 const CompletionCallback& callback, |
| 385 bool truncate) { | 391 bool truncate) { |
| 386 DCHECK(io_thread_checker_.CalledOnValidThread()); | 392 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 387 | 393 |
| 388 if (net_log_.IsLogging()) { | 394 if (net_log_.IsLogging()) { |
| 389 net_log_.AddEvent( | 395 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_CALL, |
| 390 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_CALL, | 396 CreateNetLogReadWriteDataCallback( |
| 391 CreateNetLogReadWriteDataCallback(stream_index, offset, buf_len, | 397 stream_index, offset, buf_len, truncate)); |
| 392 truncate)); | |
| 393 } | 398 } |
| 394 | 399 |
| 395 if (stream_index < 0 || stream_index >= kSimpleEntryStreamCount || | 400 if (stream_index < 0 || stream_index >= kSimpleEntryStreamCount || |
| 396 offset < 0 || buf_len < 0) { | 401 offset < 0 || buf_len < 0) { |
| 397 if (net_log_.IsLogging()) { | 402 if (net_log_.IsLogging()) { |
| 398 net_log_.AddEvent( | 403 net_log_.AddEvent( |
| 399 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, | 404 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, |
| 400 CreateNetLogReadWriteCompleteCallback(net::ERR_INVALID_ARGUMENT)); | 405 CreateNetLogReadWriteCompleteCallback(net::ERR_INVALID_ARGUMENT)); |
| 401 } | 406 } |
| 402 RecordWriteResult(cache_type_, WRITE_RESULT_INVALID_ARGUMENT); | 407 RecordWriteResult(cache_type_, WRITE_RESULT_INVALID_ARGUMENT); |
| 403 return net::ERR_INVALID_ARGUMENT; | 408 return net::ERR_INVALID_ARGUMENT; |
| 404 } | 409 } |
| 405 if (backend_.get() && offset + buf_len > backend_->GetMaxFileSize()) { | 410 if (backend_.get() && offset + buf_len > backend_->GetMaxFileSize()) { |
| 406 if (net_log_.IsLogging()) { | 411 if (net_log_.IsLogging()) { |
| 407 net_log_.AddEvent( | 412 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, |
| 408 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, | 413 CreateNetLogReadWriteCompleteCallback(net::ERR_FAILED)); |
| 409 CreateNetLogReadWriteCompleteCallback(net::ERR_FAILED)); | |
| 410 } | 414 } |
| 411 RecordWriteResult(cache_type_, WRITE_RESULT_OVER_MAX_SIZE); | 415 RecordWriteResult(cache_type_, WRITE_RESULT_OVER_MAX_SIZE); |
| 412 return net::ERR_FAILED; | 416 return net::ERR_FAILED; |
| 413 } | 417 } |
| 414 ScopedOperationRunner operation_runner(this); | 418 ScopedOperationRunner operation_runner(this); |
| 415 | 419 |
| 416 // Stream 0 data is kept in memory, so can be written immediatly if there are | 420 // Stream 0 data is kept in memory, so can be written immediatly if there are |
| 417 // no IO operations pending. | 421 // no IO operations pending. |
| 418 if (stream_index == 0 && state_ == STATE_READY && | 422 if (stream_index == 0 && state_ == STATE_READY && |
| 419 pending_operations_.size() == 0) | 423 pending_operations_.size() == 0) |
| (...skipping 19 matching lines...) Expand all Loading... |
| 439 // TODO(gavinp,pasko): For performance, don't use a copy of an IOBuffer | 443 // TODO(gavinp,pasko): For performance, don't use a copy of an IOBuffer |
| 440 // here to avoid paying the price of the RefCountedThreadSafe atomic | 444 // here to avoid paying the price of the RefCountedThreadSafe atomic |
| 441 // operations. | 445 // operations. |
| 442 if (buf) { | 446 if (buf) { |
| 443 op_buf = new IOBuffer(buf_len); | 447 op_buf = new IOBuffer(buf_len); |
| 444 memcpy(op_buf->data(), buf->data(), buf_len); | 448 memcpy(op_buf->data(), buf->data(), buf_len); |
| 445 } | 449 } |
| 446 op_callback = CompletionCallback(); | 450 op_callback = CompletionCallback(); |
| 447 ret_value = buf_len; | 451 ret_value = buf_len; |
| 448 if (net_log_.IsLogging()) { | 452 if (net_log_.IsLogging()) { |
| 449 net_log_.AddEvent( | 453 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_OPTIMISTIC, |
| 450 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_OPTIMISTIC, | 454 CreateNetLogReadWriteCompleteCallback(buf_len)); |
| 451 CreateNetLogReadWriteCompleteCallback(buf_len)); | |
| 452 } | 455 } |
| 453 } | 456 } |
| 454 | 457 |
| 455 pending_operations_.push(SimpleEntryOperation::WriteOperation(this, | 458 pending_operations_.push(SimpleEntryOperation::WriteOperation(this, |
| 456 stream_index, | 459 stream_index, |
| 457 offset, | 460 offset, |
| 458 buf_len, | 461 buf_len, |
| 459 op_buf.get(), | 462 op_buf.get(), |
| 460 truncate, | 463 truncate, |
| 461 optimistic, | 464 optimistic, |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 577 doomed_ = true; | 580 doomed_ = true; |
| 578 if (!backend_.get()) | 581 if (!backend_.get()) |
| 579 return; | 582 return; |
| 580 backend_->index()->Remove(entry_hash_); | 583 backend_->index()->Remove(entry_hash_); |
| 581 RemoveSelfFromBackend(); | 584 RemoveSelfFromBackend(); |
| 582 } | 585 } |
| 583 | 586 |
| 584 void SimpleEntryImpl::RunNextOperationIfNeeded() { | 587 void SimpleEntryImpl::RunNextOperationIfNeeded() { |
| 585 DCHECK(io_thread_checker_.CalledOnValidThread()); | 588 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 586 SIMPLE_CACHE_UMA(CUSTOM_COUNTS, | 589 SIMPLE_CACHE_UMA(CUSTOM_COUNTS, |
| 587 "EntryOperationsPending", cache_type_, | 590 "EntryOperationsPending", |
| 588 pending_operations_.size(), 0, 100, 20); | 591 cache_type_, |
| 592 pending_operations_.size(), |
| 593 0, |
| 594 100, |
| 595 20); |
| 589 if (!pending_operations_.empty() && state_ != STATE_IO_PENDING) { | 596 if (!pending_operations_.empty() && state_ != STATE_IO_PENDING) { |
| 590 scoped_ptr<SimpleEntryOperation> operation( | 597 scoped_ptr<SimpleEntryOperation> operation( |
| 591 new SimpleEntryOperation(pending_operations_.front())); | 598 new SimpleEntryOperation(pending_operations_.front())); |
| 592 pending_operations_.pop(); | 599 pending_operations_.pop(); |
| 593 switch (operation->type()) { | 600 switch (operation->type()) { |
| 594 case SimpleEntryOperation::TYPE_OPEN: | 601 case SimpleEntryOperation::TYPE_OPEN: |
| 595 OpenEntryInternal(operation->have_index(), | 602 OpenEntryInternal(operation->have_index(), |
| 596 operation->callback(), | 603 operation->callback(), |
| 597 operation->out_entry()); | 604 operation->out_entry()); |
| 598 break; | 605 break; |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 656 void SimpleEntryImpl::OpenEntryInternal(bool have_index, | 663 void SimpleEntryImpl::OpenEntryInternal(bool have_index, |
| 657 const CompletionCallback& callback, | 664 const CompletionCallback& callback, |
| 658 Entry** out_entry) { | 665 Entry** out_entry) { |
| 659 ScopedOperationRunner operation_runner(this); | 666 ScopedOperationRunner operation_runner(this); |
| 660 | 667 |
| 661 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_BEGIN); | 668 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_BEGIN); |
| 662 | 669 |
| 663 if (state_ == STATE_READY) { | 670 if (state_ == STATE_READY) { |
| 664 ReturnEntryToCaller(out_entry); | 671 ReturnEntryToCaller(out_entry); |
| 665 PostClientCallback(callback, net::OK); | 672 PostClientCallback(callback, net::OK); |
| 666 net_log_.AddEvent( | 673 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_END, |
| 667 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_END, | 674 CreateNetLogSimpleEntryCreationCallback(this, net::OK)); |
| 668 CreateNetLogSimpleEntryCreationCallback(this, net::OK)); | |
| 669 return; | 675 return; |
| 670 } | 676 } |
| 671 if (state_ == STATE_FAILURE) { | 677 if (state_ == STATE_FAILURE) { |
| 672 PostClientCallback(callback, net::ERR_FAILED); | 678 PostClientCallback(callback, net::ERR_FAILED); |
| 673 net_log_.AddEvent( | 679 net_log_.AddEvent( |
| 674 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_END, | 680 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_OPEN_END, |
| 675 CreateNetLogSimpleEntryCreationCallback(this, net::ERR_FAILED)); | 681 CreateNetLogSimpleEntryCreationCallback(this, net::ERR_FAILED)); |
| 676 return; | 682 return; |
| 677 } | 683 } |
| 678 | 684 |
| 679 DCHECK_EQ(STATE_UNINITIALIZED, state_); | 685 DCHECK_EQ(STATE_UNINITIALIZED, state_); |
| 680 DCHECK(!synchronous_entry_); | 686 DCHECK(!synchronous_entry_); |
| 681 state_ = STATE_IO_PENDING; | 687 state_ = STATE_IO_PENDING; |
| 682 const base::TimeTicks start_time = base::TimeTicks::Now(); | 688 const base::TimeTicks start_time = base::TimeTicks::Now(); |
| 683 scoped_ptr<SimpleEntryCreationResults> results( | 689 scoped_ptr<SimpleEntryCreationResults> results( |
| 684 new SimpleEntryCreationResults( | 690 new SimpleEntryCreationResults(SimpleEntryStat( |
| 685 SimpleEntryStat(last_used_, last_modified_, data_size_, | 691 last_used_, last_modified_, data_size_, sparse_data_size_))); |
| 686 sparse_data_size_))); | |
| 687 Closure task = base::Bind(&SimpleSynchronousEntry::OpenEntry, | 692 Closure task = base::Bind(&SimpleSynchronousEntry::OpenEntry, |
| 688 cache_type_, | 693 cache_type_, |
| 689 path_, | 694 path_, |
| 690 entry_hash_, | 695 entry_hash_, |
| 691 have_index, | 696 have_index, |
| 692 results.get()); | 697 results.get()); |
| 693 Closure reply = base::Bind(&SimpleEntryImpl::CreationOperationComplete, | 698 Closure reply = base::Bind(&SimpleEntryImpl::CreationOperationComplete, |
| 694 this, | 699 this, |
| 695 callback, | 700 callback, |
| 696 start_time, | 701 start_time, |
| (...skipping 26 matching lines...) Expand all Loading... |
| 723 // Since we don't know the correct values for |last_used_| and | 728 // Since we don't know the correct values for |last_used_| and |
| 724 // |last_modified_| yet, we make this approximation. | 729 // |last_modified_| yet, we make this approximation. |
| 725 last_used_ = last_modified_ = base::Time::Now(); | 730 last_used_ = last_modified_ = base::Time::Now(); |
| 726 | 731 |
| 727 // If creation succeeds, we should mark all streams to be saved on close. | 732 // If creation succeeds, we should mark all streams to be saved on close. |
| 728 for (int i = 0; i < kSimpleEntryStreamCount; ++i) | 733 for (int i = 0; i < kSimpleEntryStreamCount; ++i) |
| 729 have_written_[i] = true; | 734 have_written_[i] = true; |
| 730 | 735 |
| 731 const base::TimeTicks start_time = base::TimeTicks::Now(); | 736 const base::TimeTicks start_time = base::TimeTicks::Now(); |
| 732 scoped_ptr<SimpleEntryCreationResults> results( | 737 scoped_ptr<SimpleEntryCreationResults> results( |
| 733 new SimpleEntryCreationResults( | 738 new SimpleEntryCreationResults(SimpleEntryStat( |
| 734 SimpleEntryStat(last_used_, last_modified_, data_size_, | 739 last_used_, last_modified_, data_size_, sparse_data_size_))); |
| 735 sparse_data_size_))); | |
| 736 Closure task = base::Bind(&SimpleSynchronousEntry::CreateEntry, | 740 Closure task = base::Bind(&SimpleSynchronousEntry::CreateEntry, |
| 737 cache_type_, | 741 cache_type_, |
| 738 path_, | 742 path_, |
| 739 key_, | 743 key_, |
| 740 entry_hash_, | 744 entry_hash_, |
| 741 have_index, | 745 have_index, |
| 742 results.get()); | 746 results.get()); |
| 743 Closure reply = base::Bind(&SimpleEntryImpl::CreationOperationComplete, | 747 Closure reply = base::Bind(&SimpleEntryImpl::CreationOperationComplete, |
| 744 this, | 748 this, |
| 745 callback, | 749 callback, |
| 746 start_time, | 750 start_time, |
| 747 base::Passed(&results), | 751 base::Passed(&results), |
| 748 out_entry, | 752 out_entry, |
| 749 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CREATE_END); | 753 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CREATE_END); |
| 750 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 754 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 751 } | 755 } |
| 752 | 756 |
| 753 void SimpleEntryImpl::CloseInternal() { | 757 void SimpleEntryImpl::CloseInternal() { |
| 754 DCHECK(io_thread_checker_.CalledOnValidThread()); | 758 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 755 typedef SimpleSynchronousEntry::CRCRecord CRCRecord; | 759 typedef SimpleSynchronousEntry::CRCRecord CRCRecord; |
| 756 scoped_ptr<std::vector<CRCRecord> > | 760 scoped_ptr<std::vector<CRCRecord> > crc32s_to_write( |
| 757 crc32s_to_write(new std::vector<CRCRecord>()); | 761 new std::vector<CRCRecord>()); |
| 758 | 762 |
| 759 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CLOSE_BEGIN); | 763 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CLOSE_BEGIN); |
| 760 | 764 |
| 761 if (state_ == STATE_READY) { | 765 if (state_ == STATE_READY) { |
| 762 DCHECK(synchronous_entry_); | 766 DCHECK(synchronous_entry_); |
| 763 state_ = STATE_IO_PENDING; | 767 state_ = STATE_IO_PENDING; |
| 764 for (int i = 0; i < kSimpleEntryStreamCount; ++i) { | 768 for (int i = 0; i < kSimpleEntryStreamCount; ++i) { |
| 765 if (have_written_[i]) { | 769 if (have_written_[i]) { |
| 766 if (GetDataSize(i) == crc32s_end_offset_[i]) { | 770 if (GetDataSize(i) == crc32s_end_offset_[i]) { |
| 767 int32 crc = GetDataSize(i) == 0 ? crc32(0, Z_NULL, 0) : crc32s_[i]; | 771 int32 crc = GetDataSize(i) == 0 ? crc32(0, Z_NULL, 0) : crc32s_[i]; |
| 768 crc32s_to_write->push_back(CRCRecord(i, true, crc)); | 772 crc32s_to_write->push_back(CRCRecord(i, true, crc)); |
| 769 } else { | 773 } else { |
| 770 crc32s_to_write->push_back(CRCRecord(i, false, 0)); | 774 crc32s_to_write->push_back(CRCRecord(i, false, 0)); |
| 771 } | 775 } |
| 772 } | 776 } |
| 773 } | 777 } |
| 774 } else { | 778 } else { |
| 775 DCHECK(STATE_UNINITIALIZED == state_ || STATE_FAILURE == state_); | 779 DCHECK(STATE_UNINITIALIZED == state_ || STATE_FAILURE == state_); |
| 776 } | 780 } |
| 777 | 781 |
| 778 if (synchronous_entry_) { | 782 if (synchronous_entry_) { |
| 779 Closure task = | 783 Closure task = base::Bind( |
| 780 base::Bind(&SimpleSynchronousEntry::Close, | 784 &SimpleSynchronousEntry::Close, |
| 781 base::Unretained(synchronous_entry_), | 785 base::Unretained(synchronous_entry_), |
| 782 SimpleEntryStat(last_used_, last_modified_, data_size_, | 786 SimpleEntryStat( |
| 783 sparse_data_size_), | 787 last_used_, last_modified_, data_size_, sparse_data_size_), |
| 784 base::Passed(&crc32s_to_write), | 788 base::Passed(&crc32s_to_write), |
| 785 stream_0_data_); | 789 stream_0_data_); |
| 786 Closure reply = base::Bind(&SimpleEntryImpl::CloseOperationComplete, this); | 790 Closure reply = base::Bind(&SimpleEntryImpl::CloseOperationComplete, this); |
| 787 synchronous_entry_ = NULL; | 791 synchronous_entry_ = NULL; |
| 788 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 792 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 789 | 793 |
| 790 for (int i = 0; i < kSimpleEntryStreamCount; ++i) { | 794 for (int i = 0; i < kSimpleEntryStreamCount; ++i) { |
| 791 if (!have_written_[i]) { | 795 if (!have_written_[i]) { |
| 792 SIMPLE_CACHE_UMA(ENUMERATION, | 796 SIMPLE_CACHE_UMA(ENUMERATION, |
| 793 "CheckCRCResult", cache_type_, | 797 "CheckCRCResult", |
| 794 crc_check_state_[i], CRC_CHECK_MAX); | 798 cache_type_, |
| 799 crc_check_state_[i], |
| 800 CRC_CHECK_MAX); |
| 795 } | 801 } |
| 796 } | 802 } |
| 797 } else { | 803 } else { |
| 798 CloseOperationComplete(); | 804 CloseOperationComplete(); |
| 799 } | 805 } |
| 800 } | 806 } |
| 801 | 807 |
| 802 void SimpleEntryImpl::ReadDataInternal(int stream_index, | 808 void SimpleEntryImpl::ReadDataInternal(int stream_index, |
| 803 int offset, | 809 int offset, |
| 804 net::IOBuffer* buf, | 810 net::IOBuffer* buf, |
| 805 int buf_len, | 811 int buf_len, |
| 806 const CompletionCallback& callback) { | 812 const CompletionCallback& callback) { |
| 807 DCHECK(io_thread_checker_.CalledOnValidThread()); | 813 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 808 ScopedOperationRunner operation_runner(this); | 814 ScopedOperationRunner operation_runner(this); |
| 809 | 815 |
| 810 if (net_log_.IsLogging()) { | 816 if (net_log_.IsLogging()) { |
| 811 net_log_.AddEvent( | 817 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_BEGIN, |
| 812 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_BEGIN, | 818 CreateNetLogReadWriteDataCallback( |
| 813 CreateNetLogReadWriteDataCallback(stream_index, offset, buf_len, | 819 stream_index, offset, buf_len, false)); |
| 814 false)); | |
| 815 } | 820 } |
| 816 | 821 |
| 817 if (state_ == STATE_FAILURE || state_ == STATE_UNINITIALIZED) { | 822 if (state_ == STATE_FAILURE || state_ == STATE_UNINITIALIZED) { |
| 818 if (!callback.is_null()) { | 823 if (!callback.is_null()) { |
| 819 RecordReadResult(cache_type_, READ_RESULT_BAD_STATE); | 824 RecordReadResult(cache_type_, READ_RESULT_BAD_STATE); |
| 820 // Note that the API states that client-provided callbacks for entry-level | 825 // Note that the API states that client-provided callbacks for entry-level |
| 821 // (i.e. non-backend) operations (e.g. read, write) are invoked even if | 826 // (i.e. non-backend) operations (e.g. read, write) are invoked even if |
| 822 // the backend was already destroyed. | 827 // the backend was already destroyed. |
| 823 MessageLoopProxy::current()->PostTask( | 828 MessageLoopProxy::current()->PostTask( |
| 824 FROM_HERE, base::Bind(callback, net::ERR_FAILED)); | 829 FROM_HERE, base::Bind(callback, net::ERR_FAILED)); |
| 825 } | 830 } |
| 826 if (net_log_.IsLogging()) { | 831 if (net_log_.IsLogging()) { |
| 827 net_log_.AddEvent( | 832 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, |
| 828 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, | 833 CreateNetLogReadWriteCompleteCallback(net::ERR_FAILED)); |
| 829 CreateNetLogReadWriteCompleteCallback(net::ERR_FAILED)); | |
| 830 } | 834 } |
| 831 return; | 835 return; |
| 832 } | 836 } |
| 833 DCHECK_EQ(STATE_READY, state_); | 837 DCHECK_EQ(STATE_READY, state_); |
| 834 if (offset >= GetDataSize(stream_index) || offset < 0 || !buf_len) { | 838 if (offset >= GetDataSize(stream_index) || offset < 0 || !buf_len) { |
| 835 RecordReadResult(cache_type_, READ_RESULT_FAST_EMPTY_RETURN); | 839 RecordReadResult(cache_type_, READ_RESULT_FAST_EMPTY_RETURN); |
| 836 // If there is nothing to read, we bail out before setting state_ to | 840 // If there is nothing to read, we bail out before setting state_ to |
| 837 // STATE_IO_PENDING. | 841 // STATE_IO_PENDING. |
| 838 if (!callback.is_null()) | 842 if (!callback.is_null()) |
| 839 MessageLoopProxy::current()->PostTask(FROM_HERE, base::Bind(callback, 0)); | 843 MessageLoopProxy::current()->PostTask(FROM_HERE, base::Bind(callback, 0)); |
| (...skipping 11 matching lines...) Expand all Loading... |
| 851 } | 855 } |
| 852 return; | 856 return; |
| 853 } | 857 } |
| 854 | 858 |
| 855 state_ = STATE_IO_PENDING; | 859 state_ = STATE_IO_PENDING; |
| 856 if (!doomed_ && backend_.get()) | 860 if (!doomed_ && backend_.get()) |
| 857 backend_->index()->UseIfExists(entry_hash_); | 861 backend_->index()->UseIfExists(entry_hash_); |
| 858 | 862 |
| 859 scoped_ptr<uint32> read_crc32(new uint32()); | 863 scoped_ptr<uint32> read_crc32(new uint32()); |
| 860 scoped_ptr<int> result(new int()); | 864 scoped_ptr<int> result(new int()); |
| 861 scoped_ptr<SimpleEntryStat> entry_stat( | 865 scoped_ptr<SimpleEntryStat> entry_stat(new SimpleEntryStat( |
| 862 new SimpleEntryStat(last_used_, last_modified_, data_size_, | 866 last_used_, last_modified_, data_size_, sparse_data_size_)); |
| 863 sparse_data_size_)); | |
| 864 Closure task = base::Bind( | 867 Closure task = base::Bind( |
| 865 &SimpleSynchronousEntry::ReadData, | 868 &SimpleSynchronousEntry::ReadData, |
| 866 base::Unretained(synchronous_entry_), | 869 base::Unretained(synchronous_entry_), |
| 867 SimpleSynchronousEntry::EntryOperationData(stream_index, offset, buf_len), | 870 SimpleSynchronousEntry::EntryOperationData(stream_index, offset, buf_len), |
| 868 make_scoped_refptr(buf), | 871 make_scoped_refptr(buf), |
| 869 read_crc32.get(), | 872 read_crc32.get(), |
| 870 entry_stat.get(), | 873 entry_stat.get(), |
| 871 result.get()); | 874 result.get()); |
| 872 Closure reply = base::Bind(&SimpleEntryImpl::ReadOperationComplete, | 875 Closure reply = base::Bind(&SimpleEntryImpl::ReadOperationComplete, |
| 873 this, | 876 this, |
| 874 stream_index, | 877 stream_index, |
| 875 offset, | 878 offset, |
| 876 callback, | 879 callback, |
| 877 base::Passed(&read_crc32), | 880 base::Passed(&read_crc32), |
| 878 base::Passed(&entry_stat), | 881 base::Passed(&entry_stat), |
| 879 base::Passed(&result)); | 882 base::Passed(&result)); |
| 880 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 883 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 881 } | 884 } |
| 882 | 885 |
| 883 void SimpleEntryImpl::WriteDataInternal(int stream_index, | 886 void SimpleEntryImpl::WriteDataInternal(int stream_index, |
| 884 int offset, | 887 int offset, |
| 885 net::IOBuffer* buf, | 888 net::IOBuffer* buf, |
| 886 int buf_len, | 889 int buf_len, |
| 887 const CompletionCallback& callback, | 890 const CompletionCallback& callback, |
| 888 bool truncate) { | 891 bool truncate) { |
| 889 DCHECK(io_thread_checker_.CalledOnValidThread()); | 892 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 890 ScopedOperationRunner operation_runner(this); | 893 ScopedOperationRunner operation_runner(this); |
| 891 | 894 |
| 892 if (net_log_.IsLogging()) { | 895 if (net_log_.IsLogging()) { |
| 893 net_log_.AddEvent( | 896 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_BEGIN, |
| 894 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_BEGIN, | 897 CreateNetLogReadWriteDataCallback( |
| 895 CreateNetLogReadWriteDataCallback(stream_index, offset, buf_len, | 898 stream_index, offset, buf_len, truncate)); |
| 896 truncate)); | |
| 897 } | 899 } |
| 898 | 900 |
| 899 if (state_ == STATE_FAILURE || state_ == STATE_UNINITIALIZED) { | 901 if (state_ == STATE_FAILURE || state_ == STATE_UNINITIALIZED) { |
| 900 RecordWriteResult(cache_type_, WRITE_RESULT_BAD_STATE); | 902 RecordWriteResult(cache_type_, WRITE_RESULT_BAD_STATE); |
| 901 if (net_log_.IsLogging()) { | 903 if (net_log_.IsLogging()) { |
| 902 net_log_.AddEvent( | 904 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, |
| 903 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, | 905 CreateNetLogReadWriteCompleteCallback(net::ERR_FAILED)); |
| 904 CreateNetLogReadWriteCompleteCallback(net::ERR_FAILED)); | |
| 905 } | 906 } |
| 906 if (!callback.is_null()) { | 907 if (!callback.is_null()) { |
| 907 MessageLoopProxy::current()->PostTask( | 908 MessageLoopProxy::current()->PostTask( |
| 908 FROM_HERE, base::Bind(callback, net::ERR_FAILED)); | 909 FROM_HERE, base::Bind(callback, net::ERR_FAILED)); |
| 909 } | 910 } |
| 910 // |this| may be destroyed after return here. | 911 // |this| may be destroyed after return here. |
| 911 return; | 912 return; |
| 912 } | 913 } |
| 913 | 914 |
| 914 DCHECK_EQ(STATE_READY, state_); | 915 DCHECK_EQ(STATE_READY, state_); |
| 915 | 916 |
| 916 // Since stream 0 data is kept in memory, it will be written immediatly. | 917 // Since stream 0 data is kept in memory, it will be written immediatly. |
| 917 if (stream_index == 0) { | 918 if (stream_index == 0) { |
| 918 int ret_value = SetStream0Data(buf, offset, buf_len, truncate); | 919 int ret_value = SetStream0Data(buf, offset, buf_len, truncate); |
| 919 if (!callback.is_null()) { | 920 if (!callback.is_null()) { |
| 920 MessageLoopProxy::current()->PostTask(FROM_HERE, | 921 MessageLoopProxy::current()->PostTask(FROM_HERE, |
| 921 base::Bind(callback, ret_value)); | 922 base::Bind(callback, ret_value)); |
| 922 } | 923 } |
| 923 return; | 924 return; |
| 924 } | 925 } |
| 925 | 926 |
| 926 // Ignore zero-length writes that do not change the file size. | 927 // Ignore zero-length writes that do not change the file size. |
| 927 if (buf_len == 0) { | 928 if (buf_len == 0) { |
| 928 int32 data_size = data_size_[stream_index]; | 929 int32 data_size = data_size_[stream_index]; |
| 929 if (truncate ? (offset == data_size) : (offset <= data_size)) { | 930 if (truncate ? (offset == data_size) : (offset <= data_size)) { |
| 930 RecordWriteResult(cache_type_, WRITE_RESULT_FAST_EMPTY_RETURN); | 931 RecordWriteResult(cache_type_, WRITE_RESULT_FAST_EMPTY_RETURN); |
| 931 if (!callback.is_null()) { | 932 if (!callback.is_null()) { |
| 932 MessageLoopProxy::current()->PostTask(FROM_HERE, base::Bind( | 933 MessageLoopProxy::current()->PostTask(FROM_HERE, |
| 933 callback, 0)); | 934 base::Bind(callback, 0)); |
| 934 } | 935 } |
| 935 return; | 936 return; |
| 936 } | 937 } |
| 937 } | 938 } |
| 938 state_ = STATE_IO_PENDING; | 939 state_ = STATE_IO_PENDING; |
| 939 if (!doomed_ && backend_.get()) | 940 if (!doomed_ && backend_.get()) |
| 940 backend_->index()->UseIfExists(entry_hash_); | 941 backend_->index()->UseIfExists(entry_hash_); |
| 941 | 942 |
| 942 AdvanceCrc(buf, offset, buf_len, stream_index); | 943 AdvanceCrc(buf, offset, buf_len, stream_index); |
| 943 | 944 |
| 944 // |entry_stat| needs to be initialized before modifying |data_size_|. | 945 // |entry_stat| needs to be initialized before modifying |data_size_|. |
| 945 scoped_ptr<SimpleEntryStat> entry_stat( | 946 scoped_ptr<SimpleEntryStat> entry_stat(new SimpleEntryStat( |
| 946 new SimpleEntryStat(last_used_, last_modified_, data_size_, | 947 last_used_, last_modified_, data_size_, sparse_data_size_)); |
| 947 sparse_data_size_)); | |
| 948 if (truncate) { | 948 if (truncate) { |
| 949 data_size_[stream_index] = offset + buf_len; | 949 data_size_[stream_index] = offset + buf_len; |
| 950 } else { | 950 } else { |
| 951 data_size_[stream_index] = std::max(offset + buf_len, | 951 data_size_[stream_index] = |
| 952 GetDataSize(stream_index)); | 952 std::max(offset + buf_len, GetDataSize(stream_index)); |
| 953 } | 953 } |
| 954 | 954 |
| 955 // Since we don't know the correct values for |last_used_| and | 955 // Since we don't know the correct values for |last_used_| and |
| 956 // |last_modified_| yet, we make this approximation. | 956 // |last_modified_| yet, we make this approximation. |
| 957 last_used_ = last_modified_ = base::Time::Now(); | 957 last_used_ = last_modified_ = base::Time::Now(); |
| 958 | 958 |
| 959 have_written_[stream_index] = true; | 959 have_written_[stream_index] = true; |
| 960 // Writing on stream 1 affects the placement of stream 0 in the file, the EOF | 960 // Writing on stream 1 affects the placement of stream 0 in the file, the EOF |
| 961 // record will have to be rewritten. | 961 // record will have to be rewritten. |
| 962 if (stream_index == 1) | 962 if (stream_index == 1) |
| 963 have_written_[0] = true; | 963 have_written_[0] = true; |
| 964 | 964 |
| 965 scoped_ptr<int> result(new int()); | 965 scoped_ptr<int> result(new int()); |
| 966 Closure task = base::Bind(&SimpleSynchronousEntry::WriteData, | 966 Closure task = |
| 967 base::Unretained(synchronous_entry_), | 967 base::Bind(&SimpleSynchronousEntry::WriteData, |
| 968 SimpleSynchronousEntry::EntryOperationData( | 968 base::Unretained(synchronous_entry_), |
| 969 stream_index, offset, buf_len, truncate, | 969 SimpleSynchronousEntry::EntryOperationData( |
| 970 doomed_), | 970 stream_index, offset, buf_len, truncate, doomed_), |
| 971 make_scoped_refptr(buf), | 971 make_scoped_refptr(buf), |
| 972 entry_stat.get(), | 972 entry_stat.get(), |
| 973 result.get()); | 973 result.get()); |
| 974 Closure reply = base::Bind(&SimpleEntryImpl::WriteOperationComplete, | 974 Closure reply = base::Bind(&SimpleEntryImpl::WriteOperationComplete, |
| 975 this, | 975 this, |
| 976 stream_index, | 976 stream_index, |
| 977 callback, | 977 callback, |
| 978 base::Passed(&entry_stat), | 978 base::Passed(&entry_stat), |
| 979 base::Passed(&result)); | 979 base::Passed(&result)); |
| 980 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 980 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 981 } | 981 } |
| 982 | 982 |
| 983 void SimpleEntryImpl::ReadSparseDataInternal( | 983 void SimpleEntryImpl::ReadSparseDataInternal( |
| 984 int64 sparse_offset, | 984 int64 sparse_offset, |
| 985 net::IOBuffer* buf, | 985 net::IOBuffer* buf, |
| 986 int buf_len, | 986 int buf_len, |
| 987 const CompletionCallback& callback) { | 987 const CompletionCallback& callback) { |
| 988 DCHECK(io_thread_checker_.CalledOnValidThread()); | 988 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 989 ScopedOperationRunner operation_runner(this); | 989 ScopedOperationRunner operation_runner(this); |
| 990 | 990 |
| 991 DCHECK_EQ(STATE_READY, state_); | 991 DCHECK_EQ(STATE_READY, state_); |
| 992 state_ = STATE_IO_PENDING; | 992 state_ = STATE_IO_PENDING; |
| 993 | 993 |
| 994 scoped_ptr<int> result(new int()); | 994 scoped_ptr<int> result(new int()); |
| 995 scoped_ptr<base::Time> last_used(new base::Time()); | 995 scoped_ptr<base::Time> last_used(new base::Time()); |
| 996 Closure task = base::Bind(&SimpleSynchronousEntry::ReadSparseData, | 996 Closure task = base::Bind( |
| 997 base::Unretained(synchronous_entry_), | 997 &SimpleSynchronousEntry::ReadSparseData, |
| 998 SimpleSynchronousEntry::EntryOperationData( | 998 base::Unretained(synchronous_entry_), |
| 999 sparse_offset, buf_len), | 999 SimpleSynchronousEntry::EntryOperationData(sparse_offset, buf_len), |
| 1000 make_scoped_refptr(buf), | 1000 make_scoped_refptr(buf), |
| 1001 last_used.get(), | 1001 last_used.get(), |
| 1002 result.get()); | 1002 result.get()); |
| 1003 Closure reply = base::Bind(&SimpleEntryImpl::ReadSparseOperationComplete, | 1003 Closure reply = base::Bind(&SimpleEntryImpl::ReadSparseOperationComplete, |
| 1004 this, | 1004 this, |
| 1005 callback, | 1005 callback, |
| 1006 base::Passed(&last_used), | 1006 base::Passed(&last_used), |
| 1007 base::Passed(&result)); | 1007 base::Passed(&result)); |
| 1008 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 1008 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 1009 } | 1009 } |
| 1010 | 1010 |
| 1011 void SimpleEntryImpl::WriteSparseDataInternal( | 1011 void SimpleEntryImpl::WriteSparseDataInternal( |
| 1012 int64 sparse_offset, | 1012 int64 sparse_offset, |
| 1013 net::IOBuffer* buf, | 1013 net::IOBuffer* buf, |
| 1014 int buf_len, | 1014 int buf_len, |
| 1015 const CompletionCallback& callback) { | 1015 const CompletionCallback& callback) { |
| 1016 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1016 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1017 ScopedOperationRunner operation_runner(this); | 1017 ScopedOperationRunner operation_runner(this); |
| 1018 | 1018 |
| 1019 DCHECK_EQ(STATE_READY, state_); | 1019 DCHECK_EQ(STATE_READY, state_); |
| 1020 state_ = STATE_IO_PENDING; | 1020 state_ = STATE_IO_PENDING; |
| 1021 | 1021 |
| 1022 int64 max_sparse_data_size = kint64max; | 1022 int64 max_sparse_data_size = kint64max; |
| 1023 if (backend_.get()) { | 1023 if (backend_.get()) { |
| 1024 int64 max_cache_size = backend_->index()->max_size(); | 1024 int64 max_cache_size = backend_->index()->max_size(); |
| 1025 max_sparse_data_size = max_cache_size / kMaxSparseDataSizeDivisor; | 1025 max_sparse_data_size = max_cache_size / kMaxSparseDataSizeDivisor; |
| 1026 } | 1026 } |
| 1027 | 1027 |
| 1028 scoped_ptr<SimpleEntryStat> entry_stat( | 1028 scoped_ptr<SimpleEntryStat> entry_stat(new SimpleEntryStat( |
| 1029 new SimpleEntryStat(last_used_, last_modified_, data_size_, | 1029 last_used_, last_modified_, data_size_, sparse_data_size_)); |
| 1030 sparse_data_size_)); | |
| 1031 | 1030 |
| 1032 last_used_ = last_modified_ = base::Time::Now(); | 1031 last_used_ = last_modified_ = base::Time::Now(); |
| 1033 | 1032 |
| 1034 scoped_ptr<int> result(new int()); | 1033 scoped_ptr<int> result(new int()); |
| 1035 Closure task = base::Bind(&SimpleSynchronousEntry::WriteSparseData, | 1034 Closure task = base::Bind( |
| 1036 base::Unretained(synchronous_entry_), | 1035 &SimpleSynchronousEntry::WriteSparseData, |
| 1037 SimpleSynchronousEntry::EntryOperationData( | 1036 base::Unretained(synchronous_entry_), |
| 1038 sparse_offset, buf_len), | 1037 SimpleSynchronousEntry::EntryOperationData(sparse_offset, buf_len), |
| 1039 make_scoped_refptr(buf), | 1038 make_scoped_refptr(buf), |
| 1040 max_sparse_data_size, | 1039 max_sparse_data_size, |
| 1041 entry_stat.get(), | 1040 entry_stat.get(), |
| 1042 result.get()); | 1041 result.get()); |
| 1043 Closure reply = base::Bind(&SimpleEntryImpl::WriteSparseOperationComplete, | 1042 Closure reply = base::Bind(&SimpleEntryImpl::WriteSparseOperationComplete, |
| 1044 this, | 1043 this, |
| 1045 callback, | 1044 callback, |
| 1046 base::Passed(&entry_stat), | 1045 base::Passed(&entry_stat), |
| 1047 base::Passed(&result)); | 1046 base::Passed(&result)); |
| 1048 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 1047 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 1049 } | 1048 } |
| 1050 | 1049 |
| 1051 void SimpleEntryImpl::GetAvailableRangeInternal( | 1050 void SimpleEntryImpl::GetAvailableRangeInternal( |
| 1052 int64 sparse_offset, | 1051 int64 sparse_offset, |
| 1053 int len, | 1052 int len, |
| 1054 int64* out_start, | 1053 int64* out_start, |
| 1055 const CompletionCallback& callback) { | 1054 const CompletionCallback& callback) { |
| 1056 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1055 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1057 ScopedOperationRunner operation_runner(this); | 1056 ScopedOperationRunner operation_runner(this); |
| 1058 | 1057 |
| 1059 DCHECK_EQ(STATE_READY, state_); | 1058 DCHECK_EQ(STATE_READY, state_); |
| 1060 state_ = STATE_IO_PENDING; | 1059 state_ = STATE_IO_PENDING; |
| 1061 | 1060 |
| 1062 scoped_ptr<int> result(new int()); | 1061 scoped_ptr<int> result(new int()); |
| 1063 Closure task = base::Bind(&SimpleSynchronousEntry::GetAvailableRange, | 1062 Closure task = |
| 1064 base::Unretained(synchronous_entry_), | 1063 base::Bind(&SimpleSynchronousEntry::GetAvailableRange, |
| 1065 SimpleSynchronousEntry::EntryOperationData( | 1064 base::Unretained(synchronous_entry_), |
| 1066 sparse_offset, len), | 1065 SimpleSynchronousEntry::EntryOperationData(sparse_offset, len), |
| 1067 out_start, | 1066 out_start, |
| 1068 result.get()); | 1067 result.get()); |
| 1069 Closure reply = base::Bind( | 1068 Closure reply = |
| 1070 &SimpleEntryImpl::GetAvailableRangeOperationComplete, | 1069 base::Bind(&SimpleEntryImpl::GetAvailableRangeOperationComplete, |
| 1071 this, | 1070 this, |
| 1072 callback, | 1071 callback, |
| 1073 base::Passed(&result)); | 1072 base::Passed(&result)); |
| 1074 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 1073 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 1075 } | 1074 } |
| 1076 | 1075 |
| 1077 void SimpleEntryImpl::DoomEntryInternal(const CompletionCallback& callback) { | 1076 void SimpleEntryImpl::DoomEntryInternal(const CompletionCallback& callback) { |
| 1078 PostTaskAndReplyWithResult( | 1077 PostTaskAndReplyWithResult( |
| 1079 worker_pool_, FROM_HERE, | 1078 worker_pool_, |
| 1079 FROM_HERE, |
| 1080 base::Bind(&SimpleSynchronousEntry::DoomEntry, path_, entry_hash_), | 1080 base::Bind(&SimpleSynchronousEntry::DoomEntry, path_, entry_hash_), |
| 1081 base::Bind(&SimpleEntryImpl::DoomOperationComplete, this, callback, | 1081 base::Bind( |
| 1082 state_)); | 1082 &SimpleEntryImpl::DoomOperationComplete, this, callback, state_)); |
| 1083 state_ = STATE_IO_PENDING; | 1083 state_ = STATE_IO_PENDING; |
| 1084 } | 1084 } |
| 1085 | 1085 |
| 1086 void SimpleEntryImpl::CreationOperationComplete( | 1086 void SimpleEntryImpl::CreationOperationComplete( |
| 1087 const CompletionCallback& completion_callback, | 1087 const CompletionCallback& completion_callback, |
| 1088 const base::TimeTicks& start_time, | 1088 const base::TimeTicks& start_time, |
| 1089 scoped_ptr<SimpleEntryCreationResults> in_results, | 1089 scoped_ptr<SimpleEntryCreationResults> in_results, |
| 1090 Entry** out_entry, | 1090 Entry** out_entry, |
| 1091 net::NetLog::EventType end_event_type) { | 1091 net::NetLog::EventType end_event_type) { |
| 1092 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1092 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1093 DCHECK_EQ(state_, STATE_IO_PENDING); | 1093 DCHECK_EQ(state_, STATE_IO_PENDING); |
| 1094 DCHECK(in_results); | 1094 DCHECK(in_results); |
| 1095 ScopedOperationRunner operation_runner(this); | 1095 ScopedOperationRunner operation_runner(this); |
| 1096 SIMPLE_CACHE_UMA(BOOLEAN, | 1096 SIMPLE_CACHE_UMA(BOOLEAN, |
| 1097 "EntryCreationResult", cache_type_, | 1097 "EntryCreationResult", |
| 1098 cache_type_, |
| 1098 in_results->result == net::OK); | 1099 in_results->result == net::OK); |
| 1099 if (in_results->result != net::OK) { | 1100 if (in_results->result != net::OK) { |
| 1100 if (in_results->result != net::ERR_FILE_EXISTS) | 1101 if (in_results->result != net::ERR_FILE_EXISTS) |
| 1101 MarkAsDoomed(); | 1102 MarkAsDoomed(); |
| 1102 | 1103 |
| 1103 net_log_.AddEventWithNetErrorCode(end_event_type, net::ERR_FAILED); | 1104 net_log_.AddEventWithNetErrorCode(end_event_type, net::ERR_FAILED); |
| 1104 PostClientCallback(completion_callback, net::ERR_FAILED); | 1105 PostClientCallback(completion_callback, net::ERR_FAILED); |
| 1105 MakeUninitialized(); | 1106 MakeUninitialized(); |
| 1106 return; | 1107 return; |
| 1107 } | 1108 } |
| (...skipping 13 matching lines...) Expand all Loading... |
| 1121 } | 1122 } |
| 1122 if (key_.empty()) { | 1123 if (key_.empty()) { |
| 1123 SetKey(synchronous_entry_->key()); | 1124 SetKey(synchronous_entry_->key()); |
| 1124 } else { | 1125 } else { |
| 1125 // This should only be triggered when creating an entry. The key check in | 1126 // This should only be triggered when creating an entry. The key check in |
| 1126 // the open case is handled in SimpleBackendImpl. | 1127 // the open case is handled in SimpleBackendImpl. |
| 1127 DCHECK_EQ(key_, synchronous_entry_->key()); | 1128 DCHECK_EQ(key_, synchronous_entry_->key()); |
| 1128 } | 1129 } |
| 1129 UpdateDataFromEntryStat(in_results->entry_stat); | 1130 UpdateDataFromEntryStat(in_results->entry_stat); |
| 1130 SIMPLE_CACHE_UMA(TIMES, | 1131 SIMPLE_CACHE_UMA(TIMES, |
| 1131 "EntryCreationTime", cache_type_, | 1132 "EntryCreationTime", |
| 1133 cache_type_, |
| 1132 (base::TimeTicks::Now() - start_time)); | 1134 (base::TimeTicks::Now() - start_time)); |
| 1133 AdjustOpenEntryCountBy(cache_type_, 1); | 1135 AdjustOpenEntryCountBy(cache_type_, 1); |
| 1134 | 1136 |
| 1135 net_log_.AddEvent(end_event_type); | 1137 net_log_.AddEvent(end_event_type); |
| 1136 PostClientCallback(completion_callback, net::OK); | 1138 PostClientCallback(completion_callback, net::OK); |
| 1137 } | 1139 } |
| 1138 | 1140 |
| 1139 void SimpleEntryImpl::EntryOperationComplete( | 1141 void SimpleEntryImpl::EntryOperationComplete( |
| 1140 const CompletionCallback& completion_callback, | 1142 const CompletionCallback& completion_callback, |
| 1141 const SimpleEntryStat& entry_stat, | 1143 const SimpleEntryStat& entry_stat, |
| 1142 scoped_ptr<int> result) { | 1144 scoped_ptr<int> result) { |
| 1143 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1145 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1144 DCHECK(synchronous_entry_); | 1146 DCHECK(synchronous_entry_); |
| 1145 DCHECK_EQ(STATE_IO_PENDING, state_); | 1147 DCHECK_EQ(STATE_IO_PENDING, state_); |
| 1146 DCHECK(result); | 1148 DCHECK(result); |
| 1147 if (*result < 0) { | 1149 if (*result < 0) { |
| 1148 state_ = STATE_FAILURE; | 1150 state_ = STATE_FAILURE; |
| 1149 MarkAsDoomed(); | 1151 MarkAsDoomed(); |
| 1150 } else { | 1152 } else { |
| 1151 state_ = STATE_READY; | 1153 state_ = STATE_READY; |
| 1152 UpdateDataFromEntryStat(entry_stat); | 1154 UpdateDataFromEntryStat(entry_stat); |
| 1153 } | 1155 } |
| 1154 | 1156 |
| 1155 if (!completion_callback.is_null()) { | 1157 if (!completion_callback.is_null()) { |
| 1156 MessageLoopProxy::current()->PostTask(FROM_HERE, base::Bind( | 1158 MessageLoopProxy::current()->PostTask( |
| 1157 completion_callback, *result)); | 1159 FROM_HERE, base::Bind(completion_callback, *result)); |
| 1158 } | 1160 } |
| 1159 RunNextOperationIfNeeded(); | 1161 RunNextOperationIfNeeded(); |
| 1160 } | 1162 } |
| 1161 | 1163 |
| 1162 void SimpleEntryImpl::ReadOperationComplete( | 1164 void SimpleEntryImpl::ReadOperationComplete( |
| 1163 int stream_index, | 1165 int stream_index, |
| 1164 int offset, | 1166 int offset, |
| 1165 const CompletionCallback& completion_callback, | 1167 const CompletionCallback& completion_callback, |
| 1166 scoped_ptr<uint32> read_crc32, | 1168 scoped_ptr<uint32> read_crc32, |
| 1167 scoped_ptr<SimpleEntryStat> entry_stat, | 1169 scoped_ptr<SimpleEntryStat> entry_stat, |
| 1168 scoped_ptr<int> result) { | 1170 scoped_ptr<int> result) { |
| 1169 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1171 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1170 DCHECK(synchronous_entry_); | 1172 DCHECK(synchronous_entry_); |
| 1171 DCHECK_EQ(STATE_IO_PENDING, state_); | 1173 DCHECK_EQ(STATE_IO_PENDING, state_); |
| 1172 DCHECK(read_crc32); | 1174 DCHECK(read_crc32); |
| 1173 DCHECK(result); | 1175 DCHECK(result); |
| 1174 | 1176 |
| 1175 if (*result > 0 && | 1177 if (*result > 0 && |
| 1176 crc_check_state_[stream_index] == CRC_CHECK_NEVER_READ_AT_ALL) { | 1178 crc_check_state_[stream_index] == CRC_CHECK_NEVER_READ_AT_ALL) { |
| 1177 crc_check_state_[stream_index] = CRC_CHECK_NEVER_READ_TO_END; | 1179 crc_check_state_[stream_index] = CRC_CHECK_NEVER_READ_TO_END; |
| 1178 } | 1180 } |
| 1179 | 1181 |
| 1180 if (*result > 0 && crc32s_end_offset_[stream_index] == offset) { | 1182 if (*result > 0 && crc32s_end_offset_[stream_index] == offset) { |
| 1181 uint32 current_crc = offset == 0 ? crc32(0, Z_NULL, 0) | 1183 uint32 current_crc = |
| 1182 : crc32s_[stream_index]; | 1184 offset == 0 ? crc32(0, Z_NULL, 0) : crc32s_[stream_index]; |
| 1183 crc32s_[stream_index] = crc32_combine(current_crc, *read_crc32, *result); | 1185 crc32s_[stream_index] = crc32_combine(current_crc, *read_crc32, *result); |
| 1184 crc32s_end_offset_[stream_index] += *result; | 1186 crc32s_end_offset_[stream_index] += *result; |
| 1185 if (!have_written_[stream_index] && | 1187 if (!have_written_[stream_index] && |
| 1186 GetDataSize(stream_index) == crc32s_end_offset_[stream_index]) { | 1188 GetDataSize(stream_index) == crc32s_end_offset_[stream_index]) { |
| 1187 // We have just read a file from start to finish, and so we have | 1189 // We have just read a file from start to finish, and so we have |
| 1188 // computed a crc of the entire file. We can check it now. If a cache | 1190 // computed a crc of the entire file. We can check it now. If a cache |
| 1189 // entry has a single reader, the normal pattern is to read from start | 1191 // entry has a single reader, the normal pattern is to read from start |
| 1190 // to finish. | 1192 // to finish. |
| 1191 | 1193 |
| 1192 // Other cases are possible. In the case of two readers on the same | 1194 // Other cases are possible. In the case of two readers on the same |
| 1193 // entry, one reader can be behind the other. In this case we compute | 1195 // entry, one reader can be behind the other. In this case we compute |
| 1194 // the crc as the most advanced reader progresses, and check it for | 1196 // the crc as the most advanced reader progresses, and check it for |
| 1195 // both readers as they read the last byte. | 1197 // both readers as they read the last byte. |
| 1196 | 1198 |
| 1197 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CHECKSUM_BEGIN); | 1199 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CHECKSUM_BEGIN); |
| 1198 | 1200 |
| 1199 scoped_ptr<int> new_result(new int()); | 1201 scoped_ptr<int> new_result(new int()); |
| 1200 Closure task = base::Bind(&SimpleSynchronousEntry::CheckEOFRecord, | 1202 Closure task = base::Bind(&SimpleSynchronousEntry::CheckEOFRecord, |
| 1201 base::Unretained(synchronous_entry_), | 1203 base::Unretained(synchronous_entry_), |
| 1202 stream_index, | 1204 stream_index, |
| 1203 *entry_stat, | 1205 *entry_stat, |
| 1204 crc32s_[stream_index], | 1206 crc32s_[stream_index], |
| 1205 new_result.get()); | 1207 new_result.get()); |
| 1206 Closure reply = base::Bind(&SimpleEntryImpl::ChecksumOperationComplete, | 1208 Closure reply = base::Bind(&SimpleEntryImpl::ChecksumOperationComplete, |
| 1207 this, *result, stream_index, | 1209 this, |
| 1210 *result, |
| 1211 stream_index, |
| 1208 completion_callback, | 1212 completion_callback, |
| 1209 base::Passed(&new_result)); | 1213 base::Passed(&new_result)); |
| 1210 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); | 1214 worker_pool_->PostTaskAndReply(FROM_HERE, task, reply); |
| 1211 crc_check_state_[stream_index] = CRC_CHECK_DONE; | 1215 crc_check_state_[stream_index] = CRC_CHECK_DONE; |
| 1212 return; | 1216 return; |
| 1213 } | 1217 } |
| 1214 } | 1218 } |
| 1215 | 1219 |
| 1216 if (*result < 0) { | 1220 if (*result < 0) { |
| 1217 crc32s_end_offset_[stream_index] = 0; | 1221 crc32s_end_offset_[stream_index] = 0; |
| 1218 } | 1222 } |
| 1219 | 1223 |
| 1220 if (*result < 0) { | 1224 if (*result < 0) { |
| 1221 RecordReadResult(cache_type_, READ_RESULT_SYNC_READ_FAILURE); | 1225 RecordReadResult(cache_type_, READ_RESULT_SYNC_READ_FAILURE); |
| 1222 } else { | 1226 } else { |
| 1223 RecordReadResult(cache_type_, READ_RESULT_SUCCESS); | 1227 RecordReadResult(cache_type_, READ_RESULT_SUCCESS); |
| 1224 if (crc_check_state_[stream_index] == CRC_CHECK_NEVER_READ_TO_END && | 1228 if (crc_check_state_[stream_index] == CRC_CHECK_NEVER_READ_TO_END && |
| 1225 offset + *result == GetDataSize(stream_index)) { | 1229 offset + *result == GetDataSize(stream_index)) { |
| 1226 crc_check_state_[stream_index] = CRC_CHECK_NOT_DONE; | 1230 crc_check_state_[stream_index] = CRC_CHECK_NOT_DONE; |
| 1227 } | 1231 } |
| 1228 } | 1232 } |
| 1229 if (net_log_.IsLogging()) { | 1233 if (net_log_.IsLogging()) { |
| 1230 net_log_.AddEvent( | 1234 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, |
| 1231 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, | 1235 CreateNetLogReadWriteCompleteCallback(*result)); |
| 1232 CreateNetLogReadWriteCompleteCallback(*result)); | |
| 1233 } | 1236 } |
| 1234 | 1237 |
| 1235 EntryOperationComplete(completion_callback, *entry_stat, result.Pass()); | 1238 EntryOperationComplete(completion_callback, *entry_stat, result.Pass()); |
| 1236 } | 1239 } |
| 1237 | 1240 |
| 1238 void SimpleEntryImpl::WriteOperationComplete( | 1241 void SimpleEntryImpl::WriteOperationComplete( |
| 1239 int stream_index, | 1242 int stream_index, |
| 1240 const CompletionCallback& completion_callback, | 1243 const CompletionCallback& completion_callback, |
| 1241 scoped_ptr<SimpleEntryStat> entry_stat, | 1244 scoped_ptr<SimpleEntryStat> entry_stat, |
| 1242 scoped_ptr<int> result) { | 1245 scoped_ptr<int> result) { |
| 1243 if (*result >= 0) | 1246 if (*result >= 0) |
| 1244 RecordWriteResult(cache_type_, WRITE_RESULT_SUCCESS); | 1247 RecordWriteResult(cache_type_, WRITE_RESULT_SUCCESS); |
| 1245 else | 1248 else |
| 1246 RecordWriteResult(cache_type_, WRITE_RESULT_SYNC_WRITE_FAILURE); | 1249 RecordWriteResult(cache_type_, WRITE_RESULT_SYNC_WRITE_FAILURE); |
| 1247 if (net_log_.IsLogging()) { | 1250 if (net_log_.IsLogging()) { |
| 1248 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, | 1251 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_WRITE_END, |
| 1249 CreateNetLogReadWriteCompleteCallback(*result)); | 1252 CreateNetLogReadWriteCompleteCallback(*result)); |
| 1250 } | 1253 } |
| 1251 | 1254 |
| 1252 if (*result < 0) { | 1255 if (*result < 0) { |
| 1253 crc32s_end_offset_[stream_index] = 0; | 1256 crc32s_end_offset_[stream_index] = 0; |
| 1254 } | 1257 } |
| 1255 | 1258 |
| 1256 EntryOperationComplete(completion_callback, *entry_stat, result.Pass()); | 1259 EntryOperationComplete(completion_callback, *entry_stat, result.Pass()); |
| 1257 } | 1260 } |
| 1258 | 1261 |
| 1259 void SimpleEntryImpl::ReadSparseOperationComplete( | 1262 void SimpleEntryImpl::ReadSparseOperationComplete( |
| 1260 const CompletionCallback& completion_callback, | 1263 const CompletionCallback& completion_callback, |
| 1261 scoped_ptr<base::Time> last_used, | 1264 scoped_ptr<base::Time> last_used, |
| 1262 scoped_ptr<int> result) { | 1265 scoped_ptr<int> result) { |
| 1263 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1266 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1264 DCHECK(synchronous_entry_); | 1267 DCHECK(synchronous_entry_); |
| 1265 DCHECK(result); | 1268 DCHECK(result); |
| 1266 | 1269 |
| 1267 SimpleEntryStat entry_stat(*last_used, last_modified_, data_size_, | 1270 SimpleEntryStat entry_stat( |
| 1268 sparse_data_size_); | 1271 *last_used, last_modified_, data_size_, sparse_data_size_); |
| 1269 EntryOperationComplete(completion_callback, entry_stat, result.Pass()); | 1272 EntryOperationComplete(completion_callback, entry_stat, result.Pass()); |
| 1270 } | 1273 } |
| 1271 | 1274 |
| 1272 void SimpleEntryImpl::WriteSparseOperationComplete( | 1275 void SimpleEntryImpl::WriteSparseOperationComplete( |
| 1273 const CompletionCallback& completion_callback, | 1276 const CompletionCallback& completion_callback, |
| 1274 scoped_ptr<SimpleEntryStat> entry_stat, | 1277 scoped_ptr<SimpleEntryStat> entry_stat, |
| 1275 scoped_ptr<int> result) { | 1278 scoped_ptr<int> result) { |
| 1276 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1279 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1277 DCHECK(synchronous_entry_); | 1280 DCHECK(synchronous_entry_); |
| 1278 DCHECK(result); | 1281 DCHECK(result); |
| 1279 | 1282 |
| 1280 EntryOperationComplete(completion_callback, *entry_stat, result.Pass()); | 1283 EntryOperationComplete(completion_callback, *entry_stat, result.Pass()); |
| 1281 } | 1284 } |
| 1282 | 1285 |
| 1283 void SimpleEntryImpl::GetAvailableRangeOperationComplete( | 1286 void SimpleEntryImpl::GetAvailableRangeOperationComplete( |
| 1284 const CompletionCallback& completion_callback, | 1287 const CompletionCallback& completion_callback, |
| 1285 scoped_ptr<int> result) { | 1288 scoped_ptr<int> result) { |
| 1286 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1289 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1287 DCHECK(synchronous_entry_); | 1290 DCHECK(synchronous_entry_); |
| 1288 DCHECK(result); | 1291 DCHECK(result); |
| 1289 | 1292 |
| 1290 SimpleEntryStat entry_stat(last_used_, last_modified_, data_size_, | 1293 SimpleEntryStat entry_stat( |
| 1291 sparse_data_size_); | 1294 last_used_, last_modified_, data_size_, sparse_data_size_); |
| 1292 EntryOperationComplete(completion_callback, entry_stat, result.Pass()); | 1295 EntryOperationComplete(completion_callback, entry_stat, result.Pass()); |
| 1293 } | 1296 } |
| 1294 | 1297 |
| 1295 void SimpleEntryImpl::DoomOperationComplete( | 1298 void SimpleEntryImpl::DoomOperationComplete(const CompletionCallback& callback, |
| 1296 const CompletionCallback& callback, | 1299 State state_to_restore, |
| 1297 State state_to_restore, | 1300 int result) { |
| 1298 int result) { | |
| 1299 state_ = state_to_restore; | 1301 state_ = state_to_restore; |
| 1300 if (!callback.is_null()) | 1302 if (!callback.is_null()) |
| 1301 callback.Run(result); | 1303 callback.Run(result); |
| 1302 RunNextOperationIfNeeded(); | 1304 RunNextOperationIfNeeded(); |
| 1303 if (backend_) | 1305 if (backend_) |
| 1304 backend_->OnDoomComplete(entry_hash_); | 1306 backend_->OnDoomComplete(entry_hash_); |
| 1305 } | 1307 } |
| 1306 | 1308 |
| 1307 void SimpleEntryImpl::ChecksumOperationComplete( | 1309 void SimpleEntryImpl::ChecksumOperationComplete( |
| 1308 int orig_result, | 1310 int orig_result, |
| 1309 int stream_index, | 1311 int stream_index, |
| 1310 const CompletionCallback& completion_callback, | 1312 const CompletionCallback& completion_callback, |
| 1311 scoped_ptr<int> result) { | 1313 scoped_ptr<int> result) { |
| 1312 DCHECK(io_thread_checker_.CalledOnValidThread()); | 1314 DCHECK(io_thread_checker_.CalledOnValidThread()); |
| 1313 DCHECK(synchronous_entry_); | 1315 DCHECK(synchronous_entry_); |
| 1314 DCHECK_EQ(STATE_IO_PENDING, state_); | 1316 DCHECK_EQ(STATE_IO_PENDING, state_); |
| 1315 DCHECK(result); | 1317 DCHECK(result); |
| 1316 | 1318 |
| 1317 if (net_log_.IsLogging()) { | 1319 if (net_log_.IsLogging()) { |
| 1318 net_log_.AddEventWithNetErrorCode( | 1320 net_log_.AddEventWithNetErrorCode( |
| 1319 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CHECKSUM_END, | 1321 net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CHECKSUM_END, *result); |
| 1320 *result); | |
| 1321 } | 1322 } |
| 1322 | 1323 |
| 1323 if (*result == net::OK) { | 1324 if (*result == net::OK) { |
| 1324 *result = orig_result; | 1325 *result = orig_result; |
| 1325 if (orig_result >= 0) | 1326 if (orig_result >= 0) |
| 1326 RecordReadResult(cache_type_, READ_RESULT_SUCCESS); | 1327 RecordReadResult(cache_type_, READ_RESULT_SUCCESS); |
| 1327 else | 1328 else |
| 1328 RecordReadResult(cache_type_, READ_RESULT_SYNC_READ_FAILURE); | 1329 RecordReadResult(cache_type_, READ_RESULT_SYNC_READ_FAILURE); |
| 1329 } else { | 1330 } else { |
| 1330 RecordReadResult(cache_type_, READ_RESULT_SYNC_CHECKSUM_FAILURE); | 1331 RecordReadResult(cache_type_, READ_RESULT_SYNC_CHECKSUM_FAILURE); |
| 1331 } | 1332 } |
| 1332 if (net_log_.IsLogging()) { | 1333 if (net_log_.IsLogging()) { |
| 1333 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, | 1334 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_READ_END, |
| 1334 CreateNetLogReadWriteCompleteCallback(*result)); | 1335 CreateNetLogReadWriteCompleteCallback(*result)); |
| 1335 } | 1336 } |
| 1336 | 1337 |
| 1337 SimpleEntryStat entry_stat(last_used_, last_modified_, data_size_, | 1338 SimpleEntryStat entry_stat( |
| 1338 sparse_data_size_); | 1339 last_used_, last_modified_, data_size_, sparse_data_size_); |
| 1339 EntryOperationComplete(completion_callback, entry_stat, result.Pass()); | 1340 EntryOperationComplete(completion_callback, entry_stat, result.Pass()); |
| 1340 } | 1341 } |
| 1341 | 1342 |
| 1342 void SimpleEntryImpl::CloseOperationComplete() { | 1343 void SimpleEntryImpl::CloseOperationComplete() { |
| 1343 DCHECK(!synchronous_entry_); | 1344 DCHECK(!synchronous_entry_); |
| 1344 DCHECK_EQ(0, open_count_); | 1345 DCHECK_EQ(0, open_count_); |
| 1345 DCHECK(STATE_IO_PENDING == state_ || STATE_FAILURE == state_ || | 1346 DCHECK(STATE_IO_PENDING == state_ || STATE_FAILURE == state_ || |
| 1346 STATE_UNINITIALIZED == state_); | 1347 STATE_UNINITIALIZED == state_); |
| 1347 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CLOSE_END); | 1348 net_log_.AddEvent(net::NetLog::TYPE_SIMPLE_CACHE_ENTRY_CLOSE_END); |
| 1348 AdjustOpenEntryCountBy(cache_type_, -1); | 1349 AdjustOpenEntryCountBy(cache_type_, -1); |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1396 type = READ_ALONE_IN_QUEUE; | 1397 type = READ_ALONE_IN_QUEUE; |
| 1397 } else if (executing_operation_->type() == SimpleEntryOperation::TYPE_READ) { | 1398 } else if (executing_operation_->type() == SimpleEntryOperation::TYPE_READ) { |
| 1398 type = READ_FOLLOWS_READ; | 1399 type = READ_FOLLOWS_READ; |
| 1399 } else if (executing_operation_->type() == SimpleEntryOperation::TYPE_WRITE) { | 1400 } else if (executing_operation_->type() == SimpleEntryOperation::TYPE_WRITE) { |
| 1400 if (executing_operation_->ConflictsWith(operation)) | 1401 if (executing_operation_->ConflictsWith(operation)) |
| 1401 type = READ_FOLLOWS_CONFLICTING_WRITE; | 1402 type = READ_FOLLOWS_CONFLICTING_WRITE; |
| 1402 else | 1403 else |
| 1403 type = READ_FOLLOWS_NON_CONFLICTING_WRITE; | 1404 type = READ_FOLLOWS_NON_CONFLICTING_WRITE; |
| 1404 } | 1405 } |
| 1405 SIMPLE_CACHE_UMA(ENUMERATION, | 1406 SIMPLE_CACHE_UMA(ENUMERATION, |
| 1406 "ReadIsParallelizable", cache_type_, | 1407 "ReadIsParallelizable", |
| 1407 type, READ_DEPENDENCY_TYPE_MAX); | 1408 cache_type_, |
| 1409 type, |
| 1410 READ_DEPENDENCY_TYPE_MAX); |
| 1408 } | 1411 } |
| 1409 | 1412 |
| 1410 void SimpleEntryImpl::RecordWriteDependencyType( | 1413 void SimpleEntryImpl::RecordWriteDependencyType( |
| 1411 const SimpleEntryOperation& operation) const { | 1414 const SimpleEntryOperation& operation) const { |
| 1412 if (!executing_operation_) | 1415 if (!executing_operation_) |
| 1413 return; | 1416 return; |
| 1414 // Used in histograms, please only add entries at the end. | 1417 // Used in histograms, please only add entries at the end. |
| 1415 enum WriteDependencyType { | 1418 enum WriteDependencyType { |
| 1416 WRITE_OPTIMISTIC = 0, | 1419 WRITE_OPTIMISTIC = 0, |
| 1417 WRITE_FOLLOWS_CONFLICTING_OPTIMISTIC = 1, | 1420 WRITE_FOLLOWS_CONFLICTING_OPTIMISTIC = 1, |
| (...skipping 18 matching lines...) Expand all Loading... |
| 1436 : WRITE_FOLLOWS_NON_CONFLICTING_READ; | 1439 : WRITE_FOLLOWS_NON_CONFLICTING_READ; |
| 1437 } else if (executing_operation_->optimistic()) { | 1440 } else if (executing_operation_->optimistic()) { |
| 1438 type = conflicting ? WRITE_FOLLOWS_CONFLICTING_OPTIMISTIC | 1441 type = conflicting ? WRITE_FOLLOWS_CONFLICTING_OPTIMISTIC |
| 1439 : WRITE_FOLLOWS_NON_CONFLICTING_OPTIMISTIC; | 1442 : WRITE_FOLLOWS_NON_CONFLICTING_OPTIMISTIC; |
| 1440 } else { | 1443 } else { |
| 1441 type = conflicting ? WRITE_FOLLOWS_CONFLICTING_WRITE | 1444 type = conflicting ? WRITE_FOLLOWS_CONFLICTING_WRITE |
| 1442 : WRITE_FOLLOWS_NON_CONFLICTING_WRITE; | 1445 : WRITE_FOLLOWS_NON_CONFLICTING_WRITE; |
| 1443 } | 1446 } |
| 1444 } | 1447 } |
| 1445 SIMPLE_CACHE_UMA(ENUMERATION, | 1448 SIMPLE_CACHE_UMA(ENUMERATION, |
| 1446 "WriteDependencyType", cache_type_, | 1449 "WriteDependencyType", |
| 1447 type, WRITE_DEPENDENCY_TYPE_MAX); | 1450 cache_type_, |
| 1451 type, |
| 1452 WRITE_DEPENDENCY_TYPE_MAX); |
| 1448 } | 1453 } |
| 1449 | 1454 |
| 1450 int SimpleEntryImpl::ReadStream0Data(net::IOBuffer* buf, | 1455 int SimpleEntryImpl::ReadStream0Data(net::IOBuffer* buf, |
| 1451 int offset, | 1456 int offset, |
| 1452 int buf_len) { | 1457 int buf_len) { |
| 1453 if (buf_len < 0) { | 1458 if (buf_len < 0) { |
| 1454 RecordReadResult(cache_type_, READ_RESULT_SYNC_READ_FAILURE); | 1459 RecordReadResult(cache_type_, READ_RESULT_SYNC_READ_FAILURE); |
| 1455 return 0; | 1460 return 0; |
| 1456 } | 1461 } |
| 1457 memcpy(buf->data(), stream_0_data_->data() + offset, buf_len); | 1462 memcpy(buf->data(), stream_0_data_->data() + offset, buf_len); |
| 1458 UpdateDataFromEntryStat( | 1463 UpdateDataFromEntryStat(SimpleEntryStat( |
| 1459 SimpleEntryStat(base::Time::Now(), last_modified_, data_size_, | 1464 base::Time::Now(), last_modified_, data_size_, sparse_data_size_)); |
| 1460 sparse_data_size_)); | |
| 1461 RecordReadResult(cache_type_, READ_RESULT_SUCCESS); | 1465 RecordReadResult(cache_type_, READ_RESULT_SUCCESS); |
| 1462 return buf_len; | 1466 return buf_len; |
| 1463 } | 1467 } |
| 1464 | 1468 |
| 1465 int SimpleEntryImpl::SetStream0Data(net::IOBuffer* buf, | 1469 int SimpleEntryImpl::SetStream0Data(net::IOBuffer* buf, |
| 1466 int offset, | 1470 int offset, |
| 1467 int buf_len, | 1471 int buf_len, |
| 1468 bool truncate) { | 1472 bool truncate) { |
| 1469 // Currently, stream 0 is only used for HTTP headers, and always writes them | 1473 // Currently, stream 0 is only used for HTTP headers, and always writes them |
| 1470 // with a single, truncating write. Detect these writes and record the size | 1474 // with a single, truncating write. Detect these writes and record the size |
| (...skipping 16 matching lines...) Expand all Loading... |
| 1487 // zero-filled. | 1491 // zero-filled. |
| 1488 const int fill_size = offset <= data_size ? 0 : offset - data_size; | 1492 const int fill_size = offset <= data_size ? 0 : offset - data_size; |
| 1489 if (fill_size > 0) | 1493 if (fill_size > 0) |
| 1490 memset(stream_0_data_->data() + data_size, 0, fill_size); | 1494 memset(stream_0_data_->data() + data_size, 0, fill_size); |
| 1491 if (buf) | 1495 if (buf) |
| 1492 memcpy(stream_0_data_->data() + offset, buf->data(), buf_len); | 1496 memcpy(stream_0_data_->data() + offset, buf->data(), buf_len); |
| 1493 data_size_[0] = buffer_size; | 1497 data_size_[0] = buffer_size; |
| 1494 } | 1498 } |
| 1495 base::Time modification_time = base::Time::Now(); | 1499 base::Time modification_time = base::Time::Now(); |
| 1496 AdvanceCrc(buf, offset, buf_len, 0); | 1500 AdvanceCrc(buf, offset, buf_len, 0); |
| 1497 UpdateDataFromEntryStat( | 1501 UpdateDataFromEntryStat(SimpleEntryStat( |
| 1498 SimpleEntryStat(modification_time, modification_time, data_size_, | 1502 modification_time, modification_time, data_size_, sparse_data_size_)); |
| 1499 sparse_data_size_)); | |
| 1500 RecordWriteResult(cache_type_, WRITE_RESULT_SUCCESS); | 1503 RecordWriteResult(cache_type_, WRITE_RESULT_SUCCESS); |
| 1501 return buf_len; | 1504 return buf_len; |
| 1502 } | 1505 } |
| 1503 | 1506 |
| 1504 void SimpleEntryImpl::AdvanceCrc(net::IOBuffer* buffer, | 1507 void SimpleEntryImpl::AdvanceCrc(net::IOBuffer* buffer, |
| 1505 int offset, | 1508 int offset, |
| 1506 int length, | 1509 int length, |
| 1507 int stream_index) { | 1510 int stream_index) { |
| 1508 // It is easy to incrementally compute the CRC from [0 .. |offset + buf_len|) | 1511 // It is easy to incrementally compute the CRC from [0 .. |offset + buf_len|) |
| 1509 // if |offset == 0| or we have already computed the CRC for [0 .. offset). | 1512 // if |offset == 0| or we have already computed the CRC for [0 .. offset). |
| 1510 // We rely on most write operations being sequential, start to end to compute | 1513 // We rely on most write operations being sequential, start to end to compute |
| 1511 // the crc of the data. When we write to an entry and close without having | 1514 // the crc of the data. When we write to an entry and close without having |
| 1512 // done a sequential write, we don't check the CRC on read. | 1515 // done a sequential write, we don't check the CRC on read. |
| 1513 if (offset == 0 || crc32s_end_offset_[stream_index] == offset) { | 1516 if (offset == 0 || crc32s_end_offset_[stream_index] == offset) { |
| 1514 uint32 initial_crc = | 1517 uint32 initial_crc = |
| 1515 (offset != 0) ? crc32s_[stream_index] : crc32(0, Z_NULL, 0); | 1518 (offset != 0) ? crc32s_[stream_index] : crc32(0, Z_NULL, 0); |
| 1516 if (length > 0) { | 1519 if (length > 0) { |
| 1517 crc32s_[stream_index] = crc32( | 1520 crc32s_[stream_index] = crc32( |
| 1518 initial_crc, reinterpret_cast<const Bytef*>(buffer->data()), length); | 1521 initial_crc, reinterpret_cast<const Bytef*>(buffer->data()), length); |
| 1519 } | 1522 } |
| 1520 crc32s_end_offset_[stream_index] = offset + length; | 1523 crc32s_end_offset_[stream_index] = offset + length; |
| 1521 } else if (offset < crc32s_end_offset_[stream_index]) { | 1524 } else if (offset < crc32s_end_offset_[stream_index]) { |
| 1522 // If a range for which the crc32 was already computed is rewritten, the | 1525 // If a range for which the crc32 was already computed is rewritten, the |
| 1523 // computation of the crc32 need to start from 0 again. | 1526 // computation of the crc32 need to start from 0 again. |
| 1524 crc32s_end_offset_[stream_index] = 0; | 1527 crc32s_end_offset_[stream_index] = 0; |
| 1525 } | 1528 } |
| 1526 } | 1529 } |
| 1527 | 1530 |
| 1528 } // namespace disk_cache | 1531 } // namespace disk_cache |
| OLD | NEW |