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

Side by Side Diff: chrome/browser/sync_file_system/local/local_file_change_tracker.cc

Issue 394033005: [SyncFS] Make the snapshot sync of local-to-remote sync parallelization enabled. (2/3) (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 5 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 2013 The Chromium Authors. All rights reserved. 1 // Copyright 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 "chrome/browser/sync_file_system/local/local_file_change_tracker.h" 5 #include "chrome/browser/sync_file_system/local/local_file_change_tracker.h"
6 6
7 #include <queue> 7 #include <queue>
8 8
9 #include "base/location.h" 9 #include "base/location.h"
10 #include "base/logging.h" 10 #include "base/logging.h"
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
72 72
73 // LocalFileChangeTracker ------------------------------------------------------ 73 // LocalFileChangeTracker ------------------------------------------------------
74 74
75 LocalFileChangeTracker::LocalFileChangeTracker( 75 LocalFileChangeTracker::LocalFileChangeTracker(
76 const base::FilePath& base_path, 76 const base::FilePath& base_path,
77 leveldb::Env* env_override, 77 leveldb::Env* env_override,
78 base::SequencedTaskRunner* file_task_runner) 78 base::SequencedTaskRunner* file_task_runner)
79 : initialized_(false), 79 : initialized_(false),
80 file_task_runner_(file_task_runner), 80 file_task_runner_(file_task_runner),
81 tracker_db_(new TrackerDB(base_path, env_override)), 81 tracker_db_(new TrackerDB(base_path, env_override)),
82 current_change_seq_(0), 82 current_change_seq_number_(0),
83 num_changes_(0) { 83 num_changes_(0) {
84 } 84 }
85 85
86 LocalFileChangeTracker::~LocalFileChangeTracker() { 86 LocalFileChangeTracker::~LocalFileChangeTracker() {
87 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 87 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
88 tracker_db_.reset(); 88 tracker_db_.reset();
89 } 89 }
90 90
91 void LocalFileChangeTracker::OnStartUpdate(const FileSystemURL& url) { 91 void LocalFileChangeTracker::OnStartUpdate(const FileSystemURL& url) {
92 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 92 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
93 if (ContainsKey(changes_, url)) 93 if (ContainsKey(changes_, url) || ContainsKey(demoted_changes_, url))
94 return; 94 return;
95 // TODO(nhiroki): propagate the error code (see http://crbug.com/152127). 95 // TODO(nhiroki): propagate the error code (see http://crbug.com/152127).
96 MarkDirtyOnDatabase(url); 96 MarkDirtyOnDatabase(url);
97 } 97 }
98 98
99 void LocalFileChangeTracker::OnEndUpdate(const FileSystemURL& url) {} 99 void LocalFileChangeTracker::OnEndUpdate(const FileSystemURL& url) {}
100 100
101 void LocalFileChangeTracker::OnCreateFile(const FileSystemURL& url) { 101 void LocalFileChangeTracker::OnCreateFile(const FileSystemURL& url) {
102 RecordChange(url, FileChange(FileChange::FILE_CHANGE_ADD_OR_UPDATE, 102 RecordChange(url, FileChange(FileChange::FILE_CHANGE_ADD_OR_UPDATE,
103 SYNC_FILE_TYPE_FILE)); 103 SYNC_FILE_TYPE_FILE));
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after
179 } 179 }
180 180
181 void LocalFileChangeTracker::RemoveMirrorAndCommitChangesForURL( 181 void LocalFileChangeTracker::RemoveMirrorAndCommitChangesForURL(
182 const fileapi::FileSystemURL& url) { 182 const fileapi::FileSystemURL& url) {
183 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 183 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
184 FileChangeMap::iterator found = mirror_changes_.find(url); 184 FileChangeMap::iterator found = mirror_changes_.find(url);
185 if (found == mirror_changes_.end()) 185 if (found == mirror_changes_.end())
186 return; 186 return;
187 mirror_changes_.erase(found); 187 mirror_changes_.erase(found);
188 188
189 if (ContainsKey(changes_, url)) 189 if (ContainsKey(changes_, url) || ContainsKey(demoted_changes_, url))
190 MarkDirtyOnDatabase(url); 190 MarkDirtyOnDatabase(url);
191 else 191 else
192 ClearDirtyOnDatabase(url); 192 ClearDirtyOnDatabase(url);
193 UpdateNumChanges(); 193 UpdateNumChanges();
194 } 194 }
195 195
196 void LocalFileChangeTracker::ResetToMirrorAndCommitChangesForURL( 196 void LocalFileChangeTracker::ResetToMirrorAndCommitChangesForURL(
197 const fileapi::FileSystemURL& url) { 197 const fileapi::FileSystemURL& url) {
198 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 198 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
199 FileChangeMap::iterator found = mirror_changes_.find(url); 199 FileChangeMap::iterator found = mirror_changes_.find(url);
200 if (found == mirror_changes_.end() || found->second.change_list.empty()) { 200 if (found == mirror_changes_.end() || found->second.change_list.empty()) {
201 ClearChangesForURL(url); 201 ClearChangesForURL(url);
202 return; 202 return;
203 } 203 }
204 const ChangeInfo& info = found->second; 204 const ChangeInfo& info = found->second;
205 change_seqs_[info.change_seq] = url; 205 if (ContainsKey(demoted_changes_, url)) {
206 changes_[url] = info; 206 DCHECK(!ContainsKey(changes_, url));
207 demoted_changes_[url] = info;
208 } else {
209 DCHECK(!ContainsKey(demoted_changes_, url));
210 change_seqs_[info.change_seq] = url;
211 changes_[url] = info;
212 }
207 RemoveMirrorAndCommitChangesForURL(url); 213 RemoveMirrorAndCommitChangesForURL(url);
208 } 214 }
209 215
210 void LocalFileChangeTracker::DemoteChangesForURL( 216 void LocalFileChangeTracker::DemoteChangesForURL(
211 const fileapi::FileSystemURL& url) { 217 const fileapi::FileSystemURL& url) {
212 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 218 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
219
213 FileChangeMap::iterator found = changes_.find(url); 220 FileChangeMap::iterator found = changes_.find(url);
214 if (found == changes_.end()) 221 if (found == changes_.end())
215 return; 222 return;
216 FileChangeList changes = found->second.change_list; 223 DCHECK(!ContainsKey(demoted_changes_, url));
217
218 mirror_changes_.erase(url);
219 change_seqs_.erase(found->second.change_seq); 224 change_seqs_.erase(found->second.change_seq);
225 demoted_changes_.insert(*found);
220 changes_.erase(found); 226 changes_.erase(found);
221
222 FileChangeList::List change_list = changes.list();
223 while (!change_list.empty()) {
224 RecordChangeToChangeMaps(url, change_list.front(), 0,
225 &demoted_changes_, NULL);
226 change_list.pop_front();
227 }
228 UpdateNumChanges(); 227 UpdateNumChanges();
229 } 228 }
230 229
231 void LocalFileChangeTracker::PromoteDemotedChangesForURL( 230 void LocalFileChangeTracker::PromoteDemotedChangesForURL(
232 const fileapi::FileSystemURL& url) { 231 const fileapi::FileSystemURL& url) {
233 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 232 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
234 233
235 FileChangeMap::iterator iter = demoted_changes_.find(url); 234 FileChangeMap::iterator iter = demoted_changes_.find(url);
236 if (iter == demoted_changes_.end()) 235 if (iter == demoted_changes_.end())
237 return; 236 return;
238 237
239 FileChangeList::List change_list = iter->second.change_list.list(); 238 FileChangeList::List change_list = iter->second.change_list.list();
240 // Make sure that this URL is in no queues. 239 // Make sure that this URL is in no queues.
240 DCHECK(!ContainsKey(change_seqs_, iter->second.change_seq));
241 DCHECK(!ContainsKey(changes_, url)); 241 DCHECK(!ContainsKey(changes_, url));
242 DCHECK(!ContainsKey(mirror_changes_, url));
243 242
243 change_seqs_[iter->second.change_seq] = url;
244 changes_.insert(*iter);
244 demoted_changes_.erase(iter); 245 demoted_changes_.erase(iter);
245
246 while (!change_list.empty()) {
247 RecordChange(url, change_list.front());
248 change_list.pop_front();
249 }
250 } 246 }
251 247
252 bool LocalFileChangeTracker::PromoteDemotedChanges() { 248 bool LocalFileChangeTracker::PromoteDemotedChanges() {
253 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 249 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
254 if (demoted_changes_.empty()) 250 if (demoted_changes_.empty())
255 return false; 251 return false;
256 while (!demoted_changes_.empty()) { 252 while (!demoted_changes_.empty()) {
257 fileapi::FileSystemURL url = demoted_changes_.begin()->first; 253 fileapi::FileSystemURL url = demoted_changes_.begin()->first;
258 PromoteDemotedChangesForURL(url); 254 PromoteDemotedChangesForURL(url);
259 } 255 }
(...skipping 14 matching lines...) Expand all
274 } 270 }
275 271
276 void LocalFileChangeTracker::ResetForFileSystem( 272 void LocalFileChangeTracker::ResetForFileSystem(
277 const GURL& origin, 273 const GURL& origin,
278 fileapi::FileSystemType type) { 274 fileapi::FileSystemType type) {
279 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 275 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
280 scoped_ptr<leveldb::WriteBatch> batch(new leveldb::WriteBatch); 276 scoped_ptr<leveldb::WriteBatch> batch(new leveldb::WriteBatch);
281 for (FileChangeMap::iterator iter = changes_.begin(); 277 for (FileChangeMap::iterator iter = changes_.begin();
282 iter != changes_.end();) { 278 iter != changes_.end();) {
283 fileapi::FileSystemURL url = iter->first; 279 fileapi::FileSystemURL url = iter->first;
284 if (url.origin() != origin || url.type() != type) { 280 int change_seq = iter->second.change_seq;
285 ++iter; 281 // Advance |iter| before calling ResetForURL to avoid the iterator
286 continue; 282 // invalidation in it.
287 } 283 ++iter;
288 mirror_changes_.erase(url); 284 if (url.origin() == origin && url.type() == type)
289 demoted_changes_.erase(url); 285 ResetForURL(url, change_seq, batch.get());
290 change_seqs_.erase(iter->second.change_seq); 286 }
291 changes_.erase(iter++);
292 287
293 std::string serialized_url; 288 for (FileChangeMap::iterator iter = demoted_changes_.begin();
294 const bool should_success = 289 iter != demoted_changes_.end();) {
295 SerializeSyncableFileSystemURL(url, &serialized_url); 290 fileapi::FileSystemURL url = iter->first;
296 if (!should_success) { 291 int change_seq = iter->second.change_seq;
297 NOTREACHED() << "Failed to serialize: " << url.DebugString(); 292 // Advance |iter| before calling ResetForURL to avoid the iterator
298 continue; 293 // invalidation in it.
299 } 294 ++iter;
300 batch->Delete(serialized_url); 295 if (url.origin() == origin && url.type() == type)
296 ResetForURL(url, change_seq, batch.get());
301 } 297 }
298
302 // Fail to apply batch to database wouldn't have critical effect, they'll be 299 // Fail to apply batch to database wouldn't have critical effect, they'll be
303 // just marked deleted on next relaunch. 300 // just marked deleted on next relaunch.
304 tracker_db_->WriteBatch(batch.Pass()); 301 tracker_db_->WriteBatch(batch.Pass());
305 UpdateNumChanges(); 302 UpdateNumChanges();
306 } 303 }
307 304
308 void LocalFileChangeTracker::UpdateNumChanges() { 305 void LocalFileChangeTracker::UpdateNumChanges() {
309 base::AutoLock lock(num_changes_lock_); 306 base::AutoLock lock(num_changes_lock_);
310 num_changes_ = static_cast<int64>(change_seqs_.size()); 307 num_changes_ = static_cast<int64>(change_seqs_.size());
311 } 308 }
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after
408 LOG(WARNING) << "Failed to access local file."; 405 LOG(WARNING) << "Failed to access local file.";
409 break; 406 break;
410 } 407 }
411 } 408 }
412 return SYNC_STATUS_OK; 409 return SYNC_STATUS_OK;
413 } 410 }
414 411
415 void LocalFileChangeTracker::RecordChange( 412 void LocalFileChangeTracker::RecordChange(
416 const FileSystemURL& url, const FileChange& change) { 413 const FileSystemURL& url, const FileChange& change) {
417 DCHECK(file_task_runner_->RunsTasksOnCurrentThread()); 414 DCHECK(file_task_runner_->RunsTasksOnCurrentThread());
415 int change_seq = current_change_seq_number_++;
418 if (ContainsKey(demoted_changes_, url)) { 416 if (ContainsKey(demoted_changes_, url)) {
419 RecordChangeToChangeMaps(url, change, 0, &demoted_changes_, NULL); 417 RecordChangeToChangeMaps(url, change, change_seq,
420 return; 418 &demoted_changes_, NULL);
419 } else {
420 RecordChangeToChangeMaps(url, change, change_seq, &changes_, &change_seqs_);
421 } 421 }
422 int change_seq = current_change_seq_++;
423 RecordChangeToChangeMaps(url, change, change_seq, &changes_, &change_seqs_);
424 if (ContainsKey(mirror_changes_, url)) 422 if (ContainsKey(mirror_changes_, url))
425 RecordChangeToChangeMaps(url, change, change_seq, &mirror_changes_, NULL); 423 RecordChangeToChangeMaps(url, change, change_seq, &mirror_changes_, NULL);
426 UpdateNumChanges(); 424 UpdateNumChanges();
427 } 425 }
428 426
429 // static 427 // static
430 void LocalFileChangeTracker::RecordChangeToChangeMaps( 428 void LocalFileChangeTracker::RecordChangeToChangeMaps(
431 const FileSystemURL& url, 429 const FileSystemURL& url,
432 const FileChange& change, 430 const FileChange& change,
433 int new_change_seq, 431 int new_change_seq,
434 FileChangeMap* changes, 432 FileChangeMap* changes,
435 ChangeSeqMap* change_seqs) { 433 ChangeSeqMap* change_seqs) {
436 ChangeInfo& info = (*changes)[url]; 434 ChangeInfo& info = (*changes)[url];
437 if (info.change_seq >= 0 && change_seqs) 435 if (info.change_seq >= 0 && change_seqs)
438 change_seqs->erase(info.change_seq); 436 change_seqs->erase(info.change_seq);
439 info.change_list.Update(change); 437 info.change_list.Update(change);
440 if (info.change_list.empty()) { 438 if (info.change_list.empty()) {
441 changes->erase(url); 439 changes->erase(url);
442 return; 440 return;
443 } 441 }
444 info.change_seq = new_change_seq; 442 info.change_seq = new_change_seq;
445 if (change_seqs) 443 if (change_seqs)
446 (*change_seqs)[info.change_seq] = url; 444 (*change_seqs)[info.change_seq] = url;
447 } 445 }
448 446
447 void LocalFileChangeTracker::ResetForURL(const fileapi::FileSystemURL& url,
448 int change_seq,
449 leveldb::WriteBatch* batch) {
450 mirror_changes_.erase(url);
451 demoted_changes_.erase(url);
452 change_seqs_.erase(change_seq);
453 changes_.erase(url);
454
455 std::string serialized_url;
456 if (!SerializeSyncableFileSystemURL(url, &serialized_url)) {
457 NOTREACHED() << "Failed to serialize: " << url.DebugString();
458 return;
459 }
460 batch->Delete(serialized_url);
461 }
462
449 // TrackerDB ------------------------------------------------------------------- 463 // TrackerDB -------------------------------------------------------------------
450 464
451 LocalFileChangeTracker::TrackerDB::TrackerDB(const base::FilePath& base_path, 465 LocalFileChangeTracker::TrackerDB::TrackerDB(const base::FilePath& base_path,
452 leveldb::Env* env_override) 466 leveldb::Env* env_override)
453 : base_path_(base_path), 467 : base_path_(base_path),
454 env_override_(env_override), 468 env_override_(env_override),
455 db_status_(SYNC_STATUS_OK) {} 469 db_status_(SYNC_STATUS_OK) {}
456 470
457 SyncStatusCode LocalFileChangeTracker::TrackerDB::Init( 471 SyncStatusCode LocalFileChangeTracker::TrackerDB::Init(
458 RecoveryOption recovery_option) { 472 RecoveryOption recovery_option) {
(...skipping 134 matching lines...) Expand 10 before | Expand all | Expand 10 after
593 if (!status.ok() && !status.IsNotFound()) { 607 if (!status.ok() && !status.IsNotFound()) {
594 HandleError(FROM_HERE, status); 608 HandleError(FROM_HERE, status);
595 db_status_ = LevelDBStatusToSyncStatusCode(status); 609 db_status_ = LevelDBStatusToSyncStatusCode(status);
596 db_.reset(); 610 db_.reset();
597 return db_status_; 611 return db_status_;
598 } 612 }
599 return SYNC_STATUS_OK; 613 return SYNC_STATUS_OK;
600 } 614 }
601 615
602 } // namespace sync_file_system 616 } // namespace sync_file_system
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698