Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(447)

Side by Side Diff: webkit/browser/appcache/appcache_disk_cache.cc

Issue 137493003: Appcache::OnCorruptionDetected handling (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "webkit/browser/appcache/appcache_disk_cache.h" 5 #include "webkit/browser/appcache/appcache_disk_cache.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/bind_helpers.h" 8 #include "base/bind_helpers.h"
9 #include "base/files/file_path.h" 9 #include "base/files/file_path.h"
10 #include "base/logging.h" 10 #include "base/logging.h"
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
42 ~CreateBackendCallbackShim() { 42 ~CreateBackendCallbackShim() {
43 } 43 }
44 44
45 AppCacheDiskCache* appcache_diskcache_; // Unowned pointer. 45 AppCacheDiskCache* appcache_diskcache_; // Unowned pointer.
46 }; 46 };
47 47
48 // An implementation of AppCacheDiskCacheInterface::Entry that's a thin 48 // An implementation of AppCacheDiskCacheInterface::Entry that's a thin
49 // wrapper around disk_cache::Entry. 49 // wrapper around disk_cache::Entry.
50 class AppCacheDiskCache::EntryImpl : public Entry { 50 class AppCacheDiskCache::EntryImpl : public Entry {
51 public: 51 public:
52 explicit EntryImpl(disk_cache::Entry* disk_cache_entry) 52 EntryImpl(disk_cache::Entry* disk_cache_entry,
53 : disk_cache_entry_(disk_cache_entry) { 53 AppCacheDiskCache* owner)
54 : disk_cache_entry_(disk_cache_entry), owner_(owner) {
54 DCHECK(disk_cache_entry); 55 DCHECK(disk_cache_entry);
56 DCHECK(owner);
57 owner_->AddOpenEntry(this);
55 } 58 }
56 59
57 // Entry implementation. 60 // Entry implementation.
58 virtual int Read(int index, int64 offset, net::IOBuffer* buf, int buf_len, 61 virtual int Read(int index, int64 offset, net::IOBuffer* buf, int buf_len,
59 const net::CompletionCallback& callback) OVERRIDE { 62 const net::CompletionCallback& callback) OVERRIDE {
60 if (offset < 0 || offset > kint32max) 63 if (offset < 0 || offset > kint32max)
61 return net::ERR_INVALID_ARGUMENT; 64 return net::ERR_INVALID_ARGUMENT;
65 if (!disk_cache_entry_)
66 return net::ERR_ABORTED;
62 return disk_cache_entry_->ReadData( 67 return disk_cache_entry_->ReadData(
63 index, static_cast<int>(offset), buf, buf_len, callback); 68 index, static_cast<int>(offset), buf, buf_len, callback);
64 } 69 }
65 70
66 virtual int Write(int index, int64 offset, net::IOBuffer* buf, int buf_len, 71 virtual int Write(int index, int64 offset, net::IOBuffer* buf, int buf_len,
67 const net::CompletionCallback& callback) OVERRIDE { 72 const net::CompletionCallback& callback) OVERRIDE {
68 if (offset < 0 || offset > kint32max) 73 if (offset < 0 || offset > kint32max)
69 return net::ERR_INVALID_ARGUMENT; 74 return net::ERR_INVALID_ARGUMENT;
75 if (!disk_cache_entry_)
76 return net::ERR_ABORTED;
70 const bool kTruncate = true; 77 const bool kTruncate = true;
71 return disk_cache_entry_->WriteData( 78 return disk_cache_entry_->WriteData(
72 index, static_cast<int>(offset), buf, buf_len, callback, kTruncate); 79 index, static_cast<int>(offset), buf, buf_len, callback, kTruncate);
73 } 80 }
74 81
75 virtual int64 GetSize(int index) OVERRIDE { 82 virtual int64 GetSize(int index) OVERRIDE {
76 return disk_cache_entry_->GetDataSize(index); 83 return disk_cache_entry_ ? disk_cache_entry_->GetDataSize(index) : 0L;
77 } 84 }
78 85
79 virtual void Close() OVERRIDE { 86 virtual void Close() OVERRIDE {
80 disk_cache_entry_->Close(); 87 if (disk_cache_entry_)
88 disk_cache_entry_->Close();
81 delete this; 89 delete this;
82 } 90 }
83 91
92 void Abandon() {
93 owner_ = NULL;
94 disk_cache_entry_->Close();
95 disk_cache_entry_ = NULL;
96 }
97
84 private: 98 private:
99 virtual ~EntryImpl() {
100 if (owner_)
101 owner_->RemoveOpenEntry(this);
102 }
103
85 disk_cache::Entry* disk_cache_entry_; 104 disk_cache::Entry* disk_cache_entry_;
105 AppCacheDiskCache* owner_;
86 }; 106 };
87 107
88 // Separate object to hold state for each Create, Delete, or Doom call 108 // Separate object to hold state for each Create, Delete, or Doom call
89 // while the call is in-flight and to produce an EntryImpl upon completion. 109 // while the call is in-flight and to produce an EntryImpl upon completion.
90 class AppCacheDiskCache::ActiveCall { 110 class AppCacheDiskCache::ActiveCall {
91 public: 111 public:
92 explicit ActiveCall(AppCacheDiskCache* owner) 112 explicit ActiveCall(AppCacheDiskCache* owner)
93 : entry_(NULL), 113 : entry_(NULL),
94 owner_(owner), 114 owner_(owner),
95 entry_ptr_(NULL) { 115 entry_ptr_(NULL) {
(...skipping 26 matching lines...) Expand all
122 int HandleImmediateReturnValue(int rv, Entry** entry, 142 int HandleImmediateReturnValue(int rv, Entry** entry,
123 const net::CompletionCallback& callback) { 143 const net::CompletionCallback& callback) {
124 if (rv == net::ERR_IO_PENDING) { 144 if (rv == net::ERR_IO_PENDING) {
125 // OnAsyncCompletion will be called later. 145 // OnAsyncCompletion will be called later.
126 callback_ = callback; 146 callback_ = callback;
127 entry_ = entry; 147 entry_ = entry;
128 owner_->AddActiveCall(this); 148 owner_->AddActiveCall(this);
129 return net::ERR_IO_PENDING; 149 return net::ERR_IO_PENDING;
130 } 150 }
131 if (rv == net::OK && entry) 151 if (rv == net::OK && entry)
132 *entry = new EntryImpl(entry_ptr_); 152 *entry = new EntryImpl(entry_ptr_, owner_);
133 delete this; 153 delete this;
134 return rv; 154 return rv;
135 } 155 }
136 156
137 void OnAsyncCompletion(int rv) { 157 void OnAsyncCompletion(int rv) {
138 owner_->RemoveActiveCall(this); 158 owner_->RemoveActiveCall(this);
139 if (rv == net::OK && entry_) 159 if (rv == net::OK && entry_)
140 *entry_ = new EntryImpl(entry_ptr_); 160 *entry_ = new EntryImpl(entry_ptr_, owner_);
141 callback_.Run(rv); 161 callback_.Run(rv);
142 callback_.Reset(); 162 callback_.Reset();
143 delete this; 163 delete this;
144 } 164 }
145 165
146 Entry** entry_; 166 Entry** entry_;
147 net::CompletionCallback callback_; 167 net::CompletionCallback callback_;
148 AppCacheDiskCache* owner_; 168 AppCacheDiskCache* owner_;
149 disk_cache::Entry* entry_ptr_; 169 disk_cache::Entry* entry_ptr_;
150 }; 170 };
151 171
152 AppCacheDiskCache::AppCacheDiskCache() 172 AppCacheDiskCache::AppCacheDiskCache()
153 : is_disabled_(false) { 173 : is_disabled_(false) {
154 } 174 }
155 175
156 AppCacheDiskCache::~AppCacheDiskCache() { 176 AppCacheDiskCache::~AppCacheDiskCache() {
157 if (create_backend_callback_.get()) { 177 Disable();
158 create_backend_callback_->Cancel();
159 create_backend_callback_ = NULL;
160 OnCreateBackendComplete(net::ERR_ABORTED);
161 }
162 disk_cache_.reset();
163 STLDeleteElements(&active_calls_);
164 } 178 }
165 179
166 int AppCacheDiskCache::InitWithDiskBackend( 180 int AppCacheDiskCache::InitWithDiskBackend(
167 const base::FilePath& disk_cache_directory, int disk_cache_size, bool force, 181 const base::FilePath& disk_cache_directory, int disk_cache_size, bool force,
168 base::MessageLoopProxy* cache_thread, 182 base::MessageLoopProxy* cache_thread,
169 const net::CompletionCallback& callback) { 183 const net::CompletionCallback& callback) {
170 return Init(net::APP_CACHE, disk_cache_directory, 184 return Init(net::APP_CACHE, disk_cache_directory,
171 disk_cache_size, force, cache_thread, callback); 185 disk_cache_size, force, cache_thread, callback);
172 } 186 }
173 187
174 int AppCacheDiskCache::InitWithMemBackend( 188 int AppCacheDiskCache::InitWithMemBackend(
175 int mem_cache_size, const net::CompletionCallback& callback) { 189 int mem_cache_size, const net::CompletionCallback& callback) {
176 return Init(net::MEMORY_CACHE, base::FilePath(), mem_cache_size, false, NULL, 190 return Init(net::MEMORY_CACHE, base::FilePath(), mem_cache_size, false, NULL,
177 callback); 191 callback);
178 } 192 }
179 193
180 void AppCacheDiskCache::Disable() { 194 void AppCacheDiskCache::Disable() {
181 if (is_disabled_) 195 if (is_disabled_)
182 return; 196 return;
183 197
184 is_disabled_ = true; 198 is_disabled_ = true;
185 199
186 if (create_backend_callback_.get()) { 200 if (create_backend_callback_.get()) {
187 create_backend_callback_->Cancel(); 201 create_backend_callback_->Cancel();
188 create_backend_callback_ = NULL; 202 create_backend_callback_ = NULL;
189 OnCreateBackendComplete(net::ERR_ABORTED); 203 OnCreateBackendComplete(net::ERR_ABORTED);
190 } 204 }
205
206 // We need to close open file handles in order to reinitalize the
207 // appcache system on the fly. File handles held in both entries and in
208 // the main disk_cache::Backend class need to be released.
209 for (OpenEntries::const_iterator iter = open_entries_.begin();
210 iter != open_entries_.end(); ++iter) {
211 (*iter)->Abandon();
212 }
213 open_entries_.clear();
214 disk_cache_.reset();
215 STLDeleteElements(&active_calls_);
191 } 216 }
192 217
193 int AppCacheDiskCache::CreateEntry(int64 key, Entry** entry, 218 int AppCacheDiskCache::CreateEntry(int64 key, Entry** entry,
194 const net::CompletionCallback& callback) { 219 const net::CompletionCallback& callback) {
195 DCHECK(entry); 220 DCHECK(entry);
196 DCHECK(!callback.is_null()); 221 DCHECK(!callback.is_null());
197 if (is_disabled_) 222 if (is_disabled_)
198 return net::ERR_ABORTED; 223 return net::ERR_ABORTED;
199 224
200 if (is_initializing()) { 225 if (is_initializing()) {
(...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after
317 NOTREACHED(); 342 NOTREACHED();
318 break; 343 break;
319 } 344 }
320 if (rv != net::ERR_IO_PENDING) 345 if (rv != net::ERR_IO_PENDING)
321 iter->callback.Run(rv); 346 iter->callback.Run(rv);
322 } 347 }
323 pending_calls_.clear(); 348 pending_calls_.clear();
324 } 349 }
325 350
326 } // namespace appcache 351 } // namespace appcache
OLDNEW
« no previous file with comments | « webkit/browser/appcache/appcache_disk_cache.h ('k') | webkit/browser/appcache/appcache_disk_cache_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698