| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/prefs/pref_service.h" | 5 #include "chrome/browser/prefs/pref_service.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/command_line.h" | |
| 11 #include "base/file_path.h" | 10 #include "base/file_path.h" |
| 12 #include "base/logging.h" | 11 #include "base/logging.h" |
| 13 #include "base/message_loop.h" | 12 #include "base/message_loop.h" |
| 14 #include "base/metrics/histogram.h" | 13 #include "base/metrics/histogram.h" |
| 15 #include "base/prefs/default_pref_store.h" | 14 #include "base/prefs/default_pref_store.h" |
| 16 #include "base/prefs/overlay_user_pref_store.h" | |
| 17 #include "base/stl_util.h" | 15 #include "base/stl_util.h" |
| 18 #include "base/string_number_conversions.h" | 16 #include "base/string_number_conversions.h" |
| 19 #include "base/string_util.h" | 17 #include "base/string_util.h" |
| 20 #include "base/value_conversions.h" | 18 #include "base/value_conversions.h" |
| 21 #include "build/build_config.h" | 19 #include "build/build_config.h" |
| 22 #include "chrome/browser/browser_process.h" | |
| 23 #include "chrome/browser/prefs/command_line_pref_store.h" | |
| 24 #include "chrome/browser/prefs/pref_model_associator.h" | |
| 25 #include "chrome/browser/prefs/pref_notifier_impl.h" | 20 #include "chrome/browser/prefs/pref_notifier_impl.h" |
| 26 #include "chrome/browser/prefs/pref_service_observer.h" | |
| 27 #include "chrome/browser/prefs/pref_value_store.h" | 21 #include "chrome/browser/prefs/pref_value_store.h" |
| 28 #include "chrome/browser/ui/prefs/prefs_tab_helper.h" | |
| 29 | 22 |
| 30 using content::BrowserContext; | 23 using content::BrowserContext; |
| 31 | 24 |
| 32 namespace { | 25 namespace { |
| 33 | 26 |
| 34 // A helper function for RegisterLocalized*Pref that creates a Value* | |
| 35 // based on a localized string. Because we control the values in a | |
| 36 // locale dll, this should always return a Value of the appropriate | |
| 37 // type. | |
| 38 Value* CreateLocaleDefaultValue(base::Value::Type type, | |
| 39 const std::string& resource_string) { | |
| 40 DCHECK(!resource_string.empty()); | |
| 41 switch (type) { | |
| 42 case Value::TYPE_BOOLEAN: { | |
| 43 if ("true" == resource_string) | |
| 44 return Value::CreateBooleanValue(true); | |
| 45 if ("false" == resource_string) | |
| 46 return Value::CreateBooleanValue(false); | |
| 47 break; | |
| 48 } | |
| 49 | |
| 50 case Value::TYPE_INTEGER: { | |
| 51 int val; | |
| 52 base::StringToInt(resource_string, &val); | |
| 53 return Value::CreateIntegerValue(val); | |
| 54 } | |
| 55 | |
| 56 case Value::TYPE_DOUBLE: { | |
| 57 double val; | |
| 58 base::StringToDouble(resource_string, &val); | |
| 59 return Value::CreateDoubleValue(val); | |
| 60 } | |
| 61 | |
| 62 case Value::TYPE_STRING: { | |
| 63 return Value::CreateStringValue(resource_string); | |
| 64 } | |
| 65 | |
| 66 default: { | |
| 67 NOTREACHED() << | |
| 68 "list and dictionary types cannot have default locale values"; | |
| 69 } | |
| 70 } | |
| 71 NOTREACHED(); | |
| 72 return Value::CreateNullValue(); | |
| 73 } | |
| 74 | |
| 75 class ReadErrorHandler : public PersistentPrefStore::ReadErrorDelegate { | 27 class ReadErrorHandler : public PersistentPrefStore::ReadErrorDelegate { |
| 76 public: | 28 public: |
| 77 ReadErrorHandler(base::Callback<void(PersistentPrefStore::PrefReadError)> cb) | 29 ReadErrorHandler(base::Callback<void(PersistentPrefStore::PrefReadError)> cb) |
| 78 : callback_(cb) {} | 30 : callback_(cb) {} |
| 79 | 31 |
| 80 virtual void OnError(PersistentPrefStore::PrefReadError error) { | 32 virtual void OnError(PersistentPrefStore::PrefReadError error) { |
| 81 callback_.Run(error); | 33 callback_.Run(error); |
| 82 } | 34 } |
| 83 | 35 |
| 84 private: | 36 private: |
| 85 base::Callback<void(PersistentPrefStore::PrefReadError)> callback_; | 37 base::Callback<void(PersistentPrefStore::PrefReadError)> callback_; |
| 86 }; | 38 }; |
| 87 | 39 |
| 88 } // namespace | 40 } // namespace |
| 89 | 41 |
| 90 PrefService* PrefService::CreateIncognitoPrefService( | |
| 91 PrefStore* incognito_extension_prefs) { | |
| 92 pref_service_forked_ = true; | |
| 93 PrefNotifierImpl* pref_notifier = new PrefNotifierImpl(); | |
| 94 OverlayUserPrefStore* incognito_pref_store = | |
| 95 new OverlayUserPrefStore(user_pref_store_.get()); | |
| 96 PrefsTabHelper::InitIncognitoUserPrefStore(incognito_pref_store); | |
| 97 return new PrefService( | |
| 98 pref_notifier, | |
| 99 pref_value_store_->CloneAndSpecialize( | |
| 100 NULL, // managed | |
| 101 incognito_extension_prefs, | |
| 102 NULL, // command_line_prefs | |
| 103 incognito_pref_store, | |
| 104 NULL, // recommended | |
| 105 default_store_.get(), | |
| 106 NULL, // pref_sync_associator | |
| 107 pref_notifier), | |
| 108 incognito_pref_store, | |
| 109 default_store_.get(), | |
| 110 NULL, | |
| 111 get_localized_string_method_, | |
| 112 read_error_callback_, | |
| 113 false); | |
| 114 } | |
| 115 | |
| 116 PrefService::PrefService( | |
| 117 PrefNotifierImpl* pref_notifier, | |
| 118 PrefValueStore* pref_value_store, | |
| 119 PersistentPrefStore* user_prefs, | |
| 120 DefaultPrefStore* default_store, | |
| 121 PrefModelAssociator* pref_sync_associator, | |
| 122 base::Callback<std::string(int)> get_localized_string_method, | |
| 123 base::Callback<void(PersistentPrefStore::PrefReadError)> | |
| 124 read_error_callback, | |
| 125 bool async) | |
| 126 : pref_notifier_(pref_notifier), | |
| 127 pref_value_store_(pref_value_store), | |
| 128 user_pref_store_(user_prefs), | |
| 129 default_store_(default_store), | |
| 130 pref_sync_associator_(pref_sync_associator), | |
| 131 get_localized_string_method_(get_localized_string_method), | |
| 132 read_error_callback_(read_error_callback), | |
| 133 pref_service_forked_(false) { | |
| 134 pref_notifier_->SetPrefService(this); | |
| 135 if (pref_sync_associator_.get()) | |
| 136 pref_sync_associator_->SetPrefService(this); | |
| 137 InitFromStorage(async); | |
| 138 } | |
| 139 | |
| 140 PrefService::~PrefService() { | 42 PrefService::~PrefService() { |
| 141 DCHECK(CalledOnValidThread()); | 43 DCHECK(CalledOnValidThread()); |
| 142 | 44 |
| 143 // Reset pointers so accesses after destruction reliably crash. | 45 // Reset pointers so accesses after destruction reliably crash. |
| 144 pref_value_store_.reset(); | 46 pref_value_store_.reset(); |
| 145 user_pref_store_ = NULL; | 47 user_pref_store_ = NULL; |
| 146 default_store_ = NULL; | 48 default_store_ = NULL; |
| 147 pref_sync_associator_.reset(); | |
| 148 pref_notifier_.reset(); | 49 pref_notifier_.reset(); |
| 149 } | 50 } |
| 150 | 51 |
| 151 void PrefService::InitFromStorage(bool async) { | 52 void PrefService::InitFromStorage(bool async) { |
| 152 if (!async) { | 53 if (!async) { |
| 153 read_error_callback_.Run(user_pref_store_->ReadPrefs()); | 54 read_error_callback_.Run(user_pref_store_->ReadPrefs()); |
| 154 } else { | 55 } else { |
| 155 // Guarantee that initialization happens after this function returned. | 56 // Guarantee that initialization happens after this function returned. |
| 156 MessageLoop::current()->PostTask( | 57 MessageLoop::current()->PostTask( |
| 157 FROM_HERE, | 58 FROM_HERE, |
| 158 base::Bind(&PersistentPrefStore::ReadPrefsAsync, | 59 base::Bind(&PersistentPrefStore::ReadPrefsAsync, |
| 159 user_pref_store_.get(), | 60 user_pref_store_.get(), |
| 160 new ReadErrorHandler(read_error_callback_))); | 61 new ReadErrorHandler(read_error_callback_))); |
| 161 } | 62 } |
| 162 } | 63 } |
| 163 | 64 |
| 164 bool PrefService::ReloadPersistentPrefs() { | 65 bool PrefService::ReloadPersistentPrefs() { |
| 165 return user_pref_store_->ReadPrefs() == | 66 return user_pref_store_->ReadPrefs() == |
| 166 PersistentPrefStore::PREF_READ_ERROR_NONE; | 67 PersistentPrefStore::PREF_READ_ERROR_NONE; |
| 167 } | 68 } |
| 168 | 69 |
| 169 void PrefService::CommitPendingWrite() { | 70 void PrefService::CommitPendingWrite() { |
| 170 DCHECK(CalledOnValidThread()); | 71 DCHECK(CalledOnValidThread()); |
| 171 user_pref_store_->CommitPendingWrite(); | 72 user_pref_store_->CommitPendingWrite(); |
| 172 } | 73 } |
| 173 | 74 |
| 174 void PrefService::AddObserver(PrefServiceObserver* observer) { | |
| 175 observer_list_.AddObserver(observer); | |
| 176 } | |
| 177 | |
| 178 void PrefService::RemoveObserver(PrefServiceObserver* observer) { | |
| 179 observer_list_.RemoveObserver(observer); | |
| 180 } | |
| 181 | |
| 182 bool PrefService::IsSyncing() { | |
| 183 return pref_sync_associator_.get() && | |
| 184 pref_sync_associator_->models_associated(); | |
| 185 } | |
| 186 | |
| 187 void PrefService::OnIsSyncingChanged() { | |
| 188 FOR_EACH_OBSERVER(PrefServiceObserver, observer_list_, OnIsSyncingChanged()); | |
| 189 } | |
| 190 | |
| 191 namespace { | |
| 192 | |
| 193 // If there's no g_browser_process or no local state, return true (for testing). | |
| 194 bool IsLocalStatePrefService(PrefService* prefs) { | |
| 195 return (!g_browser_process || | |
| 196 !g_browser_process->local_state() || | |
| 197 g_browser_process->local_state() == prefs); | |
| 198 } | |
| 199 | |
| 200 // If there's no g_browser_process, return true (for testing). | |
| 201 bool IsProfilePrefService(PrefService* prefs) { | |
| 202 // TODO(zea): uncomment this once all preferences are only ever registered | |
| 203 // with either the local_state's pref service or the profile's pref service. | |
| 204 // return (!g_browser_process || g_browser_process->local_state() != prefs); | |
| 205 return true; | |
| 206 } | |
| 207 | |
| 208 } // namespace | |
| 209 | |
| 210 // Local State prefs. | |
| 211 void PrefService::RegisterBooleanPref(const char* path, | |
| 212 bool default_value) { | |
| 213 // If this fails, the pref service in use is a profile pref service, so the | |
| 214 // sync status must be provided (see profile pref registration calls below). | |
| 215 DCHECK(IsLocalStatePrefService(this)); | |
| 216 RegisterPreference(path, | |
| 217 Value::CreateBooleanValue(default_value), | |
| 218 UNSYNCABLE_PREF); | |
| 219 } | |
| 220 | |
| 221 void PrefService::RegisterIntegerPref(const char* path, int default_value) { | |
| 222 // If this fails, the pref service in use is a profile pref service, so the | |
| 223 // sync status must be provided (see profile pref registration calls below). | |
| 224 DCHECK(IsLocalStatePrefService(this)); | |
| 225 RegisterPreference(path, | |
| 226 Value::CreateIntegerValue(default_value), | |
| 227 UNSYNCABLE_PREF); | |
| 228 } | |
| 229 | |
| 230 void PrefService::RegisterDoublePref(const char* path, double default_value) { | |
| 231 // If this fails, the pref service in use is a profile pref service, so the | |
| 232 // sync status must be provided (see profile pref registration calls below). | |
| 233 DCHECK(IsLocalStatePrefService(this)); | |
| 234 RegisterPreference(path, | |
| 235 Value::CreateDoubleValue(default_value), | |
| 236 UNSYNCABLE_PREF); | |
| 237 } | |
| 238 | |
| 239 void PrefService::RegisterStringPref(const char* path, | |
| 240 const std::string& default_value) { | |
| 241 // If this fails, the pref service in use is a profile pref service, so the | |
| 242 // sync status must be provided (see profile pref registration calls below). | |
| 243 DCHECK(IsLocalStatePrefService(this)); | |
| 244 RegisterPreference(path, | |
| 245 Value::CreateStringValue(default_value), | |
| 246 UNSYNCABLE_PREF); | |
| 247 } | |
| 248 | |
| 249 void PrefService::RegisterFilePathPref(const char* path, | |
| 250 const FilePath& default_value) { | |
| 251 // If this fails, the pref service in use is a profile pref service, so the | |
| 252 // sync status must be provided (see profile pref registration calls below). | |
| 253 DCHECK(IsLocalStatePrefService(this)); | |
| 254 RegisterPreference(path, | |
| 255 Value::CreateStringValue(default_value.value()), | |
| 256 UNSYNCABLE_PREF); | |
| 257 } | |
| 258 | |
| 259 void PrefService::RegisterListPref(const char* path) { | |
| 260 // If this fails, the pref service in use is a profile pref service, so the | |
| 261 // sync status must be provided (see profile pref registration calls below). | |
| 262 DCHECK(IsLocalStatePrefService(this)); | |
| 263 RegisterPreference(path, | |
| 264 new ListValue(), | |
| 265 UNSYNCABLE_PREF); | |
| 266 } | |
| 267 | |
| 268 void PrefService::RegisterListPref(const char* path, ListValue* default_value) { | |
| 269 // If this fails, the pref service in use is a profile pref service, so the | |
| 270 // sync status must be provided (see profile pref registration calls below). | |
| 271 DCHECK(IsLocalStatePrefService(this)); | |
| 272 RegisterPreference(path, | |
| 273 default_value, | |
| 274 UNSYNCABLE_PREF); | |
| 275 } | |
| 276 | |
| 277 void PrefService::RegisterDictionaryPref(const char* path) { | |
| 278 // If this fails, the pref service in use is a profile pref service, so the | |
| 279 // sync status must be provided (see profile pref registration calls below). | |
| 280 DCHECK(IsLocalStatePrefService(this)); | |
| 281 RegisterPreference(path, | |
| 282 new DictionaryValue(), | |
| 283 UNSYNCABLE_PREF); | |
| 284 } | |
| 285 | |
| 286 void PrefService::RegisterDictionaryPref(const char* path, | |
| 287 DictionaryValue* default_value) { | |
| 288 // If this fails, the pref service in use is a profile pref service, so the | |
| 289 // sync status must be provided (see profile pref registration calls below). | |
| 290 DCHECK(IsLocalStatePrefService(this)); | |
| 291 RegisterPreference(path, | |
| 292 default_value, | |
| 293 UNSYNCABLE_PREF); | |
| 294 } | |
| 295 | |
| 296 void PrefService::RegisterLocalizedBooleanPref(const char* path, | |
| 297 int locale_default_message_id) { | |
| 298 // If this fails, the pref service in use is a profile pref service, so the | |
| 299 // sync status must be provided (see profile pref registration calls below). | |
| 300 DCHECK(IsLocalStatePrefService(this)); | |
| 301 RegisterPreference( | |
| 302 path, | |
| 303 CreateLocaleDefaultValue( | |
| 304 Value::TYPE_BOOLEAN, | |
| 305 get_localized_string_method_.Run(locale_default_message_id)), | |
| 306 UNSYNCABLE_PREF); | |
| 307 } | |
| 308 | |
| 309 void PrefService::RegisterLocalizedIntegerPref(const char* path, | |
| 310 int locale_default_message_id) { | |
| 311 // If this fails, the pref service in use is a profile pref service, so the | |
| 312 // sync status must be provided (see profile pref registration calls below). | |
| 313 DCHECK(IsLocalStatePrefService(this)); | |
| 314 RegisterPreference( | |
| 315 path, | |
| 316 CreateLocaleDefaultValue( | |
| 317 Value::TYPE_INTEGER, | |
| 318 get_localized_string_method_.Run(locale_default_message_id)), | |
| 319 UNSYNCABLE_PREF); | |
| 320 } | |
| 321 | |
| 322 void PrefService::RegisterLocalizedDoublePref(const char* path, | |
| 323 int locale_default_message_id) { | |
| 324 // If this fails, the pref service in use is a profile pref service, so the | |
| 325 // sync status must be provided (see profile pref registration calls below). | |
| 326 DCHECK(IsLocalStatePrefService(this)); | |
| 327 RegisterPreference( | |
| 328 path, | |
| 329 CreateLocaleDefaultValue( | |
| 330 Value::TYPE_DOUBLE, | |
| 331 get_localized_string_method_.Run(locale_default_message_id)), | |
| 332 UNSYNCABLE_PREF); | |
| 333 } | |
| 334 | |
| 335 void PrefService::RegisterLocalizedStringPref(const char* path, | |
| 336 int locale_default_message_id) { | |
| 337 // If this fails, the pref service in use is a profile pref service, so the | |
| 338 // sync status must be provided (see profile pref registration calls below). | |
| 339 DCHECK(IsLocalStatePrefService(this)); | |
| 340 RegisterPreference( | |
| 341 path, | |
| 342 CreateLocaleDefaultValue( | |
| 343 Value::TYPE_STRING, | |
| 344 get_localized_string_method_.Run(locale_default_message_id)), | |
| 345 UNSYNCABLE_PREF); | |
| 346 } | |
| 347 | |
| 348 void PrefService::RegisterInt64Pref(const char* path, int64 default_value) { | |
| 349 // If this fails, the pref service in use is a profile pref service, so the | |
| 350 // sync status must be provided (see profile pref registration calls below). | |
| 351 DCHECK(IsLocalStatePrefService(this)); | |
| 352 RegisterPreference( | |
| 353 path, | |
| 354 Value::CreateStringValue(base::Int64ToString(default_value)), | |
| 355 UNSYNCABLE_PREF); | |
| 356 } | |
| 357 | |
| 358 // Profile prefs (must use the sync_status variable). | |
| 359 void PrefService::RegisterBooleanPref(const char* path, | |
| 360 bool default_value, | |
| 361 PrefSyncStatus sync_status) { | |
| 362 DCHECK(IsProfilePrefService(this)); | |
| 363 RegisterPreference(path, | |
| 364 Value::CreateBooleanValue(default_value), | |
| 365 sync_status); | |
| 366 } | |
| 367 | |
| 368 void PrefService::RegisterIntegerPref(const char* path, | |
| 369 int default_value, | |
| 370 PrefSyncStatus sync_status) { | |
| 371 DCHECK(IsProfilePrefService(this)); | |
| 372 RegisterPreference(path, | |
| 373 Value::CreateIntegerValue(default_value), | |
| 374 sync_status); | |
| 375 } | |
| 376 | |
| 377 void PrefService::RegisterDoublePref(const char* path, | |
| 378 double default_value, | |
| 379 PrefSyncStatus sync_status) { | |
| 380 DCHECK(IsProfilePrefService(this)); | |
| 381 RegisterPreference(path, | |
| 382 Value::CreateDoubleValue(default_value), | |
| 383 sync_status); | |
| 384 } | |
| 385 | |
| 386 void PrefService::RegisterStringPref(const char* path, | |
| 387 const std::string& default_value, | |
| 388 PrefSyncStatus sync_status) { | |
| 389 DCHECK(IsProfilePrefService(this)); | |
| 390 RegisterPreference(path, | |
| 391 Value::CreateStringValue(default_value), | |
| 392 sync_status); | |
| 393 } | |
| 394 | |
| 395 void PrefService::RegisterFilePathPref(const char* path, | |
| 396 const FilePath& default_value, | |
| 397 PrefSyncStatus sync_status) { | |
| 398 DCHECK(IsProfilePrefService(this)); | |
| 399 RegisterPreference(path, | |
| 400 Value::CreateStringValue(default_value.value()), | |
| 401 sync_status); | |
| 402 } | |
| 403 | |
| 404 void PrefService::RegisterListPref(const char* path, | |
| 405 PrefSyncStatus sync_status) { | |
| 406 DCHECK(IsProfilePrefService(this)); | |
| 407 RegisterPreference(path, new ListValue(), sync_status); | |
| 408 } | |
| 409 | |
| 410 void PrefService::RegisterListPref(const char* path, | |
| 411 ListValue* default_value, | |
| 412 PrefSyncStatus sync_status) { | |
| 413 DCHECK(IsProfilePrefService(this)); | |
| 414 RegisterPreference(path, default_value, sync_status); | |
| 415 } | |
| 416 | |
| 417 void PrefService::RegisterDictionaryPref(const char* path, | |
| 418 PrefSyncStatus sync_status) { | |
| 419 DCHECK(IsProfilePrefService(this)); | |
| 420 RegisterPreference(path, new DictionaryValue(), sync_status); | |
| 421 } | |
| 422 | |
| 423 void PrefService::RegisterDictionaryPref(const char* path, | |
| 424 DictionaryValue* default_value, | |
| 425 PrefSyncStatus sync_status) { | |
| 426 DCHECK(IsProfilePrefService(this)); | |
| 427 RegisterPreference(path, default_value, sync_status); | |
| 428 } | |
| 429 | |
| 430 void PrefService::RegisterLocalizedBooleanPref(const char* path, | |
| 431 int locale_default_message_id, | |
| 432 PrefSyncStatus sync_status) { | |
| 433 DCHECK(IsProfilePrefService(this)); | |
| 434 RegisterPreference( | |
| 435 path, | |
| 436 CreateLocaleDefaultValue( | |
| 437 Value::TYPE_BOOLEAN, | |
| 438 get_localized_string_method_.Run(locale_default_message_id)), | |
| 439 sync_status); | |
| 440 } | |
| 441 | |
| 442 void PrefService::RegisterLocalizedIntegerPref(const char* path, | |
| 443 int locale_default_message_id, | |
| 444 PrefSyncStatus sync_status) { | |
| 445 DCHECK(IsProfilePrefService(this)); | |
| 446 RegisterPreference( | |
| 447 path, | |
| 448 CreateLocaleDefaultValue( | |
| 449 Value::TYPE_INTEGER, | |
| 450 get_localized_string_method_.Run(locale_default_message_id)), | |
| 451 sync_status); | |
| 452 } | |
| 453 | |
| 454 void PrefService::RegisterLocalizedDoublePref(const char* path, | |
| 455 int locale_default_message_id, | |
| 456 PrefSyncStatus sync_status) { | |
| 457 DCHECK(IsProfilePrefService(this)); | |
| 458 RegisterPreference( | |
| 459 path, | |
| 460 CreateLocaleDefaultValue( | |
| 461 Value::TYPE_DOUBLE, | |
| 462 get_localized_string_method_.Run(locale_default_message_id)), | |
| 463 sync_status); | |
| 464 } | |
| 465 | |
| 466 void PrefService::RegisterLocalizedStringPref(const char* path, | |
| 467 int locale_default_message_id, | |
| 468 PrefSyncStatus sync_status) { | |
| 469 DCHECK(IsProfilePrefService(this)); | |
| 470 RegisterPreference( | |
| 471 path, | |
| 472 CreateLocaleDefaultValue( | |
| 473 Value::TYPE_STRING, | |
| 474 get_localized_string_method_.Run(locale_default_message_id)), | |
| 475 sync_status); | |
| 476 } | |
| 477 | |
| 478 void PrefService::RegisterInt64Pref(const char* path, | |
| 479 int64 default_value, | |
| 480 PrefSyncStatus sync_status) { | |
| 481 DCHECK(IsProfilePrefService(this)); | |
| 482 RegisterPreference( | |
| 483 path, | |
| 484 Value::CreateStringValue(base::Int64ToString(default_value)), | |
| 485 sync_status); | |
| 486 } | |
| 487 | |
| 488 void PrefService::RegisterUint64Pref(const char* path, | |
| 489 uint64 default_value, | |
| 490 PrefSyncStatus sync_status) { | |
| 491 DCHECK(IsProfilePrefService(this)); | |
| 492 RegisterPreference( | |
| 493 path, | |
| 494 Value::CreateStringValue(base::Uint64ToString(default_value)), | |
| 495 sync_status); | |
| 496 } | |
| 497 | |
| 498 bool PrefService::GetBoolean(const char* path) const { | 75 bool PrefService::GetBoolean(const char* path) const { |
| 499 DCHECK(CalledOnValidThread()); | 76 DCHECK(CalledOnValidThread()); |
| 500 | 77 |
| 501 bool result = false; | 78 bool result = false; |
| 502 | 79 |
| 503 const base::Value* value = GetPreferenceValue(path); | 80 const base::Value* value = GetPreferenceValue(path); |
| 504 if (!value) { | 81 if (!value) { |
| 505 NOTREACHED() << "Trying to read an unregistered pref: " << path; | 82 NOTREACHED() << "Trying to read an unregistered pref: " << path; |
| 506 return result; | 83 return result; |
| 507 } | 84 } |
| (...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 699 } | 276 } |
| 700 | 277 |
| 701 void PrefService::RemovePrefObserver(const char* path, PrefObserver* obs) { | 278 void PrefService::RemovePrefObserver(const char* path, PrefObserver* obs) { |
| 702 pref_notifier_->RemovePrefObserver(path, obs); | 279 pref_notifier_->RemovePrefObserver(path, obs); |
| 703 } | 280 } |
| 704 | 281 |
| 705 void PrefService::AddPrefInitObserver(base::Callback<void(bool)> obs) { | 282 void PrefService::AddPrefInitObserver(base::Callback<void(bool)> obs) { |
| 706 pref_notifier_->AddInitObserver(obs); | 283 pref_notifier_->AddInitObserver(obs); |
| 707 } | 284 } |
| 708 | 285 |
| 286 PrefService::PrefService() {} |
| 287 |
| 288 void PrefService::Initialize( |
| 289 PrefNotifierImpl* pref_notifier, |
| 290 PrefValueStore* pref_value_store, |
| 291 PersistentPrefStore* user_prefs, |
| 292 DefaultPrefStore* default_store, |
| 293 base::Callback<void(PersistentPrefStore::PrefReadError)> |
| 294 read_error_callback, |
| 295 bool async) { |
| 296 pref_notifier_.reset(pref_notifier); |
| 297 pref_value_store_.reset(pref_value_store); |
| 298 user_pref_store_ = user_prefs; |
| 299 default_store_ = default_store; |
| 300 read_error_callback_ = read_error_callback; |
| 301 pref_notifier_->SetPrefService(this); |
| 302 InitFromStorage(async); |
| 303 } |
| 304 |
| 709 void PrefService::RegisterPreference(const char* path, | 305 void PrefService::RegisterPreference(const char* path, |
| 710 Value* default_value, | 306 Value* default_value) { |
| 711 PrefSyncStatus sync_status) { | |
| 712 DCHECK(CalledOnValidThread()); | 307 DCHECK(CalledOnValidThread()); |
| 713 | 308 |
| 714 // The main code path takes ownership, but most don't. We'll be safe. | 309 // The main code path takes ownership, but most don't. We'll be safe. |
| 715 scoped_ptr<Value> scoped_value(default_value); | 310 scoped_ptr<Value> scoped_value(default_value); |
| 716 | 311 |
| 717 CHECK(!FindPreference(path)) << "Tried to register duplicate pref " << path; | 312 CHECK(!FindPreference(path)) << "Tried to register duplicate pref " << path; |
| 718 | 313 |
| 719 base::Value::Type orig_type = default_value->GetType(); | 314 base::Value::Type orig_type = default_value->GetType(); |
| 720 DCHECK(orig_type != Value::TYPE_NULL && orig_type != Value::TYPE_BINARY) << | 315 DCHECK(orig_type != Value::TYPE_NULL && orig_type != Value::TYPE_BINARY) << |
| 721 "invalid preference type: " << orig_type; | 316 "invalid preference type: " << orig_type; |
| (...skipping 10 matching lines...) Expand all Loading... |
| 732 } else if (orig_type == base::Value::TYPE_DICTIONARY) { | 327 } else if (orig_type == base::Value::TYPE_DICTIONARY) { |
| 733 const base::DictionaryValue* dict = NULL; | 328 const base::DictionaryValue* dict = NULL; |
| 734 if (default_value->GetAsDictionary(&dict) && !dict->empty()) | 329 if (default_value->GetAsDictionary(&dict) && !dict->empty()) |
| 735 needs_empty_value = true; | 330 needs_empty_value = true; |
| 736 } | 331 } |
| 737 if (needs_empty_value) | 332 if (needs_empty_value) |
| 738 user_pref_store_->MarkNeedsEmptyValue(path); | 333 user_pref_store_->MarkNeedsEmptyValue(path); |
| 739 | 334 |
| 740 // Hand off ownership. | 335 // Hand off ownership. |
| 741 default_store_->SetDefaultValue(path, scoped_value.release()); | 336 default_store_->SetDefaultValue(path, scoped_value.release()); |
| 742 | |
| 743 // Register with sync if necessary. | |
| 744 if (sync_status == SYNCABLE_PREF && pref_sync_associator_.get()) | |
| 745 pref_sync_associator_->RegisterPref(path); | |
| 746 } | 337 } |
| 747 | 338 |
| 748 void PrefService::UnregisterPreference(const char* path) { | 339 void PrefService::UnregisterPreference(const char* path) { |
| 749 DCHECK(CalledOnValidThread()); | 340 DCHECK(CalledOnValidThread()); |
| 750 | 341 |
| 751 PreferenceMap::iterator it = prefs_map_.find(path); | 342 PreferenceMap::iterator it = prefs_map_.find(path); |
| 752 CHECK(it != prefs_map_.end()) << "Trying to unregister an unregistered pref: " | 343 CHECK(it != prefs_map_.end()) << "Trying to unregister an unregistered pref: " |
| 753 << path; | 344 << path; |
| 754 | 345 |
| 755 prefs_map_.erase(it); | 346 prefs_map_.erase(it); |
| 756 default_store_->RemoveDefaultValue(path); | 347 default_store_->RemoveDefaultValue(path); |
| 757 if (pref_sync_associator_.get() && | |
| 758 pref_sync_associator_->IsPrefRegistered(path)) { | |
| 759 pref_sync_associator_->UnregisterPref(path); | |
| 760 } | |
| 761 } | 348 } |
| 762 | 349 |
| 763 void PrefService::ClearPref(const char* path) { | 350 void PrefService::ClearPref(const char* path) { |
| 764 DCHECK(CalledOnValidThread()); | 351 DCHECK(CalledOnValidThread()); |
| 765 | 352 |
| 766 const Preference* pref = FindPreference(path); | 353 const Preference* pref = FindPreference(path); |
| 767 if (!pref) { | 354 if (!pref) { |
| 768 NOTREACHED() << "Trying to clear an unregistered pref: " << path; | 355 NOTREACHED() << "Trying to clear an unregistered pref: " << path; |
| 769 return; | 356 return; |
| 770 } | 357 } |
| (...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 885 if (pref->GetType() != new_value->GetType()) { | 472 if (pref->GetType() != new_value->GetType()) { |
| 886 NOTREACHED() << "Trying to set pref " << path | 473 NOTREACHED() << "Trying to set pref " << path |
| 887 << " of type " << pref->GetType() | 474 << " of type " << pref->GetType() |
| 888 << " to value of type " << new_value->GetType(); | 475 << " to value of type " << new_value->GetType(); |
| 889 return; | 476 return; |
| 890 } | 477 } |
| 891 | 478 |
| 892 user_pref_store_->SetValue(path, owned_value.release()); | 479 user_pref_store_->SetValue(path, owned_value.release()); |
| 893 } | 480 } |
| 894 | 481 |
| 895 syncer::SyncableService* PrefService::GetSyncableService() { | 482 void PrefService::UpdateCommandLinePrefStore(PrefStore* command_line_store) { |
| 896 return pref_sync_associator_.get(); | 483 pref_value_store_->UpdateCommandLinePrefStore(command_line_store); |
| 897 } | |
| 898 | |
| 899 void PrefService::UpdateCommandLinePrefStore(CommandLine* command_line) { | |
| 900 // If |pref_service_forked_| is true, then this PrefService and the forked | |
| 901 // copies will be out of sync. | |
| 902 DCHECK(!pref_service_forked_); | |
| 903 pref_value_store_->UpdateCommandLinePrefStore( | |
| 904 new CommandLinePrefStore(command_line)); | |
| 905 } | 484 } |
| 906 | 485 |
| 907 /////////////////////////////////////////////////////////////////////////////// | 486 /////////////////////////////////////////////////////////////////////////////// |
| 908 // PrefService::Preference | 487 // PrefService::Preference |
| 909 | 488 |
| 910 PrefService::Preference::Preference(const PrefService* service, | 489 PrefService::Preference::Preference(const PrefService* service, |
| 911 const char* name, | 490 const char* name, |
| 912 base::Value::Type type) | 491 base::Value::Type type) |
| 913 : name_(name), | 492 : name_(name), |
| 914 type_(type), | 493 type_(type), |
| (...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 990 const Value* found_value = NULL; | 569 const Value* found_value = NULL; |
| 991 if (pref_value_store_->GetValue(path, type, &found_value)) { | 570 if (pref_value_store_->GetValue(path, type, &found_value)) { |
| 992 DCHECK(found_value->IsType(type)); | 571 DCHECK(found_value->IsType(type)); |
| 993 return found_value; | 572 return found_value; |
| 994 } | 573 } |
| 995 | 574 |
| 996 // Every registered preference has at least a default value. | 575 // Every registered preference has at least a default value. |
| 997 NOTREACHED() << "no valid value found for registered pref " << path; | 576 NOTREACHED() << "no valid value found for registered pref " << path; |
| 998 return NULL; | 577 return NULL; |
| 999 } | 578 } |
| OLD | NEW |