1cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)// Copyright 2014 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)#include "components/sync_driver/data_type_manager_impl.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <algorithm> 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <functional> 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind_helpers.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/callback.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/compiler_specific.h" 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/debug/trace_event.h" 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/logging.h" 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/metrics/histogram.h" 17868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/stringprintf.h" 185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "components/sync_driver/data_type_controller.h" 195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "components/sync_driver/data_type_encryption_handler.h" 205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "components/sync_driver/data_type_manager_observer.h" 211320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "components/sync_driver/data_type_status_table.h" 22868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "sync/internal_api/public/data_type_debug_info_listener.h" 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)namespace sync_driver { 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 26868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)namespace { 27868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 281320f92c476a1ad9d19dba2a48c72b75566198e9Primiano TucciDataTypeStatusTable::TypeErrorMap 29868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)GenerateCryptoErrorsForTypes(syncer::ModelTypeSet encrypted_types) { 301320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DataTypeStatusTable::TypeErrorMap crypto_errors; 31868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) for (syncer::ModelTypeSet::Iterator iter = encrypted_types.First(); 32868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) iter.Good(); iter.Inc()) { 33eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch crypto_errors[iter.Get()] = syncer::SyncError( 34eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch FROM_HERE, 35eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::SyncError::CRYPTO_ERROR, 36eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch "", 37eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch iter.Get()); 38868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } 39868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) return crypto_errors; 40868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} 41868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 42868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} // namespace 43868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 44868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)DataTypeManagerImpl::AssociationTypesInfo::AssociationTypesInfo() {} 45868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)DataTypeManagerImpl::AssociationTypesInfo::~AssociationTypesInfo() {} 46868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)DataTypeManagerImpl::DataTypeManagerImpl( 48cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) const base::Closure& unrecoverable_error_method, 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const syncer::WeakHandle<syncer::DataTypeDebugInfoListener>& 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) debug_info_listener, 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const DataTypeController::TypeMap* controllers, 525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) const DataTypeEncryptionHandler* encryption_handler, 53868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer* configurer, 541320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DataTypeManagerObserver* observer) 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : configurer_(configurer), 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) controllers_(controllers), 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) state_(DataTypeManager::STOPPED), 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) needs_reconfigure_(false), 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_configure_reason_(syncer::CONFIGURE_REASON_UNKNOWN), 60868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) debug_info_listener_(debug_info_listener), 61868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) model_association_manager_(controllers, this), 622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) observer_(observer), 634e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) encryption_handler_(encryption_handler), 64cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) unrecoverable_error_method_(unrecoverable_error_method), 654e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) weak_ptr_factory_(this) { 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(configurer_); 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(observer_); 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)DataTypeManagerImpl::~DataTypeManagerImpl() {} 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 72868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)void DataTypeManagerImpl::Configure(syncer::ModelTypeSet desired_types, 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) syncer::ConfigureReason reason) { 74cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (reason == syncer::CONFIGURE_REASON_BACKUP_ROLLBACK) 75cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) desired_types.PutAll(syncer::ControlTypes()); 76cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) else 77cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) desired_types.PutAll(syncer::CoreTypes()); 785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Only allow control types and types that have controllers. 805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) syncer::ModelTypeSet filtered_desired_types; 815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) for (syncer::ModelTypeSet::Iterator type = desired_types.First(); 825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) type.Good(); type.Inc()) { 836d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) DataTypeController::TypeMap::const_iterator iter = 846d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) controllers_->find(type.Get()); 855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (syncer::IsControlType(type.Get()) || 866d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) iter != controllers_->end()) { 876d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) if (iter != controllers_->end()) { 886e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) if (!iter->second->ReadyForStart() && 891320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci !data_type_status_table_.GetUnreadyErrorTypes().Has( 906e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) type.Get())) { 916d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // Add the type to the unready types set to prevent purging it. It's 926d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // up to the datatype controller to, if necessary, explicitly 936d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // mark the type as broken to trigger a purge. 946d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) syncer::SyncError error(FROM_HERE, 956d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) syncer::SyncError::UNREADY_ERROR, 966d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) "Datatype not ready at config time.", 976d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) type.Get()); 986d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) std::map<syncer::ModelType, syncer::SyncError> errors; 996d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) errors[type.Get()] = error; 1001320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.UpdateFailedDataTypes(errors); 1016e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) } else if (iter->second->ReadyForStart()) { 1021320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.ResetUnreadyErrorFor(type.Get()); 1036d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) } 1046d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) } 1055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) filtered_desired_types.Put(type.Get()); 1065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 1075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) ConfigureImpl(filtered_desired_types, reason); 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 11103b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)void DataTypeManagerImpl::ReenableType(syncer::ModelType type) { 11203b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) // TODO(zea): move the "should we reconfigure" logic into the datatype handler 11303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) // itself. 11403b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) // Only reconfigure if the type actually had a data type or unready error. 1151320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci if (!data_type_status_table_.ResetDataTypeErrorFor(type) && 1161320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci !data_type_status_table_.ResetUnreadyErrorFor(type)) { 11703b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) return; 11803b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) } 11903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) 12003b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) // Only reconfigure if the type is actually desired. 12103b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) if (!last_requested_types_.Has(type)) 12203b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) return; 12303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) 12403b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) DVLOG(1) << "Reenabling " << syncer::ModelTypeToString(type); 12503b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) needs_reconfigure_ = true; 12603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) last_configure_reason_ = syncer::CONFIGURE_REASON_PROGRAMMATIC; 12703b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) ProcessReconfigure(); 12803b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)} 12903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) 1301320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tuccivoid DataTypeManagerImpl::ResetDataTypeErrors() { 1311320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.Reset(); 1321320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci} 1331320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::PurgeForMigration( 135868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet undesired_types, 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) syncer::ConfigureReason reason) { 137868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet remainder = Difference(last_requested_types_, 138868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) undesired_types); 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ConfigureImpl(remainder, reason); 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::ConfigureImpl( 143868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet desired_types, 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) syncer::ConfigureReason reason) { 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK_NE(reason, syncer::CONFIGURE_REASON_UNKNOWN); 146868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DVLOG(1) << "Configuring for " << syncer::ModelTypeSetToString(desired_types) 147868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) << " with reason " << reason; 1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (state_ == STOPPING) { 1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // You can not set a configuration while stopping. 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) LOG(ERROR) << "Configuration set while stopping."; 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1546d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // TODO(zea): consider not performing a full configuration once there's a 1556d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // reliable way to determine if the requested set of enabled types matches the 1566d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // current set. 1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_requested_types_ = desired_types; 159868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) last_configure_reason_ = reason; 160868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Only proceed if we're in a steady state or retrying. 161868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (state_ != STOPPED && state_ != CONFIGURED && state_ != RETRYING) { 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "Received configure request while configuration in flight. " 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) << "Postponing until current configuration complete."; 1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) needs_reconfigure_ = true; 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Restart(reason); 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)BackendDataTypeConfigurer::DataTypeConfigStateMap 172868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)DataTypeManagerImpl::BuildDataTypeConfigStateMap( 173868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) const syncer::ModelTypeSet& types_being_configured) const { 1746d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // 1. Get the failed types (due to fatal, crypto, and unready errors). 175868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // 2. Add the difference between last_requested_types_ and the failed types 176868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // as CONFIGURE_INACTIVE. 177868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // 3. Flip |types_being_configured| to CONFIGURE_ACTIVE. 178868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // 4. Set non-enabled user types as DISABLED. 1796d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // 5. Set the fatal, crypto, and unready types to their respective states. 180eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet error_types = 1811320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetFailedTypes(); 182eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet fatal_types = 1831320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetFatalErrorTypes(); 184eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet crypto_types = 1851320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetCryptoErrorTypes(); 1866d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) syncer::ModelTypeSet unready_types= 1871320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetUnreadyErrorTypes(); 188eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch 189eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch // Types with persistence errors are only purged/resynced when they're 190eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch // actively being configured. 191eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet persistence_types = 1921320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetPersistenceErrorTypes(); 193eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch persistence_types.RetainAll(types_being_configured); 194eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch 1956d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) // Types with unready errors do not count as unready if they've been disabled. 1966d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) unready_types.RetainAll(last_requested_types_); 1976d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) 198868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet enabled_types = last_requested_types_; 199eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch enabled_types.RemoveAll(error_types); 200868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet disabled_types = 201868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::Difference( 202868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::Union(syncer::UserTypes(), syncer::ControlTypes()), 203868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) enabled_types); 204868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet to_configure = syncer::Intersection( 205868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) enabled_types, types_being_configured); 206868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DVLOG(1) << "Enabling: " << syncer::ModelTypeSetToString(enabled_types); 207868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DVLOG(1) << "Configuring: " << syncer::ModelTypeSetToString(to_configure); 208868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DVLOG(1) << "Disabling: " << syncer::ModelTypeSetToString(disabled_types); 209868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 2102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) BackendDataTypeConfigurer::DataTypeConfigStateMap config_state_map; 2112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) BackendDataTypeConfigurer::SetDataTypesState( 212868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::CONFIGURE_INACTIVE, enabled_types, 213868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) &config_state_map); 214868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::SetDataTypesState( 215868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::CONFIGURE_ACTIVE, to_configure, 2162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) &config_state_map); 2172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) BackendDataTypeConfigurer::SetDataTypesState( 218eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch BackendDataTypeConfigurer::CONFIGURE_CLEAN, persistence_types, 219eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch &config_state_map); 220eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch BackendDataTypeConfigurer::SetDataTypesState( 221868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::DISABLED, disabled_types, 2222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) &config_state_map); 2232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) BackendDataTypeConfigurer::SetDataTypesState( 224868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::FATAL, fatal_types, 2252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) &config_state_map); 226868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::SetDataTypesState( 227868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BackendDataTypeConfigurer::CRYPTO, crypto_types, 2282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) &config_state_map); 2296d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) BackendDataTypeConfigurer::SetDataTypesState( 2306d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) BackendDataTypeConfigurer::UNREADY, unready_types, 2316d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles) &config_state_map); 2322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return config_state_map; 2332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 2342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::Restart(syncer::ConfigureReason reason) { 2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "Restarting..."; 237868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 238868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Check for new or resolved data type crypto errors. 239868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (encryption_handler_->IsPassphraseRequired()) { 240868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet encrypted_types = 241868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) encryption_handler_->GetEncryptedDataTypes(); 242868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) encrypted_types.RetainAll(last_requested_types_); 243868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) encrypted_types.RemoveAll( 2441320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetCryptoErrorTypes()); 2451320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DataTypeStatusTable::TypeErrorMap crypto_errors = 246868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) GenerateCryptoErrorsForTypes(encrypted_types); 2471320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.UpdateFailedDataTypes(crypto_errors); 248868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } else { 2491320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.ResetCryptoErrors(); 250868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } 251868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 252868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet failed_types = 2531320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.GetFailedTypes(); 254868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet enabled_types = 255868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::Difference(last_requested_types_, failed_types); 256868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_restart_time_ = base::Time::Now(); 2585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) configuration_stats_.clear(); 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 260868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(state_ == STOPPED || state_ == CONFIGURED || state_ == RETRYING); 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Starting from a "steady state" (stopped or configured) state 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // should send a start notification. 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (state_ == STOPPED || state_ == CONFIGURED) 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NotifyStart(); 2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2671320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci state_ = DOWNLOAD_PENDING; 268868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) download_types_queue_ = PrioritizeTypes(enabled_types); 269868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_types_queue_ = std::queue<AssociationTypesInfo>(); 270868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 2711320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci model_association_manager_.Initialize(enabled_types); 2721320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Tell the backend about the new set of data types we wish to sync. 2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The task will be invoked when updates are downloaded. 2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) configurer_->ConfigureDataTypes( 2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) reason, 277868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) BuildDataTypeConfigStateMap(download_types_queue_.front()), 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind(&DataTypeManagerImpl::DownloadReady, 279868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) weak_ptr_factory_.GetWeakPtr(), 280eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch base::Time::Now(), 281eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch download_types_queue_.front(), 282eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet()), 2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind(&DataTypeManagerImpl::OnDownloadRetry, 2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) weak_ptr_factory_.GetWeakPtr())); 2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 287eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochsyncer::ModelTypeSet DataTypeManagerImpl::GetPriorityTypes() const { 288868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet high_priority_types; 289ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch high_priority_types.PutAll(syncer::PriorityCoreTypes()); 290868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) high_priority_types.PutAll(syncer::PriorityUserTypes()); 291eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch return high_priority_types; 292eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch} 293eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch 294eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen MurdochTypeSetPriorityList DataTypeManagerImpl::PrioritizeTypes( 295eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch const syncer::ModelTypeSet& types) { 296eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet high_priority_types = GetPriorityTypes(); 297868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) high_priority_types.RetainAll(types); 298868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 299868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet low_priority_types = 300868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::Difference(types, high_priority_types); 301868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 302868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) TypeSetPriorityList result; 303868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (!high_priority_types.Empty()) 304868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) result.push(high_priority_types); 305868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (!low_priority_types.Empty()) 306868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) result.push(low_priority_types); 3075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 3085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Could be empty in case of purging for migration, sync nothing, etc. 3095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Configure empty set to purge data from backend. 3105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (result.empty()) 3115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) result.push(syncer::ModelTypeSet()); 3125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 313868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) return result; 314868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} 315868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 316868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)void DataTypeManagerImpl::ProcessReconfigure() { 317868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(needs_reconfigure_); 318868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 319868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Wait for current download and association to finish. 320868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (!(download_types_queue_.empty() && association_types_queue_.empty())) 321868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) return; 322868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // An attempt was made to reconfigure while we were already configuring. 3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // This can be because a passphrase was accepted or the user changed the 3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // set of desired types. Either way, |last_requested_types_| will contain 3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // the most recent set of desired types, so we just call configure. 3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Note: we do this whether or not GetControllersNeedingStart is true, 3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // because we may need to stop datatypes. 3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "Reconfiguring due to previous configure attempt occuring while" 3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) << " busy."; 3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 332868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Note: ConfigureImpl is called directly, rather than posted, in order to 333868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // ensure that any purging/unapplying/journaling happens while the set of 334868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // failed types is still up to date. If stack unwinding were to be done 335868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // via PostTask, the failed data types may be reset before the purging was 336868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // performed. 337868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) state_ = RETRYING; 3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) needs_reconfigure_ = false; 339868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ConfigureImpl(last_requested_types_, last_configure_reason_); 3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::OnDownloadRetry() { 343868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(state_ == DOWNLOAD_PENDING || state_ == CONFIGURING); 3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer_->OnConfigureRetry(); 3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::DownloadReady( 348868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Time download_start_time, 349eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet types_to_download, 350868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelTypeSet high_priority_types_before, 351b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) syncer::ModelTypeSet first_sync_types, 3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) syncer::ModelTypeSet failed_configuration_types) { 353868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(state_ == DOWNLOAD_PENDING || state_ == CONFIGURING); 3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 355eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch // Persistence errors are reset after each backend configuration attempt 356eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch // during which they would have been purged. 3571320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.ResetPersistenceErrorsFrom(types_to_download); 358eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch 3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Ignore |failed_configuration_types| if we need to reconfigure 3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // anyway. 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (needs_reconfigure_) { 362868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) download_types_queue_ = TypeSetPriorityList(); 3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ProcessReconfigure(); 3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!failed_configuration_types.Empty()) { 368cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (!unrecoverable_error_method_.is_null()) 369cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) unrecoverable_error_method_.Run(); 3701320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DataTypeStatusTable::TypeErrorMap errors; 3716e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) for (syncer::ModelTypeSet::Iterator iter = 3726e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) failed_configuration_types.First(); iter.Good(); iter.Inc()) { 3736e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) syncer::SyncError error( 3746e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) FROM_HERE, 3756e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) syncer::SyncError::UNRECOVERABLE_ERROR, 3766e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) "Backend failed to download type.", 3776e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) iter.Get()); 3786e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) errors[iter.Get()] = error; 3796e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) } 3801320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.UpdateFailedDataTypes(errors); 3816e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) Abort(UNRECOVERABLE_ERROR); 3825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) state_ = CONFIGURING; 386b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 387868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Pop and associate download-ready types. 388eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet ready_types = types_to_download; 38934680572440d7894ef8dafce81d8039ed80726a2Torne (Richard Coles) CHECK(!download_types_queue_.empty()); 390868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) download_types_queue_.pop(); 391eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch syncer::ModelTypeSet new_types_to_download; 392eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch if (!download_types_queue_.empty()) 393eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch new_types_to_download = download_types_queue_.front(); 394868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 395868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) AssociationTypesInfo association_info; 396868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_info.types = ready_types; 397868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_info.first_sync_types = first_sync_types; 398868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_info.download_start_time = download_start_time; 399868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_info.download_ready_time = base::Time::Now(); 400868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_info.high_priority_types_before = high_priority_types_before; 401868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_types_queue_.push(association_info); 402868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (association_types_queue_.size() == 1u) 403868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) StartNextAssociation(); 404868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 405868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Download types of low priority while configuring types of high priority. 406eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch if (!new_types_to_download.Empty()) { 407868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) configurer_->ConfigureDataTypes( 408868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) last_configure_reason_, 409eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch BuildDataTypeConfigStateMap(new_types_to_download), 410868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Bind(&DataTypeManagerImpl::DownloadReady, 411868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) weak_ptr_factory_.GetWeakPtr(), 412868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Time::Now(), 413eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch new_types_to_download, 414868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::Union(ready_types, high_priority_types_before)), 415868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Bind(&DataTypeManagerImpl::OnDownloadRetry, 416868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) weak_ptr_factory_.GetWeakPtr())); 417868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } 418868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} 419868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 420868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)void DataTypeManagerImpl::StartNextAssociation() { 421868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) CHECK(!association_types_queue_.empty()); 422868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 423868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_types_queue_.front().association_request_time = 424868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) base::Time::Now(); 425868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) model_association_manager_.StartAssociationAsync( 426868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_types_queue_.front().types); 427868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} 428868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 429f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)void DataTypeManagerImpl::OnSingleDataTypeWillStop( 4306e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) syncer::ModelType type, 4316e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) const syncer::SyncError& error) { 432f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles) configurer_->DeactivateDataType(type); 4336e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) if (error.IsSet()) { 4341320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DataTypeStatusTable::TypeErrorMap failed_types; 4356e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) failed_types[type] = error; 4361320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci data_type_status_table_.UpdateFailedDataTypes( 4376e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) failed_types); 4386e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) 4396e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) // Unrecoverable errors will shut down the entire backend, so no need to 4406e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) // reconfigure. 4416e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) if (error.error_type() != syncer::SyncError::UNRECOVERABLE_ERROR) { 4426e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) needs_reconfigure_ = true; 44303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) last_configure_reason_ = syncer::CONFIGURE_REASON_PROGRAMMATIC; 4446e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) ProcessReconfigure(); 4456e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) } 4466e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) } 447f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)} 448f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles) 449868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)void DataTypeManagerImpl::OnSingleDataTypeAssociationDone( 450868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) syncer::ModelType type, 451868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) const syncer::DataTypeAssociationStats& association_stats) { 452868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(!association_types_queue_.empty()); 453010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) DataTypeController::TypeMap::const_iterator c_it = controllers_->find(type); 454010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) DCHECK(c_it != controllers_->end()); 455010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) if (c_it->second->state() == DataTypeController::RUNNING) { 456010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) // Tell the backend about the change processor for this type so it can 457010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) // begin routing changes to it. 458010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) configurer_->ActivateDataType(type, c_it->second->model_safe_group(), 459010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) c_it->second->GetChangeProcessor()); 460010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) } 461868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 462868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (!debug_info_listener_.IsInitialized()) 463868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) return; 464868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 4655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) AssociationTypesInfo& info = association_types_queue_.front(); 46668043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) configuration_stats_.push_back(syncer::DataTypeConfigurationStats()); 46768043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) configuration_stats_.back().model_type = type; 46868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) configuration_stats_.back().association_stats = association_stats; 4695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (info.types.Has(type)) { 4705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Times in |info| only apply to non-slow types. 4715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) configuration_stats_.back().download_wait_time = 4725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) info.download_start_time - last_restart_time_; 4735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (info.first_sync_types.Has(type)) { 4745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) configuration_stats_.back().download_time = 4755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) info.download_ready_time - info.download_start_time; 4765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 4775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) configuration_stats_.back().association_wait_time_for_high_priority = 4785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) info.association_request_time - info.download_ready_time; 4795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) configuration_stats_.back().high_priority_types_configured_before = 4805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) info.high_priority_types_before; 4815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) configuration_stats_.back().same_priority_types_configured_before = 4825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) info.configured_types; 4835d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) info.configured_types.Put(type); 484868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } 4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::OnModelAssociationDone( 4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const DataTypeManager::ConfigureResult& result) { 489868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(state_ == STOPPING || state_ == CONFIGURING); 490868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 491868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (state_ == STOPPING) 4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 493868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 494868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Ignore abort/unrecoverable error if we need to reconfigure anyways. 495868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (needs_reconfigure_) { 496868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_types_queue_ = std::queue<AssociationTypesInfo>(); 497868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ProcessReconfigure(); 4985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 501868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (result.status == ABORTED || result.status == UNRECOVERABLE_ERROR) { 5026e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) Abort(result.status); 5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5066e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) DCHECK(result.status == OK); 507868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 50834680572440d7894ef8dafce81d8039ed80726a2Torne (Richard Coles) CHECK(!association_types_queue_.empty()); 509868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) association_types_queue_.pop(); 510868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (!association_types_queue_.empty()) { 511868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) StartNextAssociation(); 512868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } else if (download_types_queue_.empty()) { 513868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) state_ = CONFIGURED; 5146e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) NotifyDone(result); 515868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) } 5165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::Stop() { 5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (state_ == STOPPED) 5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 522868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) bool need_to_notify = 523868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) state_ == DOWNLOAD_PENDING || state_ == CONFIGURING; 524868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) StopImpl(); 5255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 526868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (need_to_notify) { 527868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ConfigureResult result(ABORTED, 5286e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) last_requested_types_); 529868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) NotifyDone(result); 5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5336e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)void DataTypeManagerImpl::Abort(ConfigureStatus status) { 534868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) DCHECK(state_ == DOWNLOAD_PENDING || state_ == CONFIGURING); 535868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 536868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) StopImpl(); 537868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK_NE(OK, status); 5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ConfigureResult result(status, 5406e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) last_requested_types_); 5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NotifyDone(result); 5425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 544868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)void DataTypeManagerImpl::StopImpl() { 545868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) state_ = STOPPING; 546868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 547868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Invalidate weak pointer to drop download callbacks. 548868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) weak_ptr_factory_.InvalidateWeakPtrs(); 549868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 550868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // Stop all data types. This may trigger association callback but the 551868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // callback will do nothing because state is set to STOPPING above. 552868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) model_association_manager_.Stop(); 553868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 554868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) state_ = STOPPED; 555868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} 556868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::NotifyStart() { 5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer_->OnConfigureStart(); 5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5611320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tuccivoid DataTypeManagerImpl::NotifyDone(const ConfigureResult& raw_result) { 5625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AddToConfigureTime(); 5635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5641320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci ConfigureResult result = raw_result; 5651320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci result.data_type_status_table = data_type_status_table_; 5661320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "Total time spent configuring: " 5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) << configure_time_delta_.InSecondsF() << "s"; 5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) switch (result.status) { 5705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case DataTypeManager::OK: 5715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "NotifyDone called with result: OK"; 5725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("Sync.ConfigureTime_Long.OK", 5735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) configure_time_delta_); 57468043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) if (debug_info_listener_.IsInitialized() && 57568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) !configuration_stats_.empty()) { 57668043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) debug_info_listener_.Call( 57768043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) FROM_HERE, 57868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) &syncer::DataTypeDebugInfoListener::OnDataTypeConfigureComplete, 57968043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) configuration_stats_); 58068043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) } 58168043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles) configuration_stats_.clear(); 5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case DataTypeManager::ABORTED: 5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "NotifyDone called with result: ABORTED"; 5855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("Sync.ConfigureTime_Long.ABORTED", 5865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) configure_time_delta_); 5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case DataTypeManager::UNRECOVERABLE_ERROR: 5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DVLOG(1) << "NotifyDone called with result: UNRECOVERABLE_ERROR"; 5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("Sync.ConfigureTime_Long.UNRECOVERABLE_ERROR", 5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) configure_time_delta_); 5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 5936e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles) case DataTypeManager::UNKNOWN: 5945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NOTREACHED(); 5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 5965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer_->OnConfigureDone(result); 5985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)DataTypeManager::State DataTypeManagerImpl::state() const { 6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return state_; 6025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DataTypeManagerImpl::AddToConfigureTime() { 6055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(!last_restart_time_.is_null()); 6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) configure_time_delta_ += (base::Time::Now() - last_restart_time_); 6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)} // namespace sync_driver 610