Commit 936a3333 authored by Rushan Suleymanov's avatar Rushan Suleymanov Committed by Commit Bot

[Sync] Add SyncStatusObserver to sync engine.

This patch removes mutex from AllStatus class and introduces
SyncStatusObserver instead of getting of status directly from AllStatus
from different threads. AllStatus becomes single-threaded now.

Status for debugging is stored in SyncEngineImpl.

Bug: 1058773
Change-Id: Ib1d30d5ff6bc5bc5e1f24e94499de949f1e2e053
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2089695
Commit-Queue: Rushan Suleymanov <rushans@google.com>
Reviewed-by: default avatarMarc Treib <treib@chromium.org>
Reviewed-by: default avatarvitaliii <vitaliii@chromium.org>
Cr-Commit-Position: refs/heads/master@{#748611}
parent fdbddb38
...@@ -101,6 +101,8 @@ jumbo_static_library("rest_of_sync") { ...@@ -101,6 +101,8 @@ jumbo_static_library("rest_of_sync") {
"engine/sync_manager_factory.h", "engine/sync_manager_factory.h",
"engine/sync_status.cc", "engine/sync_status.cc",
"engine/sync_status.h", "engine/sync_status.h",
"engine/sync_status_observer.cc",
"engine/sync_status_observer.h",
"engine/sync_string_conversions.cc", "engine/sync_string_conversions.cc",
"engine/sync_string_conversions.h", "engine/sync_string_conversions.h",
"engine/ui_model_worker.cc", "engine/ui_model_worker.cc",
......
...@@ -225,6 +225,11 @@ void SyncEngineBackend::OnStatusCountersUpdated( ...@@ -225,6 +225,11 @@ void SyncEngineBackend::OnStatusCountersUpdated(
counters); counters);
} }
void SyncEngineBackend::OnSyncStatusChanged(const SyncStatus& status) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
host_.Call(FROM_HERE, &SyncEngineImpl::HandleSyncStatusChanged, status);
}
void SyncEngineBackend::OnActionableError(const SyncProtocolError& sync_error) { void SyncEngineBackend::OnActionableError(const SyncProtocolError& sync_error) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
host_.Call(FROM_HERE, host_.Call(FROM_HERE,
...@@ -385,6 +390,7 @@ void SyncEngineBackend::DoInitialize(SyncEngine::InitParams params) { ...@@ -385,6 +390,7 @@ void SyncEngineBackend::DoInitialize(SyncEngine::InitParams params) {
args.cache_guid = params.cache_guid; args.cache_guid = params.cache_guid;
args.birthday = params.birthday; args.birthday = params.birthday;
args.bag_of_chips = params.bag_of_chips; args.bag_of_chips = params.bag_of_chips;
args.sync_status_observers.push_back(this);
sync_manager_->Init(&args); sync_manager_->Init(&args);
base::trace_event::MemoryDumpManager::GetInstance() base::trace_event::MemoryDumpManager::GetInstance()
->RegisterDumpProviderWithSequencedTaskRunner( ->RegisterDumpProviderWithSequencedTaskRunner(
......
...@@ -27,6 +27,7 @@ ...@@ -27,6 +27,7 @@
#include "components/sync/engine/model_type_configurer.h" #include "components/sync/engine/model_type_configurer.h"
#include "components/sync/engine/shutdown_reason.h" #include "components/sync/engine/shutdown_reason.h"
#include "components/sync/engine/sync_encryption_handler.h" #include "components/sync/engine/sync_encryption_handler.h"
#include "components/sync/engine/sync_status_observer.h"
#include "components/sync/syncable/user_share.h" #include "components/sync/syncable/user_share.h"
#include "url/gurl.h" #include "url/gurl.h"
...@@ -44,7 +45,8 @@ class NigoriHandlerProxy; ...@@ -44,7 +45,8 @@ class NigoriHandlerProxy;
class SyncEngineBackend : public base::RefCountedThreadSafe<SyncEngineBackend>, class SyncEngineBackend : public base::RefCountedThreadSafe<SyncEngineBackend>,
public base::trace_event::MemoryDumpProvider, public base::trace_event::MemoryDumpProvider,
public SyncManager::Observer, public SyncManager::Observer,
public TypeDebugInfoObserver { public TypeDebugInfoObserver,
public SyncStatusObserver {
public: public:
using AllNodesCallback = using AllNodesCallback =
base::OnceCallback<void(const ModelType, base::OnceCallback<void(const ModelType,
...@@ -79,6 +81,9 @@ class SyncEngineBackend : public base::RefCountedThreadSafe<SyncEngineBackend>, ...@@ -79,6 +81,9 @@ class SyncEngineBackend : public base::RefCountedThreadSafe<SyncEngineBackend>,
void OnStatusCountersUpdated(ModelType type, void OnStatusCountersUpdated(ModelType type,
const StatusCounters& counters) override; const StatusCounters& counters) override;
// SyncStatusObserver implementation.
void OnSyncStatusChanged(const SyncStatus& status) override;
// Forwards an invalidation state change to the sync manager. // Forwards an invalidation state change to the sync manager.
void DoOnInvalidatorStateChange(InvalidatorState state); void DoOnInvalidatorStateChange(InvalidatorState state);
......
...@@ -230,8 +230,9 @@ UserShare* SyncEngineImpl::GetUserShare() const { ...@@ -230,8 +230,9 @@ UserShare* SyncEngineImpl::GetUserShare() const {
} }
SyncEngineImpl::Status SyncEngineImpl::GetDetailedStatus() { SyncEngineImpl::Status SyncEngineImpl::GetDetailedStatus() {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
DCHECK(IsInitialized()); DCHECK(IsInitialized());
return backend_->sync_manager()->GetDetailedStatus(); return cached_status_;
} }
void SyncEngineImpl::HasUnsyncedItemsForTest( void SyncEngineImpl::HasUnsyncedItemsForTest(
...@@ -435,6 +436,11 @@ void SyncEngineImpl::UpdateInvalidationVersions( ...@@ -435,6 +436,11 @@ void SyncEngineImpl::UpdateInvalidationVersions(
sync_prefs_->UpdateInvalidationVersions(invalidation_versions); sync_prefs_->UpdateInvalidationVersions(invalidation_versions);
} }
void SyncEngineImpl::HandleSyncStatusChanged(const SyncStatus& status) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
cached_status_ = status;
}
void SyncEngineImpl::OnCookieJarChanged(bool account_mismatch, void SyncEngineImpl::OnCookieJarChanged(bool account_mismatch,
bool empty_jar, bool empty_jar,
base::OnceClosure callback) { base::OnceClosure callback) {
......
...@@ -160,6 +160,9 @@ class SyncEngineImpl : public SyncEngine, public InvalidationHandler { ...@@ -160,6 +160,9 @@ class SyncEngineImpl : public SyncEngine, public InvalidationHandler {
void UpdateInvalidationVersions( void UpdateInvalidationVersions(
const std::map<ModelType, int64_t>& invalidation_versions); const std::map<ModelType, int64_t>& invalidation_versions);
// Stores the new |status| in local cache.
void HandleSyncStatusChanged(const SyncStatus& status);
private: private:
friend class SyncEngineBackend; friend class SyncEngineBackend;
...@@ -216,6 +219,8 @@ class SyncEngineImpl : public SyncEngine, public InvalidationHandler { ...@@ -216,6 +219,8 @@ class SyncEngineImpl : public SyncEngine, public InvalidationHandler {
ModelTypeSet last_enabled_types_; ModelTypeSet last_enabled_types_;
bool sessions_invalidation_enabled_ = false; bool sessions_invalidation_enabled_ = false;
SyncStatus cached_status_;
// Checks that we're on the same thread this was constructed on (UI thread). // Checks that we're on the same thread this was constructed on (UI thread).
SEQUENCE_CHECKER(sequence_checker_); SEQUENCE_CHECKER(sequence_checker_);
......
...@@ -183,11 +183,6 @@ void FakeSyncManager::RemoveObserver(Observer* observer) { ...@@ -183,11 +183,6 @@ void FakeSyncManager::RemoveObserver(Observer* observer) {
observers_.RemoveObserver(observer); observers_.RemoveObserver(observer);
} }
SyncStatus FakeSyncManager::GetDetailedStatus() const {
NOTIMPLEMENTED();
return SyncStatus();
}
void FakeSyncManager::SaveChanges() { void FakeSyncManager::SaveChanges() {
// Do nothing. // Do nothing.
} }
......
...@@ -97,7 +97,6 @@ class FakeSyncManager : public SyncManager { ...@@ -97,7 +97,6 @@ class FakeSyncManager : public SyncManager {
void SetInvalidatorEnabled(bool invalidator_enabled) override; void SetInvalidatorEnabled(bool invalidator_enabled) override;
void AddObserver(Observer* observer) override; void AddObserver(Observer* observer) override;
void RemoveObserver(Observer* observer) override; void RemoveObserver(Observer* observer) override;
SyncStatus GetDetailedStatus() const override;
void SaveChanges() override; void SaveChanges() override;
void ShutdownOnSyncThread() override; void ShutdownOnSyncThread() override;
UserShare* GetUserShare() override; UserShare* GetUserShare() override;
......
...@@ -51,6 +51,7 @@ class JsBackend; ...@@ -51,6 +51,7 @@ class JsBackend;
class JsEventHandler; class JsEventHandler;
class ProtocolEvent; class ProtocolEvent;
class SyncCycleSnapshot; class SyncCycleSnapshot;
class SyncStatusObserver;
class TypeDebugInfoObserver; class TypeDebugInfoObserver;
class UnrecoverableErrorHandler; class UnrecoverableErrorHandler;
struct UserShare; struct UserShare;
...@@ -255,6 +256,9 @@ class SyncManager { ...@@ -255,6 +256,9 @@ class SyncManager {
std::string cache_guid; std::string cache_guid;
std::string birthday; std::string birthday;
std::string bag_of_chips; std::string bag_of_chips;
// List of observers to be added to AllStatus.
std::vector<SyncStatusObserver*> sync_status_observers;
}; };
// The state of sync the feature. If the user turned on sync explicitly, it // The state of sync the feature. If the user turned on sync explicitly, it
...@@ -332,9 +336,6 @@ class SyncManager { ...@@ -332,9 +336,6 @@ class SyncManager {
// potentially dereference garbage. // potentially dereference garbage.
virtual void RemoveObserver(Observer* observer) = 0; virtual void RemoveObserver(Observer* observer) = 0;
// Status-related getter. May be called on any thread.
virtual SyncStatus GetDetailedStatus() const = 0;
// Call periodically from a database-safe thread to persist recent changes // Call periodically from a database-safe thread to persist recent changes
// to the syncapi model. // to the syncapi model.
virtual void SaveChanges() = 0; virtual void SaveChanges() = 0;
......
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "components/sync/engine/sync_status_observer.h"
namespace syncer {
SyncStatusObserver::SyncStatusObserver() = default;
SyncStatusObserver::~SyncStatusObserver() = default;
} // namespace syncer
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef COMPONENTS_SYNC_ENGINE_SYNC_STATUS_OBSERVER_H_
#define COMPONENTS_SYNC_ENGINE_SYNC_STATUS_OBSERVER_H_
#include "components/sync/engine/sync_status.h"
namespace syncer {
class SyncStatusObserver {
public:
SyncStatusObserver();
virtual ~SyncStatusObserver();
// This event is sent when SyncStatus changes.
virtual void OnSyncStatusChanged(const SyncStatus& status) = 0;
};
} // namespace syncer
#endif // COMPONENTS_SYNC_ENGINE_SYNC_STATUS_OBSERVER_H_
...@@ -5,8 +5,10 @@ ...@@ -5,8 +5,10 @@
#include "components/sync/engine_impl/all_status.h" #include "components/sync/engine_impl/all_status.h"
#include <algorithm> #include <algorithm>
#include <utility>
#include "base/logging.h" #include "base/logging.h"
#include "components/sync/engine/sync_status_observer.h"
#include "components/sync/engine_impl/net/server_connection_manager.h" #include "components/sync/engine_impl/net/server_connection_manager.h"
#include "components/sync/engine_impl/sync_cycle_event.h" #include "components/sync/engine_impl/sync_cycle_event.h"
...@@ -18,7 +20,9 @@ AllStatus::AllStatus() { ...@@ -18,7 +20,9 @@ AllStatus::AllStatus() {
status_.crypto_has_pending_keys = false; status_.crypto_has_pending_keys = false;
} }
AllStatus::~AllStatus() {} AllStatus::~AllStatus() {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
}
SyncStatus AllStatus::CreateBlankStatus() const { SyncStatus AllStatus::CreateBlankStatus() const {
// Status is initialized with the previous status value. Variables // Status is initialized with the previous status value. Variables
...@@ -69,8 +73,15 @@ SyncStatus AllStatus::CalcSyncing(const SyncCycleEvent& event) const { ...@@ -69,8 +73,15 @@ SyncStatus AllStatus::CalcSyncing(const SyncCycleEvent& event) const {
return status; return status;
} }
void AllStatus::AddObserver(SyncStatusObserver* observer) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
DCHECK(observer);
sync_status_observers_.push_back(observer);
observer->OnSyncStatusChanged(status_);
}
void AllStatus::OnSyncCycleEvent(const SyncCycleEvent& event) { void AllStatus::OnSyncCycleEvent(const SyncCycleEvent& event) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
switch (event.what_happened) { switch (event.what_happened) {
case SyncCycleEvent::SYNC_CYCLE_BEGIN: case SyncCycleEvent::SYNC_CYCLE_BEGIN:
case SyncCycleEvent::STATUS_CHANGED: case SyncCycleEvent::STATUS_CHANGED:
...@@ -81,102 +92,114 @@ void AllStatus::OnSyncCycleEvent(const SyncCycleEvent& event) { ...@@ -81,102 +92,114 @@ void AllStatus::OnSyncCycleEvent(const SyncCycleEvent& event) {
LOG(ERROR) << "Unrecognized Syncer Event: " << event.what_happened; LOG(ERROR) << "Unrecognized Syncer Event: " << event.what_happened;
break; break;
} }
NotifyStatusChanged();
} }
void AllStatus::OnActionableError( void AllStatus::OnActionableError(
const SyncProtocolError& sync_protocol_error) { const SyncProtocolError& sync_protocol_error) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_ = CreateBlankStatus(); status_ = CreateBlankStatus();
status_.sync_protocol_error = sync_protocol_error; status_.sync_protocol_error = sync_protocol_error;
NotifyStatusChanged();
} }
void AllStatus::OnRetryTimeChanged(base::Time retry_time) { void AllStatus::OnRetryTimeChanged(base::Time retry_time) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.retry_time = retry_time; status_.retry_time = retry_time;
NotifyStatusChanged();
} }
void AllStatus::OnThrottledTypesChanged(ModelTypeSet throttled_types) { void AllStatus::OnThrottledTypesChanged(ModelTypeSet throttled_types) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.throttled_types = throttled_types; status_.throttled_types = throttled_types;
NotifyStatusChanged();
} }
void AllStatus::OnBackedOffTypesChanged(ModelTypeSet backed_off_types) { void AllStatus::OnBackedOffTypesChanged(ModelTypeSet backed_off_types) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.backed_off_types = backed_off_types; status_.backed_off_types = backed_off_types;
NotifyStatusChanged();
} }
void AllStatus::OnMigrationRequested(ModelTypeSet) {} void AllStatus::OnMigrationRequested(ModelTypeSet) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
void AllStatus::OnProtocolEvent(const ProtocolEvent&) {} }
SyncStatus AllStatus::status() const { void AllStatus::OnProtocolEvent(const ProtocolEvent&) {
base::AutoLock lock(mutex_); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
return status_;
} }
void AllStatus::SetNotificationsEnabled(bool notifications_enabled) { void AllStatus::SetNotificationsEnabled(bool notifications_enabled) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.notifications_enabled = notifications_enabled; status_.notifications_enabled = notifications_enabled;
NotifyStatusChanged();
} }
void AllStatus::IncrementNotificationsReceived() { void AllStatus::IncrementNotificationsReceived() {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
++status_.notifications_received; ++status_.notifications_received;
NotifyStatusChanged();
} }
void AllStatus::SetEncryptedTypes(ModelTypeSet types) { void AllStatus::SetEncryptedTypes(ModelTypeSet types) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.encrypted_types = types; status_.encrypted_types = types;
NotifyStatusChanged();
} }
void AllStatus::SetCryptographerCanEncrypt(bool can_encrypt) { void AllStatus::SetCryptographerCanEncrypt(bool can_encrypt) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.cryptographer_can_encrypt = can_encrypt; status_.cryptographer_can_encrypt = can_encrypt;
NotifyStatusChanged();
} }
void AllStatus::SetCryptoHasPendingKeys(bool has_pending_keys) { void AllStatus::SetCryptoHasPendingKeys(bool has_pending_keys) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.crypto_has_pending_keys = has_pending_keys; status_.crypto_has_pending_keys = has_pending_keys;
NotifyStatusChanged();
} }
void AllStatus::SetPassphraseType(PassphraseType type) { void AllStatus::SetPassphraseType(PassphraseType type) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.passphrase_type = type; status_.passphrase_type = type;
NotifyStatusChanged();
} }
void AllStatus::SetHasKeystoreKey(bool has_keystore_key) { void AllStatus::SetHasKeystoreKey(bool has_keystore_key) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.has_keystore_key = has_keystore_key; status_.has_keystore_key = has_keystore_key;
NotifyStatusChanged();
} }
void AllStatus::SetKeystoreMigrationTime(const base::Time& migration_time) { void AllStatus::SetKeystoreMigrationTime(const base::Time& migration_time) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.keystore_migration_time = migration_time; status_.keystore_migration_time = migration_time;
NotifyStatusChanged();
} }
void AllStatus::SetSyncId(const std::string& sync_id) { void AllStatus::SetSyncId(const std::string& sync_id) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.sync_id = sync_id; status_.sync_id = sync_id;
NotifyStatusChanged();
} }
void AllStatus::SetInvalidatorClientId( void AllStatus::SetInvalidatorClientId(
const std::string& invalidator_client_id) { const std::string& invalidator_client_id) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.invalidator_client_id = invalidator_client_id; status_.invalidator_client_id = invalidator_client_id;
NotifyStatusChanged();
} }
void AllStatus::SetLocalBackendFolder(const std::string& folder) { void AllStatus::SetLocalBackendFolder(const std::string& folder) {
ScopedStatusLock lock(this); DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
status_.local_sync_folder = folder; status_.local_sync_folder = folder;
NotifyStatusChanged();
} }
ScopedStatusLock::ScopedStatusLock(AllStatus* allstatus) void AllStatus::NotifyStatusChanged() {
: allstatus_(allstatus) { for (SyncStatusObserver* observer : sync_status_observers_) {
allstatus->mutex_.Acquire(); observer->OnSyncStatusChanged(status_);
} }
ScopedStatusLock::~ScopedStatusLock() {
allstatus_->mutex_.Release();
} }
} // namespace syncer } // namespace syncer
...@@ -7,10 +7,11 @@ ...@@ -7,10 +7,11 @@
#include <map> #include <map>
#include <string> #include <string>
#include <vector>
#include "base/compiler_specific.h" #include "base/compiler_specific.h"
#include "base/macros.h" #include "base/macros.h"
#include "base/synchronization/lock.h" #include "base/sequence_checker.h"
#include "components/sync/base/model_type.h" #include "components/sync/base/model_type.h"
#include "components/sync/engine/sync_status.h" #include "components/sync/engine/sync_status.h"
#include "components/sync/engine_impl/nudge_source.h" #include "components/sync/engine_impl/nudge_source.h"
...@@ -19,12 +20,12 @@ ...@@ -19,12 +20,12 @@
namespace syncer { namespace syncer {
class ScopedStatusLock; class SyncStatusObserver;
struct SyncCycleEvent; struct SyncCycleEvent;
// This class watches various sync engine components, updating its internal // This class watches various sync engine components, updating its internal
// state upon change. It can return a snapshot of this state as a SyncerStatus // state upon change. It can send to observers a snapshot of this state as a
// object, aggregating all this data into one place. // SyncStatus object, aggregating all this data into one place.
// //
// Most of this data ends up on the about:sync page. But the page is only // Most of this data ends up on the about:sync page. But the page is only
// 'pinged' to update itself at the end of a sync cycle. A user could refresh // 'pinged' to update itself at the end of a sync cycle. A user could refresh
...@@ -37,6 +38,11 @@ class AllStatus : public SyncEngineEventListener { ...@@ -37,6 +38,11 @@ class AllStatus : public SyncEngineEventListener {
AllStatus(); AllStatus();
~AllStatus() override; ~AllStatus() override;
// Adds an observer which will receive a call whenever this object changes.
// The |observer| gets notification after being added right away. |observer|
// must not be null and must outlive this object.
void AddObserver(SyncStatusObserver* observer);
// SyncEngineEventListener implementation. // SyncEngineEventListener implementation.
void OnSyncCycleEvent(const SyncCycleEvent& event) override; void OnSyncCycleEvent(const SyncCycleEvent& event) override;
void OnActionableError(const SyncProtocolError& error) override; void OnActionableError(const SyncProtocolError& error) override;
...@@ -46,8 +52,6 @@ class AllStatus : public SyncEngineEventListener { ...@@ -46,8 +52,6 @@ class AllStatus : public SyncEngineEventListener {
void OnMigrationRequested(ModelTypeSet types) override; void OnMigrationRequested(ModelTypeSet types) override;
void OnProtocolEvent(const ProtocolEvent& event) override; void OnProtocolEvent(const ProtocolEvent& event) override;
SyncStatus status() const;
void SetNotificationsEnabled(bool notifications_enabled); void SetNotificationsEnabled(bool notifications_enabled);
void IncrementNotificationsReceived(); void IncrementNotificationsReceived();
...@@ -72,21 +76,17 @@ class AllStatus : public SyncEngineEventListener { ...@@ -72,21 +76,17 @@ class AllStatus : public SyncEngineEventListener {
SyncStatus status_; SyncStatus status_;
mutable base::Lock mutex_; // Protects all data members.
private: private:
friend class ScopedStatusLock; friend class ScopedStatusLock;
DISALLOW_COPY_AND_ASSIGN(AllStatus); // Notifies all observers about changing of status.
}; void NotifyStatusChanged();
class ScopedStatusLock { std::vector<SyncStatusObserver*> sync_status_observers_;
public:
explicit ScopedStatusLock(AllStatus* allstatus);
~ScopedStatusLock();
protected: SEQUENCE_CHECKER(sequence_checker_);
AllStatus* allstatus_;
DISALLOW_COPY_AND_ASSIGN(AllStatus);
}; };
} // namespace syncer } // namespace syncer
......
...@@ -340,6 +340,12 @@ void SyncManagerImpl::Init(InitArgs* args) { ...@@ -340,6 +340,12 @@ void SyncManagerImpl::Init(InitArgs* args) {
DVLOG(1) << "Setting invalidator client ID: " << args->invalidator_client_id; DVLOG(1) << "Setting invalidator client ID: " << args->invalidator_client_id;
allstatus_.SetInvalidatorClientId(args->invalidator_client_id); allstatus_.SetInvalidatorClientId(args->invalidator_client_id);
// Add observers after all initializations. Each observer will get initialized
// status while being added.
for (SyncStatusObserver* observer : args->sync_status_observers) {
allstatus_.AddObserver(observer);
}
model_type_registry_ = std::make_unique<ModelTypeRegistry>( model_type_registry_ = std::make_unique<ModelTypeRegistry>(
args->workers, share_, this, base::BindRepeating(&MigrateDirectoryData), args->workers, share_, this, base::BindRepeating(&MigrateDirectoryData),
args->cancelation_signal, args->cancelation_signal,
...@@ -918,10 +924,6 @@ void SyncManagerImpl::RefreshTypes(ModelTypeSet types) { ...@@ -918,10 +924,6 @@ void SyncManagerImpl::RefreshTypes(ModelTypeSet types) {
} }
} }
SyncStatus SyncManagerImpl::GetDetailedStatus() const {
return allstatus_.status();
}
void SyncManagerImpl::SaveChanges() { void SyncManagerImpl::SaveChanges() {
directory()->SaveChanges(); directory()->SaveChanges();
} }
......
...@@ -87,7 +87,6 @@ class SyncManagerImpl ...@@ -87,7 +87,6 @@ class SyncManagerImpl
std::unique_ptr<InvalidationInterface> invalidation) override; std::unique_ptr<InvalidationInterface> invalidation) override;
void AddObserver(SyncManager::Observer* observer) override; void AddObserver(SyncManager::Observer* observer) override;
void RemoveObserver(SyncManager::Observer* observer) override; void RemoveObserver(SyncManager::Observer* observer) override;
SyncStatus GetDetailedStatus() const override;
void SaveChanges() override; void SaveChanges() override;
void ShutdownOnSyncThread() override; void ShutdownOnSyncThread() override;
UserShare* GetUserShare() override; UserShare* GetUserShare() override;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment