| 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_backend_impl.h" | 5 #include "net/disk_cache/simple/simple_backend_impl.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <cstdlib> | 8 #include <cstdlib> |
| 9 #include <functional> | 9 #include <functional> |
| 10 | 10 |
| (...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 66 if (!g_sequenced_worker_pool) { | 66 if (!g_sequenced_worker_pool) { |
| 67 int max_worker_threads = kDefaultMaxWorkerThreads; | 67 int max_worker_threads = kDefaultMaxWorkerThreads; |
| 68 | 68 |
| 69 const std::string thread_count_field_trial = | 69 const std::string thread_count_field_trial = |
| 70 base::FieldTrialList::FindFullName("SimpleCacheMaxThreads"); | 70 base::FieldTrialList::FindFullName("SimpleCacheMaxThreads"); |
| 71 if (!thread_count_field_trial.empty()) { | 71 if (!thread_count_field_trial.empty()) { |
| 72 max_worker_threads = | 72 max_worker_threads = |
| 73 std::max(1, std::atoi(thread_count_field_trial.c_str())); | 73 std::max(1, std::atoi(thread_count_field_trial.c_str())); |
| 74 } | 74 } |
| 75 | 75 |
| 76 g_sequenced_worker_pool = new SequencedWorkerPool(max_worker_threads, | 76 g_sequenced_worker_pool = |
| 77 kThreadNamePrefix); | 77 new SequencedWorkerPool(max_worker_threads, kThreadNamePrefix); |
| 78 g_sequenced_worker_pool->AddRef(); // Leak it. | 78 g_sequenced_worker_pool->AddRef(); // Leak it. |
| 79 } | 79 } |
| 80 } | 80 } |
| 81 | 81 |
| 82 bool g_fd_limit_histogram_has_been_populated = false; | 82 bool g_fd_limit_histogram_has_been_populated = false; |
| 83 | 83 |
| 84 void MaybeHistogramFdLimit(net::CacheType cache_type) { | 84 void MaybeHistogramFdLimit(net::CacheType cache_type) { |
| 85 if (g_fd_limit_histogram_has_been_populated) | 85 if (g_fd_limit_histogram_has_been_populated) |
| 86 return; | 86 return; |
| 87 | 87 |
| 88 // Used in histograms; add new entries at end. | 88 // Used in histograms; add new entries at end. |
| 89 enum FdLimitStatus { | 89 enum FdLimitStatus { |
| 90 FD_LIMIT_STATUS_UNSUPPORTED = 0, | 90 FD_LIMIT_STATUS_UNSUPPORTED = 0, |
| 91 FD_LIMIT_STATUS_FAILED = 1, | 91 FD_LIMIT_STATUS_FAILED = 1, |
| 92 FD_LIMIT_STATUS_SUCCEEDED = 2, | 92 FD_LIMIT_STATUS_SUCCEEDED = 2, |
| 93 FD_LIMIT_STATUS_MAX = 3 | 93 FD_LIMIT_STATUS_MAX = 3 |
| 94 }; | 94 }; |
| 95 FdLimitStatus fd_limit_status = FD_LIMIT_STATUS_UNSUPPORTED; | 95 FdLimitStatus fd_limit_status = FD_LIMIT_STATUS_UNSUPPORTED; |
| 96 int soft_fd_limit = 0; | 96 int soft_fd_limit = 0; |
| 97 int hard_fd_limit = 0; | 97 int hard_fd_limit = 0; |
| 98 | 98 |
| 99 #if defined(OS_POSIX) | 99 #if defined(OS_POSIX) |
| 100 struct rlimit nofile; | 100 struct rlimit nofile; |
| 101 if (!getrlimit(RLIMIT_NOFILE, &nofile)) { | 101 if (!getrlimit(RLIMIT_NOFILE, &nofile)) { |
| 102 soft_fd_limit = nofile.rlim_cur; | 102 soft_fd_limit = nofile.rlim_cur; |
| 103 hard_fd_limit = nofile.rlim_max; | 103 hard_fd_limit = nofile.rlim_max; |
| 104 fd_limit_status = FD_LIMIT_STATUS_SUCCEEDED; | 104 fd_limit_status = FD_LIMIT_STATUS_SUCCEEDED; |
| 105 } else { | 105 } else { |
| 106 fd_limit_status = FD_LIMIT_STATUS_FAILED; | 106 fd_limit_status = FD_LIMIT_STATUS_FAILED; |
| 107 } | 107 } |
| 108 #endif | 108 #endif |
| 109 | 109 |
| 110 SIMPLE_CACHE_UMA(ENUMERATION, | 110 SIMPLE_CACHE_UMA(ENUMERATION, |
| 111 "FileDescriptorLimitStatus", cache_type, | 111 "FileDescriptorLimitStatus", |
| 112 fd_limit_status, FD_LIMIT_STATUS_MAX); | 112 cache_type, |
| 113 fd_limit_status, |
| 114 FD_LIMIT_STATUS_MAX); |
| 113 if (fd_limit_status == FD_LIMIT_STATUS_SUCCEEDED) { | 115 if (fd_limit_status == FD_LIMIT_STATUS_SUCCEEDED) { |
| 114 SIMPLE_CACHE_UMA(SPARSE_SLOWLY, | 116 SIMPLE_CACHE_UMA( |
| 115 "FileDescriptorLimitSoft", cache_type, soft_fd_limit); | 117 SPARSE_SLOWLY, "FileDescriptorLimitSoft", cache_type, soft_fd_limit); |
| 116 SIMPLE_CACHE_UMA(SPARSE_SLOWLY, | 118 SIMPLE_CACHE_UMA( |
| 117 "FileDescriptorLimitHard", cache_type, hard_fd_limit); | 119 SPARSE_SLOWLY, "FileDescriptorLimitHard", cache_type, hard_fd_limit); |
| 118 } | 120 } |
| 119 | 121 |
| 120 g_fd_limit_histogram_has_been_populated = true; | 122 g_fd_limit_histogram_has_been_populated = true; |
| 121 } | 123 } |
| 122 | 124 |
| 123 // Detects if the files in the cache directory match the current disk cache | 125 // Detects if the files in the cache directory match the current disk cache |
| 124 // backend type and version. If the directory contains no cache, occupies it | 126 // backend type and version. If the directory contains no cache, occupies it |
| 125 // with the fresh structure. | 127 // with the fresh structure. |
| 126 bool FileStructureConsistent(const base::FilePath& path) { | 128 bool FileStructureConsistent(const base::FilePath& path) { |
| 127 if (!base::PathExists(path) && !base::CreateDirectory(path)) { | 129 if (!base::PathExists(path) && !base::CreateDirectory(path)) { |
| 128 LOG(ERROR) << "Failed to create directory: " << path.LossyDisplayName(); | 130 LOG(ERROR) << "Failed to create directory: " << path.LossyDisplayName(); |
| 129 return false; | 131 return false; |
| 130 } | 132 } |
| 131 return disk_cache::UpgradeSimpleCacheOnDisk(path); | 133 return disk_cache::UpgradeSimpleCacheOnDisk(path); |
| 132 } | 134 } |
| 133 | 135 |
| 134 // A context used by a BarrierCompletionCallback to track state. | 136 // A context used by a BarrierCompletionCallback to track state. |
| 135 struct BarrierContext { | 137 struct BarrierContext { |
| 136 BarrierContext(int expected) | 138 BarrierContext(int expected) |
| 137 : expected(expected), | 139 : expected(expected), count(0), had_error(false) {} |
| 138 count(0), | |
| 139 had_error(false) {} | |
| 140 | 140 |
| 141 const int expected; | 141 const int expected; |
| 142 int count; | 142 int count; |
| 143 bool had_error; | 143 bool had_error; |
| 144 }; | 144 }; |
| 145 | 145 |
| 146 void BarrierCompletionCallbackImpl( | 146 void BarrierCompletionCallbackImpl( |
| 147 BarrierContext* context, | 147 BarrierContext* context, |
| 148 const net::CompletionCallback& final_callback, | 148 const net::CompletionCallback& final_callback, |
| 149 int result) { | 149 int result) { |
| (...skipping 11 matching lines...) Expand all Loading... |
| 161 } | 161 } |
| 162 | 162 |
| 163 // A barrier completion callback is a net::CompletionCallback that waits for | 163 // A barrier completion callback is a net::CompletionCallback that waits for |
| 164 // |count| successful results before invoking |final_callback|. In the case of | 164 // |count| successful results before invoking |final_callback|. In the case of |
| 165 // an error, the first error is passed to |final_callback| and all others | 165 // an error, the first error is passed to |final_callback| and all others |
| 166 // are ignored. | 166 // are ignored. |
| 167 net::CompletionCallback MakeBarrierCompletionCallback( | 167 net::CompletionCallback MakeBarrierCompletionCallback( |
| 168 int count, | 168 int count, |
| 169 const net::CompletionCallback& final_callback) { | 169 const net::CompletionCallback& final_callback) { |
| 170 BarrierContext* context = new BarrierContext(count); | 170 BarrierContext* context = new BarrierContext(count); |
| 171 return base::Bind(&BarrierCompletionCallbackImpl, | 171 return base::Bind( |
| 172 base::Owned(context), final_callback); | 172 &BarrierCompletionCallbackImpl, base::Owned(context), final_callback); |
| 173 } | 173 } |
| 174 | 174 |
| 175 // A short bindable thunk that ensures a completion callback is always called | 175 // A short bindable thunk that ensures a completion callback is always called |
| 176 // after running an operation asynchronously. | 176 // after running an operation asynchronously. |
| 177 void RunOperationAndCallback( | 177 void RunOperationAndCallback( |
| 178 const Callback<int(const net::CompletionCallback&)>& operation, | 178 const Callback<int(const net::CompletionCallback&)>& operation, |
| 179 const net::CompletionCallback& operation_callback) { | 179 const net::CompletionCallback& operation_callback) { |
| 180 const int operation_result = operation.Run(operation_callback); | 180 const int operation_result = operation.Run(operation_callback); |
| 181 if (operation_result != net::ERR_IO_PENDING) | 181 if (operation_result != net::ERR_IO_PENDING) |
| 182 operation_callback.Run(operation_result); | 182 operation_callback.Run(operation_result); |
| 183 } | 183 } |
| 184 | 184 |
| 185 void RecordIndexLoad(net::CacheType cache_type, | 185 void RecordIndexLoad(net::CacheType cache_type, |
| 186 base::TimeTicks constructed_since, | 186 base::TimeTicks constructed_since, |
| 187 int result) { | 187 int result) { |
| 188 const base::TimeDelta creation_to_index = base::TimeTicks::Now() - | 188 const base::TimeDelta creation_to_index = |
| 189 constructed_since; | 189 base::TimeTicks::Now() - constructed_since; |
| 190 if (result == net::OK) { | 190 if (result == net::OK) { |
| 191 SIMPLE_CACHE_UMA(TIMES, "CreationToIndex", cache_type, creation_to_index); | 191 SIMPLE_CACHE_UMA(TIMES, "CreationToIndex", cache_type, creation_to_index); |
| 192 } else { | 192 } else { |
| 193 SIMPLE_CACHE_UMA(TIMES, | 193 SIMPLE_CACHE_UMA( |
| 194 "CreationToIndexFail", cache_type, creation_to_index); | 194 TIMES, "CreationToIndexFail", cache_type, creation_to_index); |
| 195 } | 195 } |
| 196 } | 196 } |
| 197 | 197 |
| 198 } // namespace | 198 } // namespace |
| 199 | 199 |
| 200 SimpleBackendImpl::SimpleBackendImpl(const FilePath& path, | 200 SimpleBackendImpl::SimpleBackendImpl(const FilePath& path, |
| 201 int max_bytes, | 201 int max_bytes, |
| 202 net::CacheType cache_type, | 202 net::CacheType cache_type, |
| 203 base::SingleThreadTaskRunner* cache_thread, | 203 base::SingleThreadTaskRunner* cache_thread, |
| 204 net::NetLog* net_log) | 204 net::NetLog* net_log) |
| 205 : path_(path), | 205 : path_(path), |
| 206 cache_type_(cache_type), | 206 cache_type_(cache_type), |
| 207 cache_thread_(cache_thread), | 207 cache_thread_(cache_thread), |
| 208 orig_max_size_(max_bytes), | 208 orig_max_size_(max_bytes), |
| 209 entry_operations_mode_( | 209 entry_operations_mode_(cache_type == net::DISK_CACHE |
| 210 cache_type == net::DISK_CACHE ? | 210 ? SimpleEntryImpl::OPTIMISTIC_OPERATIONS |
| 211 SimpleEntryImpl::OPTIMISTIC_OPERATIONS : | 211 : SimpleEntryImpl::NON_OPTIMISTIC_OPERATIONS), |
| 212 SimpleEntryImpl::NON_OPTIMISTIC_OPERATIONS), | |
| 213 net_log_(net_log) { | 212 net_log_(net_log) { |
| 214 MaybeHistogramFdLimit(cache_type_); | 213 MaybeHistogramFdLimit(cache_type_); |
| 215 } | 214 } |
| 216 | 215 |
| 217 SimpleBackendImpl::~SimpleBackendImpl() { | 216 SimpleBackendImpl::~SimpleBackendImpl() { |
| 218 index_->WriteToDisk(); | 217 index_->WriteToDisk(); |
| 219 } | 218 } |
| 220 | 219 |
| 221 int SimpleBackendImpl::Init(const CompletionCallback& completion_callback) { | 220 int SimpleBackendImpl::Init(const CompletionCallback& completion_callback) { |
| 222 MaybeCreateSequencedWorkerPool(); | 221 MaybeCreateSequencedWorkerPool(); |
| 223 | 222 |
| 224 worker_pool_ = g_sequenced_worker_pool->GetTaskRunnerWithShutdownBehavior( | 223 worker_pool_ = g_sequenced_worker_pool->GetTaskRunnerWithShutdownBehavior( |
| 225 SequencedWorkerPool::CONTINUE_ON_SHUTDOWN); | 224 SequencedWorkerPool::CONTINUE_ON_SHUTDOWN); |
| 226 | 225 |
| 227 index_.reset(new SimpleIndex(MessageLoopProxy::current(), this, cache_type_, | 226 index_.reset(new SimpleIndex( |
| 228 make_scoped_ptr(new SimpleIndexFile( | 227 MessageLoopProxy::current(), |
| 229 cache_thread_.get(), worker_pool_.get(), | 228 this, |
| 230 cache_type_, path_)))); | 229 cache_type_, |
| 230 make_scoped_ptr(new SimpleIndexFile( |
| 231 cache_thread_.get(), worker_pool_.get(), cache_type_, path_)))); |
| 231 index_->ExecuteWhenReady( | 232 index_->ExecuteWhenReady( |
| 232 base::Bind(&RecordIndexLoad, cache_type_, base::TimeTicks::Now())); | 233 base::Bind(&RecordIndexLoad, cache_type_, base::TimeTicks::Now())); |
| 233 | 234 |
| 234 PostTaskAndReplyWithResult( | 235 PostTaskAndReplyWithResult( |
| 235 cache_thread_, | 236 cache_thread_, |
| 236 FROM_HERE, | 237 FROM_HERE, |
| 237 base::Bind(&SimpleBackendImpl::InitCacheStructureOnDisk, path_, | 238 base::Bind( |
| 238 orig_max_size_), | 239 &SimpleBackendImpl::InitCacheStructureOnDisk, path_, orig_max_size_), |
| 239 base::Bind(&SimpleBackendImpl::InitializeIndex, AsWeakPtr(), | 240 base::Bind(&SimpleBackendImpl::InitializeIndex, |
| 241 AsWeakPtr(), |
| 240 completion_callback)); | 242 completion_callback)); |
| 241 return net::ERR_IO_PENDING; | 243 return net::ERR_IO_PENDING; |
| 242 } | 244 } |
| 243 | 245 |
| 244 bool SimpleBackendImpl::SetMaxSize(int max_bytes) { | 246 bool SimpleBackendImpl::SetMaxSize(int max_bytes) { |
| 245 orig_max_size_ = max_bytes; | 247 orig_max_size_ = max_bytes; |
| 246 return index_->SetMaxSize(max_bytes); | 248 return index_->SetMaxSize(max_bytes); |
| 247 } | 249 } |
| 248 | 250 |
| 249 int SimpleBackendImpl::GetMaxFileSize() const { | 251 int SimpleBackendImpl::GetMaxFileSize() const { |
| (...skipping 13 matching lines...) Expand all Loading... |
| 263 | 265 |
| 264 void SimpleBackendImpl::OnDoomComplete(uint64 entry_hash) { | 266 void SimpleBackendImpl::OnDoomComplete(uint64 entry_hash) { |
| 265 // TODO(ttuttle): Revert to DCHECK once http://crbug.com/317138 is fixed. | 267 // TODO(ttuttle): Revert to DCHECK once http://crbug.com/317138 is fixed. |
| 266 CHECK_EQ(1u, entries_pending_doom_.count(entry_hash)); | 268 CHECK_EQ(1u, entries_pending_doom_.count(entry_hash)); |
| 267 base::hash_map<uint64, std::vector<Closure> >::iterator it = | 269 base::hash_map<uint64, std::vector<Closure> >::iterator it = |
| 268 entries_pending_doom_.find(entry_hash); | 270 entries_pending_doom_.find(entry_hash); |
| 269 std::vector<Closure> to_run_closures; | 271 std::vector<Closure> to_run_closures; |
| 270 to_run_closures.swap(it->second); | 272 to_run_closures.swap(it->second); |
| 271 entries_pending_doom_.erase(it); | 273 entries_pending_doom_.erase(it); |
| 272 | 274 |
| 273 std::for_each(to_run_closures.begin(), to_run_closures.end(), | 275 std::for_each(to_run_closures.begin(), |
| 276 to_run_closures.end(), |
| 274 std::mem_fun_ref(&Closure::Run)); | 277 std::mem_fun_ref(&Closure::Run)); |
| 275 } | 278 } |
| 276 | 279 |
| 277 void SimpleBackendImpl::DoomEntries(std::vector<uint64>* entry_hashes, | 280 void SimpleBackendImpl::DoomEntries(std::vector<uint64>* entry_hashes, |
| 278 const net::CompletionCallback& callback) { | 281 const net::CompletionCallback& callback) { |
| 279 scoped_ptr<std::vector<uint64> > | 282 scoped_ptr<std::vector<uint64> > mass_doom_entry_hashes( |
| 280 mass_doom_entry_hashes(new std::vector<uint64>()); | 283 new std::vector<uint64>()); |
| 281 mass_doom_entry_hashes->swap(*entry_hashes); | 284 mass_doom_entry_hashes->swap(*entry_hashes); |
| 282 | 285 |
| 283 std::vector<uint64> to_doom_individually_hashes; | 286 std::vector<uint64> to_doom_individually_hashes; |
| 284 | 287 |
| 285 // For each of the entry hashes, there are two cases: | 288 // For each of the entry hashes, there are two cases: |
| 286 // 1. The entry is either open or pending doom, and so it should be doomed | 289 // 1. The entry is either open or pending doom, and so it should be doomed |
| 287 // individually to avoid flakes. | 290 // individually to avoid flakes. |
| 288 // 2. The entry is not in use at all, so we can call | 291 // 2. The entry is not in use at all, so we can call |
| 289 // SimpleSynchronousEntry::DoomEntrySet and delete the files en masse. | 292 // SimpleSynchronousEntry::DoomEntrySet and delete the files en masse. |
| 290 for (int i = mass_doom_entry_hashes->size() - 1; i >= 0; --i) { | 293 for (int i = mass_doom_entry_hashes->size() - 1; i >= 0; --i) { |
| 291 const uint64 entry_hash = (*mass_doom_entry_hashes)[i]; | 294 const uint64 entry_hash = (*mass_doom_entry_hashes)[i]; |
| 292 // TODO(ttuttle): Revert to DCHECK once http://crbug.com/317138 is fixed. | 295 // TODO(ttuttle): Revert to DCHECK once http://crbug.com/317138 is fixed. |
| 293 CHECK(active_entries_.count(entry_hash) == 0 || | 296 CHECK(active_entries_.count(entry_hash) == 0 || |
| 294 entries_pending_doom_.count(entry_hash) == 0) | 297 entries_pending_doom_.count(entry_hash) == 0) |
| 295 << "The entry 0x" << std::hex << entry_hash | 298 << "The entry 0x" << std::hex << entry_hash |
| 296 << " is both active and pending doom."; | 299 << " is both active and pending doom."; |
| 297 if (!active_entries_.count(entry_hash) && | 300 if (!active_entries_.count(entry_hash) && |
| 298 !entries_pending_doom_.count(entry_hash)) { | 301 !entries_pending_doom_.count(entry_hash)) { |
| 299 continue; | 302 continue; |
| 300 } | 303 } |
| 301 | 304 |
| 302 to_doom_individually_hashes.push_back(entry_hash); | 305 to_doom_individually_hashes.push_back(entry_hash); |
| 303 | 306 |
| 304 (*mass_doom_entry_hashes)[i] = mass_doom_entry_hashes->back(); | 307 (*mass_doom_entry_hashes)[i] = mass_doom_entry_hashes->back(); |
| 305 mass_doom_entry_hashes->resize(mass_doom_entry_hashes->size() - 1); | 308 mass_doom_entry_hashes->resize(mass_doom_entry_hashes->size() - 1); |
| 306 } | 309 } |
| 307 | 310 |
| 308 net::CompletionCallback barrier_callback = | 311 net::CompletionCallback barrier_callback = MakeBarrierCompletionCallback( |
| 309 MakeBarrierCompletionCallback(to_doom_individually_hashes.size() + 1, | 312 to_doom_individually_hashes.size() + 1, callback); |
| 310 callback); | |
| 311 for (std::vector<uint64>::const_iterator | 313 for (std::vector<uint64>::const_iterator |
| 312 it = to_doom_individually_hashes.begin(), | 314 it = to_doom_individually_hashes.begin(), |
| 313 end = to_doom_individually_hashes.end(); it != end; ++it) { | 315 end = to_doom_individually_hashes.end(); |
| 316 it != end; |
| 317 ++it) { |
| 314 const int doom_result = DoomEntryFromHash(*it, barrier_callback); | 318 const int doom_result = DoomEntryFromHash(*it, barrier_callback); |
| 315 // TODO(ttuttle): Revert to DCHECK once http://crbug.com/317138 is fixed. | 319 // TODO(ttuttle): Revert to DCHECK once http://crbug.com/317138 is fixed. |
| 316 CHECK_EQ(net::ERR_IO_PENDING, doom_result); | 320 CHECK_EQ(net::ERR_IO_PENDING, doom_result); |
| 317 index_->Remove(*it); | 321 index_->Remove(*it); |
| 318 } | 322 } |
| 319 | 323 |
| 320 for (std::vector<uint64>::const_iterator it = mass_doom_entry_hashes->begin(), | 324 for (std::vector<uint64>::const_iterator it = mass_doom_entry_hashes->begin(), |
| 321 end = mass_doom_entry_hashes->end(); | 325 end = mass_doom_entry_hashes->end(); |
| 322 it != end; ++it) { | 326 it != end; |
| 327 ++it) { |
| 323 index_->Remove(*it); | 328 index_->Remove(*it); |
| 324 OnDoomStart(*it); | 329 OnDoomStart(*it); |
| 325 } | 330 } |
| 326 | 331 |
| 327 // Taking this pointer here avoids undefined behaviour from calling | 332 // Taking this pointer here avoids undefined behaviour from calling |
| 328 // base::Passed before mass_doom_entry_hashes.get(). | 333 // base::Passed before mass_doom_entry_hashes.get(). |
| 329 std::vector<uint64>* mass_doom_entry_hashes_ptr = | 334 std::vector<uint64>* mass_doom_entry_hashes_ptr = |
| 330 mass_doom_entry_hashes.get(); | 335 mass_doom_entry_hashes.get(); |
| 331 PostTaskAndReplyWithResult( | 336 PostTaskAndReplyWithResult(worker_pool_, |
| 332 worker_pool_, FROM_HERE, | 337 FROM_HERE, |
| 333 base::Bind(&SimpleSynchronousEntry::DoomEntrySet, | 338 base::Bind(&SimpleSynchronousEntry::DoomEntrySet, |
| 334 mass_doom_entry_hashes_ptr, path_), | 339 mass_doom_entry_hashes_ptr, |
| 335 base::Bind(&SimpleBackendImpl::DoomEntriesComplete, | 340 path_), |
| 336 AsWeakPtr(), base::Passed(&mass_doom_entry_hashes), | 341 base::Bind(&SimpleBackendImpl::DoomEntriesComplete, |
| 337 barrier_callback)); | 342 AsWeakPtr(), |
| 343 base::Passed(&mass_doom_entry_hashes), |
| 344 barrier_callback)); |
| 338 } | 345 } |
| 339 | 346 |
| 340 net::CacheType SimpleBackendImpl::GetCacheType() const { | 347 net::CacheType SimpleBackendImpl::GetCacheType() const { |
| 341 return net::DISK_CACHE; | 348 return net::DISK_CACHE; |
| 342 } | 349 } |
| 343 | 350 |
| 344 int32 SimpleBackendImpl::GetEntryCount() const { | 351 int32 SimpleBackendImpl::GetEntryCount() const { |
| 345 // TODO(pasko): Use directory file count when index is not ready. | 352 // TODO(pasko): Use directory file count when index is not ready. |
| 346 return index_->GetEntryCount(); | 353 return index_->GetEntryCount(); |
| 347 } | 354 } |
| 348 | 355 |
| 349 int SimpleBackendImpl::OpenEntry(const std::string& key, | 356 int SimpleBackendImpl::OpenEntry(const std::string& key, |
| 350 Entry** entry, | 357 Entry** entry, |
| 351 const CompletionCallback& callback) { | 358 const CompletionCallback& callback) { |
| 352 const uint64 entry_hash = simple_util::GetEntryHashKey(key); | 359 const uint64 entry_hash = simple_util::GetEntryHashKey(key); |
| 353 | 360 |
| 354 // TODO(gavinp): Factor out this (not quite completely) repetitive code | 361 // TODO(gavinp): Factor out this (not quite completely) repetitive code |
| 355 // block from OpenEntry/CreateEntry/DoomEntry. | 362 // block from OpenEntry/CreateEntry/DoomEntry. |
| 356 base::hash_map<uint64, std::vector<Closure> >::iterator it = | 363 base::hash_map<uint64, std::vector<Closure> >::iterator it = |
| 357 entries_pending_doom_.find(entry_hash); | 364 entries_pending_doom_.find(entry_hash); |
| 358 if (it != entries_pending_doom_.end()) { | 365 if (it != entries_pending_doom_.end()) { |
| 359 Callback<int(const net::CompletionCallback&)> operation = | 366 Callback<int(const net::CompletionCallback&)> operation = base::Bind( |
| 360 base::Bind(&SimpleBackendImpl::OpenEntry, | 367 &SimpleBackendImpl::OpenEntry, base::Unretained(this), key, entry); |
| 361 base::Unretained(this), key, entry); | 368 it->second.push_back( |
| 362 it->second.push_back(base::Bind(&RunOperationAndCallback, | 369 base::Bind(&RunOperationAndCallback, operation, callback)); |
| 363 operation, callback)); | |
| 364 return net::ERR_IO_PENDING; | 370 return net::ERR_IO_PENDING; |
| 365 } | 371 } |
| 366 scoped_refptr<SimpleEntryImpl> simple_entry = | 372 scoped_refptr<SimpleEntryImpl> simple_entry = |
| 367 CreateOrFindActiveEntry(entry_hash, key); | 373 CreateOrFindActiveEntry(entry_hash, key); |
| 368 CompletionCallback backend_callback = | 374 CompletionCallback backend_callback = |
| 369 base::Bind(&SimpleBackendImpl::OnEntryOpenedFromKey, | 375 base::Bind(&SimpleBackendImpl::OnEntryOpenedFromKey, |
| 370 AsWeakPtr(), | 376 AsWeakPtr(), |
| 371 key, | 377 key, |
| 372 entry, | 378 entry, |
| 373 simple_entry, | 379 simple_entry, |
| 374 callback); | 380 callback); |
| 375 return simple_entry->OpenEntry(entry, backend_callback); | 381 return simple_entry->OpenEntry(entry, backend_callback); |
| 376 } | 382 } |
| 377 | 383 |
| 378 int SimpleBackendImpl::CreateEntry(const std::string& key, | 384 int SimpleBackendImpl::CreateEntry(const std::string& key, |
| 379 Entry** entry, | 385 Entry** entry, |
| 380 const CompletionCallback& callback) { | 386 const CompletionCallback& callback) { |
| 381 DCHECK_LT(0u, key.size()); | 387 DCHECK_LT(0u, key.size()); |
| 382 const uint64 entry_hash = simple_util::GetEntryHashKey(key); | 388 const uint64 entry_hash = simple_util::GetEntryHashKey(key); |
| 383 | 389 |
| 384 base::hash_map<uint64, std::vector<Closure> >::iterator it = | 390 base::hash_map<uint64, std::vector<Closure> >::iterator it = |
| 385 entries_pending_doom_.find(entry_hash); | 391 entries_pending_doom_.find(entry_hash); |
| 386 if (it != entries_pending_doom_.end()) { | 392 if (it != entries_pending_doom_.end()) { |
| 387 Callback<int(const net::CompletionCallback&)> operation = | 393 Callback<int(const net::CompletionCallback&)> operation = base::Bind( |
| 388 base::Bind(&SimpleBackendImpl::CreateEntry, | 394 &SimpleBackendImpl::CreateEntry, base::Unretained(this), key, entry); |
| 389 base::Unretained(this), key, entry); | 395 it->second.push_back( |
| 390 it->second.push_back(base::Bind(&RunOperationAndCallback, | 396 base::Bind(&RunOperationAndCallback, operation, callback)); |
| 391 operation, callback)); | |
| 392 return net::ERR_IO_PENDING; | 397 return net::ERR_IO_PENDING; |
| 393 } | 398 } |
| 394 scoped_refptr<SimpleEntryImpl> simple_entry = | 399 scoped_refptr<SimpleEntryImpl> simple_entry = |
| 395 CreateOrFindActiveEntry(entry_hash, key); | 400 CreateOrFindActiveEntry(entry_hash, key); |
| 396 return simple_entry->CreateEntry(entry, callback); | 401 return simple_entry->CreateEntry(entry, callback); |
| 397 } | 402 } |
| 398 | 403 |
| 399 int SimpleBackendImpl::DoomEntry(const std::string& key, | 404 int SimpleBackendImpl::DoomEntry(const std::string& key, |
| 400 const net::CompletionCallback& callback) { | 405 const net::CompletionCallback& callback) { |
| 401 const uint64 entry_hash = simple_util::GetEntryHashKey(key); | 406 const uint64 entry_hash = simple_util::GetEntryHashKey(key); |
| 402 | 407 |
| 403 base::hash_map<uint64, std::vector<Closure> >::iterator it = | 408 base::hash_map<uint64, std::vector<Closure> >::iterator it = |
| 404 entries_pending_doom_.find(entry_hash); | 409 entries_pending_doom_.find(entry_hash); |
| 405 if (it != entries_pending_doom_.end()) { | 410 if (it != entries_pending_doom_.end()) { |
| 406 Callback<int(const net::CompletionCallback&)> operation = | 411 Callback<int(const net::CompletionCallback&)> operation = |
| 407 base::Bind(&SimpleBackendImpl::DoomEntry, base::Unretained(this), key); | 412 base::Bind(&SimpleBackendImpl::DoomEntry, base::Unretained(this), key); |
| 408 it->second.push_back(base::Bind(&RunOperationAndCallback, | 413 it->second.push_back( |
| 409 operation, callback)); | 414 base::Bind(&RunOperationAndCallback, operation, callback)); |
| 410 return net::ERR_IO_PENDING; | 415 return net::ERR_IO_PENDING; |
| 411 } | 416 } |
| 412 scoped_refptr<SimpleEntryImpl> simple_entry = | 417 scoped_refptr<SimpleEntryImpl> simple_entry = |
| 413 CreateOrFindActiveEntry(entry_hash, key); | 418 CreateOrFindActiveEntry(entry_hash, key); |
| 414 return simple_entry->DoomEntry(callback); | 419 return simple_entry->DoomEntry(callback); |
| 415 } | 420 } |
| 416 | 421 |
| 417 int SimpleBackendImpl::DoomAllEntries(const CompletionCallback& callback) { | 422 int SimpleBackendImpl::DoomAllEntries(const CompletionCallback& callback) { |
| 418 return DoomEntriesBetween(Time(), Time(), callback); | 423 return DoomEntriesBetween(Time(), Time(), callback); |
| 419 } | 424 } |
| 420 | 425 |
| 421 void SimpleBackendImpl::IndexReadyForDoom(Time initial_time, | 426 void SimpleBackendImpl::IndexReadyForDoom(Time initial_time, |
| 422 Time end_time, | 427 Time end_time, |
| 423 const CompletionCallback& callback, | 428 const CompletionCallback& callback, |
| 424 int result) { | 429 int result) { |
| 425 if (result != net::OK) { | 430 if (result != net::OK) { |
| 426 callback.Run(result); | 431 callback.Run(result); |
| 427 return; | 432 return; |
| 428 } | 433 } |
| 429 scoped_ptr<std::vector<uint64> > removed_key_hashes( | 434 scoped_ptr<std::vector<uint64> > removed_key_hashes( |
| 430 index_->GetEntriesBetween(initial_time, end_time).release()); | 435 index_->GetEntriesBetween(initial_time, end_time).release()); |
| 431 DoomEntries(removed_key_hashes.get(), callback); | 436 DoomEntries(removed_key_hashes.get(), callback); |
| 432 } | 437 } |
| 433 | 438 |
| 434 int SimpleBackendImpl::DoomEntriesBetween( | 439 int SimpleBackendImpl::DoomEntriesBetween(const Time initial_time, |
| 435 const Time initial_time, | 440 const Time end_time, |
| 436 const Time end_time, | 441 const CompletionCallback& callback) { |
| 437 const CompletionCallback& callback) { | |
| 438 return index_->ExecuteWhenReady( | 442 return index_->ExecuteWhenReady( |
| 439 base::Bind(&SimpleBackendImpl::IndexReadyForDoom, AsWeakPtr(), | 443 base::Bind(&SimpleBackendImpl::IndexReadyForDoom, |
| 440 initial_time, end_time, callback)); | 444 AsWeakPtr(), |
| 445 initial_time, |
| 446 end_time, |
| 447 callback)); |
| 441 } | 448 } |
| 442 | 449 |
| 443 int SimpleBackendImpl::DoomEntriesSince( | 450 int SimpleBackendImpl::DoomEntriesSince(const Time initial_time, |
| 444 const Time initial_time, | 451 const CompletionCallback& callback) { |
| 445 const CompletionCallback& callback) { | |
| 446 return DoomEntriesBetween(initial_time, Time(), callback); | 452 return DoomEntriesBetween(initial_time, Time(), callback); |
| 447 } | 453 } |
| 448 | 454 |
| 449 int SimpleBackendImpl::OpenNextEntry(void** iter, | 455 int SimpleBackendImpl::OpenNextEntry(void** iter, |
| 450 Entry** next_entry, | 456 Entry** next_entry, |
| 451 const CompletionCallback& callback) { | 457 const CompletionCallback& callback) { |
| 452 CompletionCallback get_next_entry = | 458 CompletionCallback get_next_entry = |
| 453 base::Bind(&SimpleBackendImpl::GetNextEntryInIterator, AsWeakPtr(), iter, | 459 base::Bind(&SimpleBackendImpl::GetNextEntryInIterator, |
| 454 next_entry, callback); | 460 AsWeakPtr(), |
| 461 iter, |
| 462 next_entry, |
| 463 callback); |
| 455 return index_->ExecuteWhenReady(get_next_entry); | 464 return index_->ExecuteWhenReady(get_next_entry); |
| 456 } | 465 } |
| 457 | 466 |
| 458 void SimpleBackendImpl::EndEnumeration(void** iter) { | 467 void SimpleBackendImpl::EndEnumeration(void** iter) { |
| 459 SimpleIndex::HashList* entry_list = | 468 SimpleIndex::HashList* entry_list = |
| 460 static_cast<SimpleIndex::HashList*>(*iter); | 469 static_cast<SimpleIndex::HashList*>(*iter); |
| 461 delete entry_list; | 470 delete entry_list; |
| 462 *iter = NULL; | 471 *iter = NULL; |
| 463 } | 472 } |
| 464 | 473 |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 503 } | 512 } |
| 504 DCHECK(result.max_size); | 513 DCHECK(result.max_size); |
| 505 } | 514 } |
| 506 return result; | 515 return result; |
| 507 } | 516 } |
| 508 | 517 |
| 509 scoped_refptr<SimpleEntryImpl> SimpleBackendImpl::CreateOrFindActiveEntry( | 518 scoped_refptr<SimpleEntryImpl> SimpleBackendImpl::CreateOrFindActiveEntry( |
| 510 const uint64 entry_hash, | 519 const uint64 entry_hash, |
| 511 const std::string& key) { | 520 const std::string& key) { |
| 512 DCHECK_EQ(entry_hash, simple_util::GetEntryHashKey(key)); | 521 DCHECK_EQ(entry_hash, simple_util::GetEntryHashKey(key)); |
| 513 std::pair<EntryMap::iterator, bool> insert_result = | 522 std::pair<EntryMap::iterator, bool> insert_result = active_entries_.insert( |
| 514 active_entries_.insert(std::make_pair(entry_hash, | 523 std::make_pair(entry_hash, base::WeakPtr<SimpleEntryImpl>())); |
| 515 base::WeakPtr<SimpleEntryImpl>())); | |
| 516 EntryMap::iterator& it = insert_result.first; | 524 EntryMap::iterator& it = insert_result.first; |
| 517 if (insert_result.second) | 525 if (insert_result.second) |
| 518 DCHECK(!it->second.get()); | 526 DCHECK(!it->second.get()); |
| 519 if (!it->second.get()) { | 527 if (!it->second.get()) { |
| 520 SimpleEntryImpl* entry = new SimpleEntryImpl( | 528 SimpleEntryImpl* entry = new SimpleEntryImpl( |
| 521 cache_type_, path_, entry_hash, entry_operations_mode_, this, net_log_); | 529 cache_type_, path_, entry_hash, entry_operations_mode_, this, net_log_); |
| 522 entry->SetKey(key); | 530 entry->SetKey(key); |
| 523 it->second = entry->AsWeakPtr(); | 531 it->second = entry->AsWeakPtr(); |
| 524 } | 532 } |
| 525 DCHECK(it->second.get()); | 533 DCHECK(it->second.get()); |
| 526 // It's possible, but unlikely, that we have an entry hash collision with a | 534 // It's possible, but unlikely, that we have an entry hash collision with a |
| 527 // currently active entry. | 535 // currently active entry. |
| 528 if (key != it->second->key()) { | 536 if (key != it->second->key()) { |
| 529 it->second->Doom(); | 537 it->second->Doom(); |
| 530 DCHECK_EQ(0U, active_entries_.count(entry_hash)); | 538 DCHECK_EQ(0U, active_entries_.count(entry_hash)); |
| 531 return CreateOrFindActiveEntry(entry_hash, key); | 539 return CreateOrFindActiveEntry(entry_hash, key); |
| 532 } | 540 } |
| 533 return make_scoped_refptr(it->second.get()); | 541 return make_scoped_refptr(it->second.get()); |
| 534 } | 542 } |
| 535 | 543 |
| 536 int SimpleBackendImpl::OpenEntryFromHash(uint64 entry_hash, | 544 int SimpleBackendImpl::OpenEntryFromHash(uint64 entry_hash, |
| 537 Entry** entry, | 545 Entry** entry, |
| 538 const CompletionCallback& callback) { | 546 const CompletionCallback& callback) { |
| 539 base::hash_map<uint64, std::vector<Closure> >::iterator it = | 547 base::hash_map<uint64, std::vector<Closure> >::iterator it = |
| 540 entries_pending_doom_.find(entry_hash); | 548 entries_pending_doom_.find(entry_hash); |
| 541 if (it != entries_pending_doom_.end()) { | 549 if (it != entries_pending_doom_.end()) { |
| 542 Callback<int(const net::CompletionCallback&)> operation = | 550 Callback<int(const net::CompletionCallback&)> operation = |
| 543 base::Bind(&SimpleBackendImpl::OpenEntryFromHash, | 551 base::Bind(&SimpleBackendImpl::OpenEntryFromHash, |
| 544 base::Unretained(this), entry_hash, entry); | 552 base::Unretained(this), |
| 545 it->second.push_back(base::Bind(&RunOperationAndCallback, | 553 entry_hash, |
| 546 operation, callback)); | 554 entry); |
| 555 it->second.push_back( |
| 556 base::Bind(&RunOperationAndCallback, operation, callback)); |
| 547 return net::ERR_IO_PENDING; | 557 return net::ERR_IO_PENDING; |
| 548 } | 558 } |
| 549 | 559 |
| 550 EntryMap::iterator has_active = active_entries_.find(entry_hash); | 560 EntryMap::iterator has_active = active_entries_.find(entry_hash); |
| 551 if (has_active != active_entries_.end()) { | 561 if (has_active != active_entries_.end()) { |
| 552 return OpenEntry(has_active->second->key(), entry, callback); | 562 return OpenEntry(has_active->second->key(), entry, callback); |
| 553 } | 563 } |
| 554 | 564 |
| 555 scoped_refptr<SimpleEntryImpl> simple_entry = new SimpleEntryImpl( | 565 scoped_refptr<SimpleEntryImpl> simple_entry = new SimpleEntryImpl( |
| 556 cache_type_, path_, entry_hash, entry_operations_mode_, this, net_log_); | 566 cache_type_, path_, entry_hash, entry_operations_mode_, this, net_log_); |
| 557 CompletionCallback backend_callback = | 567 CompletionCallback backend_callback = |
| 558 base::Bind(&SimpleBackendImpl::OnEntryOpenedFromHash, | 568 base::Bind(&SimpleBackendImpl::OnEntryOpenedFromHash, |
| 559 AsWeakPtr(), entry_hash, entry, simple_entry, callback); | 569 AsWeakPtr(), |
| 570 entry_hash, |
| 571 entry, |
| 572 simple_entry, |
| 573 callback); |
| 560 return simple_entry->OpenEntry(entry, backend_callback); | 574 return simple_entry->OpenEntry(entry, backend_callback); |
| 561 } | 575 } |
| 562 | 576 |
| 563 int SimpleBackendImpl::DoomEntryFromHash(uint64 entry_hash, | 577 int SimpleBackendImpl::DoomEntryFromHash(uint64 entry_hash, |
| 564 const CompletionCallback& callback) { | 578 const CompletionCallback& callback) { |
| 565 Entry** entry = new Entry*(); | 579 Entry** entry = new Entry*(); |
| 566 scoped_ptr<Entry*> scoped_entry(entry); | 580 scoped_ptr<Entry*> scoped_entry(entry); |
| 567 | 581 |
| 568 base::hash_map<uint64, std::vector<Closure> >::iterator pending_it = | 582 base::hash_map<uint64, std::vector<Closure> >::iterator pending_it = |
| 569 entries_pending_doom_.find(entry_hash); | 583 entries_pending_doom_.find(entry_hash); |
| 570 if (pending_it != entries_pending_doom_.end()) { | 584 if (pending_it != entries_pending_doom_.end()) { |
| 571 Callback<int(const net::CompletionCallback&)> operation = | 585 Callback<int(const net::CompletionCallback&)> operation = |
| 572 base::Bind(&SimpleBackendImpl::DoomEntryFromHash, | 586 base::Bind(&SimpleBackendImpl::DoomEntryFromHash, |
| 573 base::Unretained(this), entry_hash); | 587 base::Unretained(this), |
| 574 pending_it->second.push_back(base::Bind(&RunOperationAndCallback, | 588 entry_hash); |
| 575 operation, callback)); | 589 pending_it->second.push_back( |
| 590 base::Bind(&RunOperationAndCallback, operation, callback)); |
| 576 return net::ERR_IO_PENDING; | 591 return net::ERR_IO_PENDING; |
| 577 } | 592 } |
| 578 | 593 |
| 579 EntryMap::iterator active_it = active_entries_.find(entry_hash); | 594 EntryMap::iterator active_it = active_entries_.find(entry_hash); |
| 580 if (active_it != active_entries_.end()) | 595 if (active_it != active_entries_.end()) |
| 581 return active_it->second->DoomEntry(callback); | 596 return active_it->second->DoomEntry(callback); |
| 582 | 597 |
| 583 // There's no pending dooms, nor any open entry. We can make a trivial | 598 // There's no pending dooms, nor any open entry. We can make a trivial |
| 584 // call to DoomEntries() to delete this entry. | 599 // call to DoomEntries() to delete this entry. |
| 585 std::vector<uint64> entry_hash_vector; | 600 std::vector<uint64> entry_hash_vector; |
| (...skipping 14 matching lines...) Expand all Loading... |
| 600 if (*iter == NULL) { | 615 if (*iter == NULL) { |
| 601 *iter = index()->GetAllHashes().release(); | 616 *iter = index()->GetAllHashes().release(); |
| 602 } | 617 } |
| 603 SimpleIndex::HashList* entry_list = | 618 SimpleIndex::HashList* entry_list = |
| 604 static_cast<SimpleIndex::HashList*>(*iter); | 619 static_cast<SimpleIndex::HashList*>(*iter); |
| 605 while (entry_list->size() > 0) { | 620 while (entry_list->size() > 0) { |
| 606 uint64 entry_hash = entry_list->back(); | 621 uint64 entry_hash = entry_list->back(); |
| 607 entry_list->pop_back(); | 622 entry_list->pop_back(); |
| 608 if (index()->Has(entry_hash)) { | 623 if (index()->Has(entry_hash)) { |
| 609 *next_entry = NULL; | 624 *next_entry = NULL; |
| 610 CompletionCallback continue_iteration = base::Bind( | 625 CompletionCallback continue_iteration = |
| 611 &SimpleBackendImpl::CheckIterationReturnValue, | 626 base::Bind(&SimpleBackendImpl::CheckIterationReturnValue, |
| 612 AsWeakPtr(), | 627 AsWeakPtr(), |
| 613 iter, | 628 iter, |
| 614 next_entry, | 629 next_entry, |
| 615 callback); | 630 callback); |
| 616 int error_code_open = OpenEntryFromHash(entry_hash, | 631 int error_code_open = |
| 617 next_entry, | 632 OpenEntryFromHash(entry_hash, next_entry, continue_iteration); |
| 618 continue_iteration); | |
| 619 if (error_code_open == net::ERR_IO_PENDING) | 633 if (error_code_open == net::ERR_IO_PENDING) |
| 620 return; | 634 return; |
| 621 if (error_code_open != net::ERR_FAILED) { | 635 if (error_code_open != net::ERR_FAILED) { |
| 622 callback.Run(error_code_open); | 636 callback.Run(error_code_open); |
| 623 return; | 637 return; |
| 624 } | 638 } |
| 625 } | 639 } |
| 626 } | 640 } |
| 627 callback.Run(net::ERR_FAILED); | 641 callback.Run(net::ERR_FAILED); |
| 628 } | 642 } |
| 629 | 643 |
| 630 void SimpleBackendImpl::OnEntryOpenedFromHash( | 644 void SimpleBackendImpl::OnEntryOpenedFromHash( |
| 631 uint64 hash, | 645 uint64 hash, |
| 632 Entry** entry, | 646 Entry** entry, |
| 633 scoped_refptr<SimpleEntryImpl> simple_entry, | 647 scoped_refptr<SimpleEntryImpl> simple_entry, |
| 634 const CompletionCallback& callback, | 648 const CompletionCallback& callback, |
| 635 int error_code) { | 649 int error_code) { |
| 636 if (error_code != net::OK) { | 650 if (error_code != net::OK) { |
| 637 callback.Run(error_code); | 651 callback.Run(error_code); |
| 638 return; | 652 return; |
| 639 } | 653 } |
| 640 DCHECK(*entry); | 654 DCHECK(*entry); |
| 641 std::pair<EntryMap::iterator, bool> insert_result = | 655 std::pair<EntryMap::iterator, bool> insert_result = active_entries_.insert( |
| 642 active_entries_.insert(std::make_pair(hash, | 656 std::make_pair(hash, base::WeakPtr<SimpleEntryImpl>())); |
| 643 base::WeakPtr<SimpleEntryImpl>())); | |
| 644 EntryMap::iterator& it = insert_result.first; | 657 EntryMap::iterator& it = insert_result.first; |
| 645 const bool did_insert = insert_result.second; | 658 const bool did_insert = insert_result.second; |
| 646 if (did_insert) { | 659 if (did_insert) { |
| 647 // There is no active entry corresponding to this hash. The entry created | 660 // There is no active entry corresponding to this hash. The entry created |
| 648 // is put in the map of active entries and returned to the caller. | 661 // is put in the map of active entries and returned to the caller. |
| 649 it->second = simple_entry->AsWeakPtr(); | 662 it->second = simple_entry->AsWeakPtr(); |
| 650 callback.Run(error_code); | 663 callback.Run(error_code); |
| 651 } else { | 664 } else { |
| 652 // The entry was made active with the key while the creation from hash | 665 // The entry was made active with the key while the creation from hash |
| 653 // occurred. The entry created from hash needs to be closed, and the one | 666 // occurred. The entry created from hash needs to be closed, and the one |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 690 return; | 703 return; |
| 691 } | 704 } |
| 692 callback.Run(error_code); | 705 callback.Run(error_code); |
| 693 } | 706 } |
| 694 | 707 |
| 695 void SimpleBackendImpl::DoomEntriesComplete( | 708 void SimpleBackendImpl::DoomEntriesComplete( |
| 696 scoped_ptr<std::vector<uint64> > entry_hashes, | 709 scoped_ptr<std::vector<uint64> > entry_hashes, |
| 697 const net::CompletionCallback& callback, | 710 const net::CompletionCallback& callback, |
| 698 int result) { | 711 int result) { |
| 699 std::for_each( | 712 std::for_each( |
| 700 entry_hashes->begin(), entry_hashes->end(), | 713 entry_hashes->begin(), |
| 701 std::bind1st(std::mem_fun(&SimpleBackendImpl::OnDoomComplete), | 714 entry_hashes->end(), |
| 702 this)); | 715 std::bind1st(std::mem_fun(&SimpleBackendImpl::OnDoomComplete), this)); |
| 703 callback.Run(result); | 716 callback.Run(result); |
| 704 } | 717 } |
| 705 | 718 |
| 706 void SimpleBackendImpl::FlushWorkerPoolForTesting() { | 719 void SimpleBackendImpl::FlushWorkerPoolForTesting() { |
| 707 if (g_sequenced_worker_pool) | 720 if (g_sequenced_worker_pool) |
| 708 g_sequenced_worker_pool->FlushForTesting(); | 721 g_sequenced_worker_pool->FlushForTesting(); |
| 709 } | 722 } |
| 710 | 723 |
| 711 } // namespace disk_cache | 724 } // namespace disk_cache |
| OLD | NEW |