OLD | NEW |
---|---|
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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/syncable/syncable.h" | 5 #include "chrome/browser/sync/syncable/syncable.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 #include <cstring> | 8 #include <cstring> |
9 #include <functional> | 9 #include <functional> |
10 #include <iomanip> | 10 #include <iomanip> |
(...skipping 331 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
342 SetFieldValues(*this, kernel_info, | 342 SetFieldValues(*this, kernel_info, |
343 &GetBitTempString, &Value::CreateBooleanValue, | 343 &GetBitTempString, &Value::CreateBooleanValue, |
344 BIT_TEMPS_BEGIN, BIT_TEMPS_END - 1); | 344 BIT_TEMPS_BEGIN, BIT_TEMPS_END - 1); |
345 | 345 |
346 return kernel_info; | 346 return kernel_info; |
347 } | 347 } |
348 | 348 |
349 /////////////////////////////////////////////////////////////////////////// | 349 /////////////////////////////////////////////////////////////////////////// |
350 // Directory | 350 // Directory |
351 | 351 |
352 void Directory::InitKernel(const std::string& name, | 352 void Directory::InitKernelForTest( |
353 DirectoryChangeDelegate* delegate) { | 353 const std::string& name, |
354 DCHECK(kernel_ == NULL); | 354 DirectoryChangeDelegate* delegate, |
355 kernel_ = new Kernel(FilePath(), name, KernelLoadInfo(), delegate); | 355 const browser_sync::WeakHandle<TransactionObserver>& |
356 transaction_observer) { | |
357 DCHECK(!kernel_); | |
358 kernel_ = | |
359 new Kernel(FilePath(), name, KernelLoadInfo(), | |
Nicolas Zea
2011/11/17 21:35:45
does this not fit on previous line?
akalin
2011/11/18 00:04:32
Sure. Fixed.
| |
360 delegate, transaction_observer); | |
356 } | 361 } |
357 | 362 |
358 Directory::PersistedKernelInfo::PersistedKernelInfo() | 363 Directory::PersistedKernelInfo::PersistedKernelInfo() |
359 : next_id(0) { | 364 : next_id(0) { |
360 for (int i = FIRST_REAL_MODEL_TYPE; i < MODEL_TYPE_COUNT; ++i) { | 365 for (int i = FIRST_REAL_MODEL_TYPE; i < MODEL_TYPE_COUNT; ++i) { |
361 reset_download_progress(ModelTypeFromInt(i)); | 366 reset_download_progress(ModelTypeFromInt(i)); |
362 } | 367 } |
363 } | 368 } |
364 | 369 |
365 Directory::PersistedKernelInfo::~PersistedKernelInfo() {} | 370 Directory::PersistedKernelInfo::~PersistedKernelInfo() {} |
366 | 371 |
367 void Directory::PersistedKernelInfo::reset_download_progress( | 372 void Directory::PersistedKernelInfo::reset_download_progress( |
368 ModelType model_type) { | 373 ModelType model_type) { |
369 download_progress[model_type].set_data_type_id( | 374 download_progress[model_type].set_data_type_id( |
370 GetExtensionFieldNumberFromModelType(model_type)); | 375 GetExtensionFieldNumberFromModelType(model_type)); |
371 // An empty-string token indicates no prior knowledge. | 376 // An empty-string token indicates no prior knowledge. |
372 download_progress[model_type].set_token(std::string()); | 377 download_progress[model_type].set_token(std::string()); |
373 } | 378 } |
374 | 379 |
375 Directory::SaveChangesSnapshot::SaveChangesSnapshot() | 380 Directory::SaveChangesSnapshot::SaveChangesSnapshot() |
376 : kernel_info_status(KERNEL_SHARE_INFO_INVALID) { | 381 : kernel_info_status(KERNEL_SHARE_INFO_INVALID) { |
377 } | 382 } |
378 | 383 |
379 Directory::SaveChangesSnapshot::~SaveChangesSnapshot() {} | 384 Directory::SaveChangesSnapshot::~SaveChangesSnapshot() {} |
380 | 385 |
381 Directory::Kernel::Kernel(const FilePath& db_path, | 386 Directory::Kernel::Kernel( |
382 const string& name, | 387 const FilePath& db_path, const string& name, |
383 const KernelLoadInfo& info, | 388 const KernelLoadInfo& info, DirectoryChangeDelegate* delegate, |
384 DirectoryChangeDelegate* delegate) | 389 const browser_sync::WeakHandle<TransactionObserver>& |
390 transaction_observer) | |
385 : db_path(db_path), | 391 : db_path(db_path), |
386 refcount(1), | 392 refcount(1), |
387 next_write_transaction_id(0), | 393 next_write_transaction_id(0), |
388 name(name), | 394 name(name), |
389 metahandles_index(new Directory::MetahandlesIndex), | 395 metahandles_index(new Directory::MetahandlesIndex), |
390 ids_index(new Directory::IdsIndex), | 396 ids_index(new Directory::IdsIndex), |
391 parent_id_child_index(new Directory::ParentIdChildIndex), | 397 parent_id_child_index(new Directory::ParentIdChildIndex), |
392 client_tag_index(new Directory::ClientTagIndex), | 398 client_tag_index(new Directory::ClientTagIndex), |
393 unapplied_update_metahandles(new MetahandleSet), | 399 unapplied_update_metahandles(new MetahandleSet), |
394 unsynced_metahandles(new MetahandleSet), | 400 unsynced_metahandles(new MetahandleSet), |
395 dirty_metahandles(new MetahandleSet), | 401 dirty_metahandles(new MetahandleSet), |
396 metahandles_to_purge(new MetahandleSet), | 402 metahandles_to_purge(new MetahandleSet), |
397 info_status(Directory::KERNEL_SHARE_INFO_VALID), | 403 info_status(Directory::KERNEL_SHARE_INFO_VALID), |
398 persisted_info(info.kernel_info), | 404 persisted_info(info.kernel_info), |
399 cache_guid(info.cache_guid), | 405 cache_guid(info.cache_guid), |
400 next_metahandle(info.max_metahandle + 1), | 406 next_metahandle(info.max_metahandle + 1), |
401 delegate(delegate), | 407 delegate(delegate), |
402 observers(new ObserverListThreadSafe<TransactionObserver>()) { | 408 transaction_observer(transaction_observer) { |
403 DCHECK(delegate); | 409 DCHECK(delegate); |
410 DCHECK(transaction_observer.IsInitialized()); | |
404 } | 411 } |
405 | 412 |
406 void Directory::Kernel::AddRef() { | 413 void Directory::Kernel::AddRef() { |
407 base::subtle::NoBarrier_AtomicIncrement(&refcount, 1); | 414 base::subtle::NoBarrier_AtomicIncrement(&refcount, 1); |
408 } | 415 } |
409 | 416 |
410 void Directory::Kernel::Release() { | 417 void Directory::Kernel::Release() { |
411 if (!base::subtle::NoBarrier_AtomicIncrement(&refcount, -1)) | 418 if (!base::subtle::NoBarrier_AtomicIncrement(&refcount, -1)) |
412 delete this; | 419 delete this; |
413 } | 420 } |
(...skipping 11 matching lines...) Expand all Loading... | |
425 delete metahandles_index; | 432 delete metahandles_index; |
426 } | 433 } |
427 | 434 |
428 Directory::Directory() : kernel_(NULL), store_(NULL) { | 435 Directory::Directory() : kernel_(NULL), store_(NULL) { |
429 } | 436 } |
430 | 437 |
431 Directory::~Directory() { | 438 Directory::~Directory() { |
432 Close(); | 439 Close(); |
433 } | 440 } |
434 | 441 |
435 DirOpenResult Directory::Open(const FilePath& file_path, const string& name, | 442 DirOpenResult Directory::Open( |
436 DirectoryChangeDelegate* delegate) { | 443 const FilePath& file_path, const string& name, |
437 const DirOpenResult result = OpenImpl(file_path, name, delegate); | 444 DirectoryChangeDelegate* delegate, |
445 const browser_sync::WeakHandle<TransactionObserver>& | |
446 transaction_observer) { | |
447 const DirOpenResult result = | |
448 OpenImpl(file_path, name, delegate, transaction_observer); | |
438 if (OPENED != result) | 449 if (OPENED != result) |
439 Close(); | 450 Close(); |
440 return result; | 451 return result; |
441 } | 452 } |
442 | 453 |
443 void Directory::InitializeIndices() { | 454 void Directory::InitializeIndices() { |
444 MetahandlesIndex::iterator it = kernel_->metahandles_index->begin(); | 455 MetahandlesIndex::iterator it = kernel_->metahandles_index->begin(); |
445 for (; it != kernel_->metahandles_index->end(); ++it) { | 456 for (; it != kernel_->metahandles_index->end(); ++it) { |
446 EntryKernel* entry = *it; | 457 EntryKernel* entry = *it; |
447 InitializeIndexEntry<ParentIdAndHandleIndexer>(entry, | 458 InitializeIndexEntry<ParentIdAndHandleIndexer>(entry, |
448 kernel_->parent_id_child_index); | 459 kernel_->parent_id_child_index); |
449 InitializeIndexEntry<IdIndexer>(entry, kernel_->ids_index); | 460 InitializeIndexEntry<IdIndexer>(entry, kernel_->ids_index); |
450 InitializeIndexEntry<ClientTagIndexer>(entry, kernel_->client_tag_index); | 461 InitializeIndexEntry<ClientTagIndexer>(entry, kernel_->client_tag_index); |
451 if (entry->ref(IS_UNSYNCED)) | 462 if (entry->ref(IS_UNSYNCED)) |
452 kernel_->unsynced_metahandles->insert(entry->ref(META_HANDLE)); | 463 kernel_->unsynced_metahandles->insert(entry->ref(META_HANDLE)); |
453 if (entry->ref(IS_UNAPPLIED_UPDATE)) | 464 if (entry->ref(IS_UNAPPLIED_UPDATE)) |
454 kernel_->unapplied_update_metahandles->insert(entry->ref(META_HANDLE)); | 465 kernel_->unapplied_update_metahandles->insert(entry->ref(META_HANDLE)); |
455 DCHECK(!entry->is_dirty()); | 466 DCHECK(!entry->is_dirty()); |
456 } | 467 } |
457 } | 468 } |
458 | 469 |
459 DirectoryBackingStore* Directory::CreateBackingStore( | 470 DirectoryBackingStore* Directory::CreateBackingStore( |
460 const string& dir_name, const FilePath& backing_filepath) { | 471 const string& dir_name, const FilePath& backing_filepath) { |
461 return new DirectoryBackingStore(dir_name, backing_filepath); | 472 return new DirectoryBackingStore(dir_name, backing_filepath); |
462 } | 473 } |
463 | 474 |
464 DirOpenResult Directory::OpenImpl(const FilePath& file_path, | 475 DirOpenResult Directory::OpenImpl( |
465 const string& name, | 476 const FilePath& file_path, |
466 DirectoryChangeDelegate* delegate) { | 477 const string& name, |
478 DirectoryChangeDelegate* delegate, | |
479 const browser_sync::WeakHandle<TransactionObserver>& | |
480 transaction_observer) { | |
467 DCHECK_EQ(static_cast<DirectoryBackingStore*>(NULL), store_); | 481 DCHECK_EQ(static_cast<DirectoryBackingStore*>(NULL), store_); |
468 FilePath db_path(file_path); | 482 FilePath db_path(file_path); |
469 file_util::AbsolutePath(&db_path); | 483 file_util::AbsolutePath(&db_path); |
470 store_ = CreateBackingStore(name, db_path); | 484 store_ = CreateBackingStore(name, db_path); |
471 | 485 |
472 KernelLoadInfo info; | 486 KernelLoadInfo info; |
473 // Temporary indices before kernel_ initialized in case Load fails. We 0(1) | 487 // Temporary indices before kernel_ initialized in case Load fails. We 0(1) |
474 // swap these later. | 488 // swap these later. |
475 MetahandlesIndex metas_bucket; | 489 MetahandlesIndex metas_bucket; |
476 DirOpenResult result = store_->Load(&metas_bucket, &info); | 490 DirOpenResult result = store_->Load(&metas_bucket, &info); |
477 if (OPENED != result) | 491 if (OPENED != result) |
478 return result; | 492 return result; |
479 | 493 |
480 kernel_ = new Kernel(db_path, name, info, delegate); | 494 kernel_ = new Kernel(db_path, name, info, delegate, transaction_observer); |
481 kernel_->metahandles_index->swap(metas_bucket); | 495 kernel_->metahandles_index->swap(metas_bucket); |
482 InitializeIndices(); | 496 InitializeIndices(); |
483 return OPENED; | 497 return OPENED; |
484 } | 498 } |
485 | 499 |
486 void Directory::Close() { | 500 void Directory::Close() { |
487 if (store_) | 501 if (store_) |
488 delete store_; | 502 delete store_; |
489 store_ = NULL; | 503 store_ = NULL; |
490 if (kernel_) { | 504 if (kernel_) { |
(...skipping 611 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1102 int64 elapsed_ms = check_timer.Elapsed().InMilliseconds(); | 1116 int64 elapsed_ms = check_timer.Elapsed().InMilliseconds(); |
1103 if (elapsed_ms > max_ms) { | 1117 if (elapsed_ms > max_ms) { |
1104 VLOG(1) << "Cutting Invariant check short after " << elapsed_ms | 1118 VLOG(1) << "Cutting Invariant check short after " << elapsed_ms |
1105 << "ms. Processed " << entries_done << "/" << handles.size() | 1119 << "ms. Processed " << entries_done << "/" << handles.size() |
1106 << " entries"; | 1120 << " entries"; |
1107 return; | 1121 return; |
1108 } | 1122 } |
1109 } | 1123 } |
1110 } | 1124 } |
1111 | 1125 |
1112 void Directory::AddTransactionObserver(TransactionObserver* observer) { | |
1113 kernel_->observers->AddObserver(observer); | |
1114 } | |
1115 | |
1116 void Directory::RemoveTransactionObserver(TransactionObserver* observer) { | |
1117 kernel_->observers->RemoveObserver(observer); | |
1118 } | |
1119 | |
1120 /////////////////////////////////////////////////////////////////////////////// | 1126 /////////////////////////////////////////////////////////////////////////////// |
1121 // ScopedKernelLock | 1127 // ScopedKernelLock |
1122 | 1128 |
1123 ScopedKernelLock::ScopedKernelLock(const Directory* dir) | 1129 ScopedKernelLock::ScopedKernelLock(const Directory* dir) |
1124 : scoped_lock_(dir->kernel_->mutex), dir_(const_cast<Directory*>(dir)) { | 1130 : scoped_lock_(dir->kernel_->mutex), dir_(const_cast<Directory*>(dir)) { |
1125 } | 1131 } |
1126 | 1132 |
1127 /////////////////////////////////////////////////////////////////////////// | 1133 /////////////////////////////////////////////////////////////////////////// |
1128 // Transactions | 1134 // Transactions |
1129 | 1135 |
(...skipping 16 matching lines...) Expand all Loading... | |
1146 << name_ << " transaction completed in " << elapsed.InSecondsF() | 1152 << name_ << " transaction completed in " << elapsed.InSecondsF() |
1147 << " seconds."; | 1153 << " seconds."; |
1148 } | 1154 } |
1149 | 1155 |
1150 BaseTransaction::BaseTransaction(const tracked_objects::Location& from_here, | 1156 BaseTransaction::BaseTransaction(const tracked_objects::Location& from_here, |
1151 const char* name, | 1157 const char* name, |
1152 WriterTag writer, | 1158 WriterTag writer, |
1153 Directory* directory) | 1159 Directory* directory) |
1154 : from_here_(from_here), name_(name), writer_(writer), | 1160 : from_here_(from_here), name_(name), writer_(writer), |
1155 directory_(directory), dirkernel_(directory->kernel_) { | 1161 directory_(directory), dirkernel_(directory->kernel_) { |
1156 dirkernel_->observers->Notify( | 1162 dirkernel_->transaction_observer.Call(FROM_HERE, |
1157 &TransactionObserver::OnTransactionStart, from_here_, writer_); | 1163 &TransactionObserver::OnTransactionStart, from_here_, writer_); |
1158 } | 1164 } |
1159 | 1165 |
1160 BaseTransaction::~BaseTransaction() { | 1166 BaseTransaction::~BaseTransaction() { |
1161 dirkernel_->observers->Notify( | 1167 dirkernel_->transaction_observer.Call(FROM_HERE, |
1162 &TransactionObserver::OnTransactionEnd, from_here_, writer_); | 1168 &TransactionObserver::OnTransactionEnd, from_here_, writer_); |
1163 } | 1169 } |
1164 | 1170 |
1165 ReadTransaction::ReadTransaction(const tracked_objects::Location& location, | 1171 ReadTransaction::ReadTransaction(const tracked_objects::Location& location, |
1166 Directory* directory) | 1172 Directory* directory) |
1167 : BaseTransaction(location, "Read", INVALID, directory) { | 1173 : BaseTransaction(location, "Read", INVALID, directory) { |
1168 Lock(); | 1174 Lock(); |
1169 } | 1175 } |
1170 | 1176 |
1171 ReadTransaction::ReadTransaction(const tracked_objects::Location& location, | 1177 ReadTransaction::ReadTransaction(const tracked_objects::Location& location, |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1259 immutable_write_transaction_info, this); | 1265 immutable_write_transaction_info, this); |
1260 } else { | 1266 } else { |
1261 delegate->HandleCalculateChangesChangeEventFromSyncer( | 1267 delegate->HandleCalculateChangesChangeEventFromSyncer( |
1262 immutable_write_transaction_info, this); | 1268 immutable_write_transaction_info, this); |
1263 } | 1269 } |
1264 | 1270 |
1265 ModelTypeBitSet models_with_changes = | 1271 ModelTypeBitSet models_with_changes = |
1266 delegate->HandleTransactionEndingChangeEvent( | 1272 delegate->HandleTransactionEndingChangeEvent( |
1267 immutable_write_transaction_info, this); | 1273 immutable_write_transaction_info, this); |
1268 | 1274 |
1269 dirkernel_->observers->Notify( | 1275 dirkernel_->transaction_observer.Call(FROM_HERE, |
1270 &TransactionObserver::OnTransactionWrite, | 1276 &TransactionObserver::OnTransactionWrite, |
1271 immutable_write_transaction_info, models_with_changes); | 1277 immutable_write_transaction_info, models_with_changes); |
1272 | 1278 |
1273 return models_with_changes; | 1279 return models_with_changes; |
1274 } | 1280 } |
1275 | 1281 |
1276 void WriteTransaction::NotifyTransactionComplete( | 1282 void WriteTransaction::NotifyTransactionComplete( |
1277 ModelTypeBitSet models_with_changes) { | 1283 ModelTypeBitSet models_with_changes) { |
1278 dirkernel_->delegate->HandleTransactionCompleteChangeEvent( | 1284 dirkernel_->delegate->HandleTransactionCompleteChangeEvent( |
1279 models_with_changes); | 1285 models_with_changes); |
(...skipping 739 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2019 if (entry->ref(NEXT_ID).IsRoot() || | 2025 if (entry->ref(NEXT_ID).IsRoot() || |
2020 entry->ref(NEXT_ID) != entry->ref(PREV_ID)) { | 2026 entry->ref(NEXT_ID) != entry->ref(PREV_ID)) { |
2021 return entry; | 2027 return entry; |
2022 } | 2028 } |
2023 } | 2029 } |
2024 // There were no children in the linked list. | 2030 // There were no children in the linked list. |
2025 return NULL; | 2031 return NULL; |
2026 } | 2032 } |
2027 | 2033 |
2028 } // namespace syncable | 2034 } // namespace syncable |
OLD | NEW |