| OLD | NEW | 
|---|
| 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 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_value_store.h" | 5 #include "chrome/browser/prefs/pref_value_store.h" | 
| 6 | 6 | 
| 7 #include "chrome/browser/browser_thread.h" | 7 #include "chrome/browser/browser_thread.h" | 
| 8 #include "chrome/browser/policy/configuration_policy_pref_store.h" | 8 #include "chrome/browser/policy/configuration_policy_pref_store.h" | 
| 9 #include "chrome/browser/prefs/command_line_pref_store.h" | 9 #include "chrome/browser/prefs/pref_notifier.h" | 
| 10 #include "chrome/browser/prefs/in_memory_pref_store.h" |  | 
| 11 #include "chrome/common/json_pref_store.h" |  | 
| 12 #include "chrome/common/notification_service.h" | 10 #include "chrome/common/notification_service.h" | 
| 13 | 11 | 
| 14 namespace { | 12 PrefValueStore::PrefStoreKeeper::PrefStoreKeeper() | 
| 15 | 13     : pref_value_store_(NULL), | 
| 16 // Returns true if the actual value is a valid type for the expected type when | 14       type_(PrefValueStore::INVALID_STORE) { | 
| 17 // found in the given store. |  | 
| 18 bool IsValidType(Value::ValueType expected, Value::ValueType actual, |  | 
| 19                  PrefNotifier::PrefStoreType store) { |  | 
| 20   if (expected == actual) |  | 
| 21     return true; |  | 
| 22 |  | 
| 23   // Dictionaries and lists are allowed to hold TYPE_NULL values too, but only |  | 
| 24   // in the default pref store. |  | 
| 25   if (store == PrefNotifier::DEFAULT_STORE && |  | 
| 26       actual == Value::TYPE_NULL && |  | 
| 27       (expected == Value::TYPE_DICTIONARY || expected == Value::TYPE_LIST)) { |  | 
| 28     return true; |  | 
| 29   } |  | 
| 30   return false; |  | 
| 31 } | 15 } | 
| 32 | 16 | 
| 33 }  // namespace | 17 PrefValueStore::PrefStoreKeeper::~PrefStoreKeeper() { | 
|  | 18   if (pref_store_.get()) | 
|  | 19     pref_store_->RemoveObserver(this); | 
|  | 20 } | 
| 34 | 21 | 
| 35 // static | 22 void PrefValueStore::PrefStoreKeeper::Initialize( | 
| 36 PrefValueStore* PrefValueStore::CreatePrefValueStore( | 23     PrefValueStore* store, | 
| 37     const FilePath& pref_filename, | 24     PrefStore* pref_store, | 
| 38     Profile* profile, | 25     PrefValueStore::PrefStoreType type) { | 
| 39     bool user_only) { | 26   if (pref_store_.get()) | 
| 40   using policy::ConfigurationPolicyPrefStore; | 27     pref_store_->RemoveObserver(this); | 
| 41   ConfigurationPolicyPrefStore* managed = NULL; | 28   type_ = type; | 
| 42   ConfigurationPolicyPrefStore* device_management = NULL; | 29   pref_value_store_ = store; | 
| 43   CommandLinePrefStore* command_line = NULL; | 30   pref_store_.reset(pref_store); | 
| 44   ConfigurationPolicyPrefStore* recommended = NULL; | 31   if (pref_store_.get()) | 
|  | 32     pref_store_->AddObserver(this); | 
|  | 33 } | 
| 45 | 34 | 
| 46   JsonPrefStore* user = new JsonPrefStore( | 35 void PrefValueStore::PrefStoreKeeper::OnPrefValueChanged( | 
| 47       pref_filename, | 36     const std::string& key) { | 
| 48       BrowserThread::GetMessageLoopProxyForThread(BrowserThread::FILE)); | 37   pref_value_store_->OnPrefValueChanged(type_, key); | 
| 49   InMemoryPrefStore* extension = new InMemoryPrefStore(); | 38 } | 
| 50   InMemoryPrefStore* default_store = new InMemoryPrefStore(); |  | 
| 51 | 39 | 
| 52   if (!user_only) { | 40 void PrefValueStore::PrefStoreKeeper::OnInitializationCompleted() { | 
| 53     managed = | 41   pref_value_store_->OnInitializationCompleted(type_); | 
| 54         ConfigurationPolicyPrefStore::CreateManagedPlatformPolicyPrefStore(); | 42 } | 
| 55     device_management = | 43 | 
| 56         ConfigurationPolicyPrefStore::CreateDeviceManagementPolicyPrefStore( | 44 PrefValueStore::PrefValueStore(PrefStore* managed_platform_prefs, | 
| 57             profile); | 45                                PrefStore* device_management_prefs, | 
| 58     command_line = new CommandLinePrefStore(CommandLine::ForCurrentProcess()); | 46                                PrefStore* extension_prefs, | 
| 59     recommended = | 47                                PrefStore* command_line_prefs, | 
| 60         ConfigurationPolicyPrefStore::CreateRecommendedPolicyPrefStore(); | 48                                PrefStore* user_prefs, | 
| 61   } | 49                                PrefStore* recommended_prefs, | 
| 62   return new PrefValueStore(managed, device_management, extension, | 50                                PrefStore* default_prefs, | 
| 63                             command_line, user, recommended, default_store, | 51                                PrefNotifier* pref_notifier, | 
| 64                             profile); | 52                                Profile* profile) | 
|  | 53     : pref_notifier_(pref_notifier), | 
|  | 54       profile_(profile) { | 
|  | 55   // NULL default pref store is usually bad, but may be OK for some unit tests. | 
|  | 56   if (!default_prefs) | 
|  | 57     LOG(WARNING) << "default pref store is null"; | 
|  | 58   InitPrefStore(MANAGED_PLATFORM_STORE, managed_platform_prefs); | 
|  | 59   InitPrefStore(DEVICE_MANAGEMENT_STORE, device_management_prefs); | 
|  | 60   InitPrefStore(EXTENSION_STORE, extension_prefs); | 
|  | 61   InitPrefStore(COMMAND_LINE_STORE, command_line_prefs); | 
|  | 62   InitPrefStore(USER_STORE, user_prefs); | 
|  | 63   InitPrefStore(RECOMMENDED_STORE, recommended_prefs); | 
|  | 64   InitPrefStore(DEFAULT_STORE, default_prefs); | 
|  | 65 | 
|  | 66   // TODO(mnissler): Remove after policy refresh cleanup. | 
|  | 67   registrar_.Add(this, | 
|  | 68                  NotificationType(NotificationType::POLICY_CHANGED), | 
|  | 69                  NotificationService::AllSources()); | 
|  | 70 | 
|  | 71   CheckInitializationCompleted(); | 
| 65 } | 72 } | 
| 66 | 73 | 
| 67 PrefValueStore::~PrefValueStore() {} | 74 PrefValueStore::~PrefValueStore() {} | 
| 68 | 75 | 
| 69 bool PrefValueStore::GetValue(const std::string& name, | 76 bool PrefValueStore::GetValue(const std::string& name, | 
| 70                               Value** out_value) const { | 77                               Value** out_value) const { | 
| 71   // Check the |PrefStore|s in order of their priority from highest to lowest | 78   // Check the |PrefStore|s in order of their priority from highest to lowest | 
| 72   // to find the value of the preference described by the given preference name. | 79   // to find the value of the preference described by the given preference name. | 
| 73   for (size_t i = 0; i <= PrefNotifier::PREF_STORE_TYPE_MAX; ++i) { | 80   for (size_t i = 0; i <= PREF_STORE_TYPE_MAX; ++i) { | 
| 74     if (GetValueFromStore(name.c_str(), | 81     if (GetValueFromStore(name.c_str(), static_cast<PrefStoreType>(i), | 
| 75                           static_cast<PrefNotifier::PrefStoreType>(i), |  | 
| 76                           out_value)) | 82                           out_value)) | 
| 77       return true; | 83       return true; | 
| 78   } | 84   } | 
| 79   return false; | 85   return false; | 
| 80 } | 86 } | 
| 81 | 87 | 
| 82 bool PrefValueStore::GetUserValue(const std::string& name, | 88 bool PrefValueStore::GetUserValue(const std::string& name, | 
| 83                                   Value** out_value) const { | 89                                   Value** out_value) const { | 
| 84   return GetValueFromStore(name.c_str(), PrefNotifier::USER_STORE, out_value); | 90   return GetValueFromStore(name.c_str(), USER_STORE, out_value); | 
| 85 } | 91 } | 
| 86 | 92 | 
| 87 void PrefValueStore::RegisterPreferenceType(const std::string& name, | 93 void PrefValueStore::RegisterPreferenceType(const std::string& name, | 
| 88                                             Value::ValueType type) { | 94                                             Value::ValueType type) { | 
| 89   pref_types_[name] = type; | 95   pref_types_[name] = type; | 
| 90 } | 96 } | 
| 91 | 97 | 
| 92 Value::ValueType PrefValueStore::GetRegisteredType( | 98 Value::ValueType PrefValueStore::GetRegisteredType( | 
| 93     const std::string& name) const { | 99     const std::string& name) const { | 
| 94   PrefTypeMap::const_iterator found = pref_types_.find(name); | 100   PrefTypeMap::const_iterator found = pref_types_.find(name); | 
| 95   if (found == pref_types_.end()) | 101   if (found == pref_types_.end()) | 
| 96     return Value::TYPE_NULL; | 102     return Value::TYPE_NULL; | 
| 97   return found->second; | 103   return found->second; | 
| 98 } | 104 } | 
| 99 | 105 | 
| 100 bool PrefValueStore::WritePrefs() { | 106 bool PrefValueStore::WritePrefs() { | 
| 101   bool success = true; | 107   bool success = true; | 
| 102   for (size_t i = 0; i <= PrefNotifier::PREF_STORE_TYPE_MAX; ++i) { | 108   for (size_t i = 0; i <= PREF_STORE_TYPE_MAX; ++i) { | 
| 103     if (pref_stores_[i].get()) | 109     PrefStore* store = GetPrefStore(static_cast<PrefStoreType>(i)); | 
| 104       success = pref_stores_[i]->WritePrefs() && success; | 110     if (store) | 
|  | 111       success = store->WritePrefs() && success; | 
| 105   } | 112   } | 
| 106   return success; | 113   return success; | 
| 107 } | 114 } | 
| 108 | 115 | 
| 109 void PrefValueStore::ScheduleWritePrefs() { | 116 void PrefValueStore::ScheduleWritePrefs() { | 
| 110   for (size_t i = 0; i <= PrefNotifier::PREF_STORE_TYPE_MAX; ++i) { | 117   for (size_t i = 0; i <= PREF_STORE_TYPE_MAX; ++i) { | 
| 111     if (pref_stores_[i].get()) | 118     PrefStore* store = GetPrefStore(static_cast<PrefStoreType>(i)); | 
| 112       pref_stores_[i]->ScheduleWritePrefs(); | 119     if (store) | 
|  | 120       store->ScheduleWritePrefs(); | 
| 113   } | 121   } | 
| 114 } | 122 } | 
| 115 | 123 | 
| 116 PrefStore::PrefReadError PrefValueStore::ReadPrefs() { | 124 PrefStore::PrefReadError PrefValueStore::ReadPrefs() { | 
| 117   PrefStore::PrefReadError result = PrefStore::PREF_READ_ERROR_NONE; | 125   PrefStore::PrefReadError result = PrefStore::PREF_READ_ERROR_NONE; | 
| 118   for (size_t i = 0; i <= PrefNotifier::PREF_STORE_TYPE_MAX; ++i) { | 126   for (size_t i = 0; i <= PREF_STORE_TYPE_MAX; ++i) { | 
| 119     if (pref_stores_[i].get()) { | 127     PrefStore* store = GetPrefStore(static_cast<PrefStoreType>(i)); | 
| 120       PrefStore::PrefReadError this_error = pref_stores_[i]->ReadPrefs(); | 128     if (store) { | 
|  | 129       PrefStore::PrefReadError this_error = store->ReadPrefs(); | 
| 121       if (result == PrefStore::PREF_READ_ERROR_NONE) | 130       if (result == PrefStore::PREF_READ_ERROR_NONE) | 
| 122         result = this_error; | 131         result = this_error; | 
| 123     } | 132     } | 
| 124   } | 133   } | 
| 125 | 134 | 
| 126   if (HasPolicyConflictingUserProxySettings()) { | 135   if (HasPolicyConflictingUserProxySettings()) { | 
| 127     LOG(WARNING) << "user-requested proxy options have been overridden" | 136     LOG(WARNING) << "user-requested proxy options have been overridden" | 
| 128                  << " by a proxy configuration specified in a centrally" | 137                  << " by a proxy configuration specified in a centrally" | 
| 129                  << " administered policy."; | 138                  << " administered policy."; | 
| 130   } | 139   } | 
| 131 | 140 | 
| 132   // TODO(markusheintz): Return a better error status: maybe a struct with | 141   // TODO(markusheintz): Return a better error status: maybe a struct with | 
| 133   // the error status of all PrefStores. | 142   // the error status of all PrefStores. | 
| 134   return result; | 143   return result; | 
| 135 } | 144 } | 
| 136 | 145 | 
| 137 bool PrefValueStore::HasPrefPath(const char* path) const { | 146 bool PrefValueStore::HasPrefPath(const char* path) const { | 
| 138   Value* tmp_value = NULL; | 147   Value* tmp_value = NULL; | 
| 139   const std::string name(path); | 148   const std::string name(path); | 
| 140   bool rv = GetValue(name, &tmp_value); | 149   bool rv = GetValue(name, &tmp_value); | 
| 141   // Merely registering a pref doesn't count as "having" it: we require a | 150   // Merely registering a pref doesn't count as "having" it: we require a | 
| 142   // non-default value set. | 151   // non-default value set. | 
| 143   return rv && !PrefValueFromDefaultStore(path); | 152   return rv && !PrefValueFromDefaultStore(path); | 
| 144 } | 153 } | 
| 145 | 154 | 
| 146 bool PrefValueStore::PrefHasChanged(const char* path, | 155 void PrefValueStore::NotifyPrefChanged( | 
| 147                                     PrefNotifier::PrefStoreType new_store) { | 156     const char* path, | 
| 148   DCHECK(new_store != PrefNotifier::INVALID_STORE); | 157     PrefValueStore::PrefStoreType new_store) { | 
| 149   // If we get a change notification about an unregistered preference, | 158   DCHECK(new_store != INVALID_STORE); | 
| 150   // discard it silently because there cannot be any listeners. |  | 
| 151   if (pref_types_.find(path) == pref_types_.end()) |  | 
| 152     return false; |  | 
| 153 | 159 | 
| 154   // Replying that the pref has changed may cause problems, but it's the safer | 160   // If this pref is not registered, just discard the notification. | 
| 155   // choice. | 161   if (!pref_types_.count(path)) | 
| 156   if (new_store == PrefNotifier::INVALID_STORE) | 162     return; | 
| 157     return true; |  | 
| 158 | 163 | 
| 159   PrefNotifier::PrefStoreType controller = ControllingPrefStoreForPref(path); | 164   bool changed = true; | 
| 160   DCHECK(controller != PrefNotifier::INVALID_STORE) | 165   // Replying that the pref has changed in case the new store is invalid may | 
| 161       << "Invalid controller for path " << path; | 166   // cause problems, but it's the safer choice. | 
| 162   if (controller == PrefNotifier::INVALID_STORE) | 167   if (new_store != INVALID_STORE) { | 
| 163     return true; | 168     PrefStoreType controller = ControllingPrefStoreForPref(path); | 
|  | 169     DCHECK(controller != INVALID_STORE); | 
|  | 170     // If the pref is controlled by a higher-priority store, its effective value | 
|  | 171     // cannot have changed. | 
|  | 172     if (controller != INVALID_STORE && | 
|  | 173         controller < new_store) { | 
|  | 174       changed = false; | 
|  | 175     } | 
|  | 176   } | 
| 164 | 177 | 
| 165   // If the pref is controlled by a higher-priority store, its effective value | 178   if (changed) | 
| 166   // cannot have changed. | 179     pref_notifier_->OnPreferenceChanged(path); | 
| 167   if (controller < new_store) |  | 
| 168     return false; |  | 
| 169 |  | 
| 170   // Otherwise, we take the pref store's word that something changed. |  | 
| 171   return true; |  | 
| 172 } | 180 } | 
| 173 | 181 | 
| 174 // Note the |DictionaryValue| referenced by the |PrefStore| USER_STORE | 182 void PrefValueStore::SetUserPrefValue(const char* name, Value* in_value) { | 
| 175 // (returned by the method prefs()) takes the ownership of the Value referenced | 183   DCHECK(in_value); | 
| 176 // by in_value. |  | 
| 177 bool PrefValueStore::SetUserPrefValue(const char* name, Value* in_value) { |  | 
| 178   Value* old_value = NULL; | 184   Value* old_value = NULL; | 
| 179   pref_stores_[PrefNotifier::USER_STORE]->prefs()->Get(name, &old_value); | 185   GetPrefStore(USER_STORE)->prefs()->Get(name, &old_value); | 
| 180   bool value_changed = !(old_value && old_value->Equals(in_value)); | 186   bool value_changed = !old_value || !old_value->Equals(in_value); | 
|  | 187   GetPrefStore(USER_STORE)->prefs()->Set(name, in_value); | 
| 181 | 188 | 
| 182   pref_stores_[PrefNotifier::USER_STORE]->prefs()->Set(name, in_value); | 189   if (value_changed) | 
| 183   return value_changed; | 190     NotifyPrefChanged(name, USER_STORE); | 
| 184 } | 191 } | 
| 185 | 192 | 
| 186 // Note the |DictionaryValue| referenced by the |PrefStore| DEFAULT_STORE | 193 void PrefValueStore::SetUserPrefValueSilently(const char* name, | 
| 187 // (returned by the method prefs()) takes the ownership of the Value referenced | 194                                               Value* in_value) { | 
| 188 // by in_value. | 195   DCHECK(in_value); | 
| 189 void PrefValueStore::SetDefaultPrefValue(const char* name, Value* in_value) { | 196   GetPrefStore(USER_STORE)->prefs()->Set(name, in_value); | 
| 190   pref_stores_[PrefNotifier::DEFAULT_STORE]->prefs()->Set(name, in_value); |  | 
| 191 } | 197 } | 
| 192 | 198 | 
| 193 bool PrefValueStore::ReadOnly() { | 199 bool PrefValueStore::ReadOnly() const { | 
| 194   return pref_stores_[PrefNotifier::USER_STORE]->ReadOnly(); | 200   return GetPrefStore(USER_STORE)->ReadOnly(); | 
| 195 } | 201 } | 
| 196 | 202 | 
| 197 bool PrefValueStore::RemoveUserPrefValue(const char* name) { | 203 void PrefValueStore::RemoveUserPrefValue(const char* name) { | 
| 198   if (pref_stores_[PrefNotifier::USER_STORE].get()) { | 204   if (GetPrefStore(USER_STORE)) { | 
| 199     return pref_stores_[PrefNotifier::USER_STORE]->prefs()->Remove(name, NULL); | 205     if (GetPrefStore(USER_STORE)->prefs()->Remove(name, NULL)) | 
|  | 206       NotifyPrefChanged(name, USER_STORE); | 
|  | 207   } | 
|  | 208 } | 
|  | 209 | 
|  | 210 bool PrefValueStore::PrefValueInManagedPlatformStore(const char* name) const { | 
|  | 211   return PrefValueInStore(name, MANAGED_PLATFORM_STORE); | 
|  | 212 } | 
|  | 213 | 
|  | 214 bool PrefValueStore::PrefValueInDeviceManagementStore(const char* name) const { | 
|  | 215   return PrefValueInStore(name, DEVICE_MANAGEMENT_STORE); | 
|  | 216 } | 
|  | 217 | 
|  | 218 bool PrefValueStore::PrefValueInExtensionStore(const char* name) const { | 
|  | 219   return PrefValueInStore(name, EXTENSION_STORE); | 
|  | 220 } | 
|  | 221 | 
|  | 222 bool PrefValueStore::PrefValueInUserStore(const char* name) const { | 
|  | 223   return PrefValueInStore(name, USER_STORE); | 
|  | 224 } | 
|  | 225 | 
|  | 226 bool PrefValueStore::PrefValueFromExtensionStore(const char* name) const { | 
|  | 227   return ControllingPrefStoreForPref(name) == EXTENSION_STORE; | 
|  | 228 } | 
|  | 229 | 
|  | 230 bool PrefValueStore::PrefValueFromUserStore(const char* name) const { | 
|  | 231   return ControllingPrefStoreForPref(name) == USER_STORE; | 
|  | 232 } | 
|  | 233 | 
|  | 234 bool PrefValueStore::PrefValueFromDefaultStore(const char* name) const { | 
|  | 235   return ControllingPrefStoreForPref(name) == DEFAULT_STORE; | 
|  | 236 } | 
|  | 237 | 
|  | 238 bool PrefValueStore::PrefValueUserModifiable(const char* name) const { | 
|  | 239   PrefStoreType effective_store = ControllingPrefStoreForPref(name); | 
|  | 240   return effective_store >= USER_STORE || | 
|  | 241          effective_store == INVALID_STORE; | 
|  | 242 } | 
|  | 243 | 
|  | 244 bool PrefValueStore::HasPolicyConflictingUserProxySettings() const { | 
|  | 245   using policy::ConfigurationPolicyPrefStore; | 
|  | 246   ConfigurationPolicyPrefStore::ProxyPreferenceSet proxy_prefs; | 
|  | 247   ConfigurationPolicyPrefStore::GetProxyPreferenceSet(&proxy_prefs); | 
|  | 248   ConfigurationPolicyPrefStore::ProxyPreferenceSet::const_iterator i; | 
|  | 249   for (i = proxy_prefs.begin(); i != proxy_prefs.end(); ++i) { | 
|  | 250     if ((PrefValueInManagedPlatformStore(*i) || | 
|  | 251          PrefValueInDeviceManagementStore(*i)) && | 
|  | 252         PrefValueInStoreRange(*i, | 
|  | 253                               COMMAND_LINE_STORE, | 
|  | 254                               USER_STORE)) | 
|  | 255       return true; | 
| 200   } | 256   } | 
| 201   return false; | 257   return false; | 
| 202 } | 258 } | 
| 203 | 259 | 
| 204 bool PrefValueStore::PrefValueInManagedPlatformStore(const char* name) const { | 260 // Returns true if the actual value is a valid type for the expected type when | 
| 205   return PrefValueInStore(name, PrefNotifier::MANAGED_PLATFORM_STORE); | 261 // found in the given store. | 
|  | 262 bool PrefValueStore::IsValidType(Value::ValueType expected, | 
|  | 263                                  Value::ValueType actual, | 
|  | 264                                  PrefValueStore::PrefStoreType store) { | 
|  | 265   if (expected == actual) | 
|  | 266     return true; | 
|  | 267 | 
|  | 268   // Dictionaries and lists are allowed to hold TYPE_NULL values too, but only | 
|  | 269   // in the default pref store. | 
|  | 270   if (store == DEFAULT_STORE && | 
|  | 271       actual == Value::TYPE_NULL && | 
|  | 272       (expected == Value::TYPE_DICTIONARY || expected == Value::TYPE_LIST)) { | 
|  | 273     return true; | 
|  | 274   } | 
|  | 275   return false; | 
| 206 } | 276 } | 
| 207 | 277 | 
| 208 bool PrefValueStore::PrefValueInDeviceManagementStore(const char* name) const { | 278 bool PrefValueStore::PrefValueInStore( | 
| 209   return PrefValueInStore(name, PrefNotifier::DEVICE_MANAGEMENT_STORE); | 279     const char* name, | 
| 210 } | 280     PrefValueStore::PrefStoreType store) const { | 
| 211 | 281   // Declare a temp Value* and call GetValueFromStore, | 
| 212 bool PrefValueStore::PrefValueInExtensionStore(const char* name) const { | 282   // ignoring the output value. | 
| 213   return PrefValueInStore(name, PrefNotifier::EXTENSION_STORE); | 283   Value* tmp_value = NULL; | 
| 214 } | 284   return GetValueFromStore(name, store, &tmp_value); | 
| 215 |  | 
| 216 bool PrefValueStore::PrefValueInUserStore(const char* name) const { |  | 
| 217   return PrefValueInStore(name, PrefNotifier::USER_STORE); |  | 
| 218 } | 285 } | 
| 219 | 286 | 
| 220 bool PrefValueStore::PrefValueInStoreRange( | 287 bool PrefValueStore::PrefValueInStoreRange( | 
| 221     const char* name, | 288     const char* name, | 
| 222     PrefNotifier::PrefStoreType first_checked_store, | 289     PrefValueStore::PrefStoreType first_checked_store, | 
| 223     PrefNotifier::PrefStoreType last_checked_store) { | 290     PrefValueStore::PrefStoreType last_checked_store) const { | 
| 224   if (first_checked_store > last_checked_store) { | 291   if (first_checked_store > last_checked_store) { | 
| 225     NOTREACHED(); | 292     NOTREACHED(); | 
| 226     return false; | 293     return false; | 
| 227   } | 294   } | 
| 228 | 295 | 
| 229   for (size_t i = first_checked_store; | 296   for (size_t i = first_checked_store; | 
| 230        i <= static_cast<size_t>(last_checked_store); ++i) { | 297        i <= static_cast<size_t>(last_checked_store); ++i) { | 
| 231     if (PrefValueInStore(name, static_cast<PrefNotifier::PrefStoreType>(i))) | 298     if (PrefValueInStore(name, static_cast<PrefStoreType>(i))) | 
| 232       return true; | 299       return true; | 
| 233   } | 300   } | 
| 234   return false; | 301   return false; | 
| 235 } | 302 } | 
| 236 | 303 | 
| 237 bool PrefValueStore::PrefValueFromExtensionStore(const char* name) const { | 304 PrefValueStore::PrefStoreType PrefValueStore::ControllingPrefStoreForPref( | 
| 238   return ControllingPrefStoreForPref(name) == PrefNotifier::EXTENSION_STORE; | 305     const char* name) const { | 
|  | 306   for (size_t i = 0; i <= PREF_STORE_TYPE_MAX; ++i) { | 
|  | 307     if (PrefValueInStore(name, static_cast<PrefStoreType>(i))) | 
|  | 308       return static_cast<PrefStoreType>(i); | 
|  | 309   } | 
|  | 310   return INVALID_STORE; | 
| 239 } | 311 } | 
| 240 | 312 | 
| 241 bool PrefValueStore::PrefValueFromUserStore(const char* name) const { | 313 bool PrefValueStore::GetValueFromStore(const char* name, | 
| 242   return ControllingPrefStoreForPref(name) == PrefNotifier::USER_STORE; | 314                                        PrefValueStore::PrefStoreType store_type, | 
| 243 } | 315                                        Value** out_value) const { | 
| 244 |  | 
| 245 bool PrefValueStore::PrefValueFromDefaultStore(const char* name) const { |  | 
| 246   return ControllingPrefStoreForPref(name) == PrefNotifier::DEFAULT_STORE; |  | 
| 247 } |  | 
| 248 |  | 
| 249 bool PrefValueStore::PrefValueUserModifiable(const char* name) const { |  | 
| 250   PrefNotifier::PrefStoreType effective_store = |  | 
| 251       ControllingPrefStoreForPref(name); |  | 
| 252   return effective_store >= PrefNotifier::USER_STORE || |  | 
| 253          effective_store == PrefNotifier::INVALID_STORE; |  | 
| 254 } |  | 
| 255 |  | 
| 256 PrefNotifier::PrefStoreType PrefValueStore::ControllingPrefStoreForPref( |  | 
| 257     const char* name) const { |  | 
| 258   for (int i = 0; i <= PrefNotifier::PREF_STORE_TYPE_MAX; ++i) { |  | 
| 259     if (PrefValueInStore(name, static_cast<PrefNotifier::PrefStoreType>(i))) |  | 
| 260       return static_cast<PrefNotifier::PrefStoreType>(i); |  | 
| 261   } |  | 
| 262   return PrefNotifier::INVALID_STORE; |  | 
| 263 } |  | 
| 264 |  | 
| 265 bool PrefValueStore::PrefValueInStore( |  | 
| 266     const char* name, |  | 
| 267     PrefNotifier::PrefStoreType store) const { |  | 
| 268   // Declare a temp Value* and call GetValueFromStore, |  | 
| 269   // ignoring the output value. |  | 
| 270   Value* tmp_value = NULL; |  | 
| 271   return GetValueFromStore(name, store, &tmp_value); |  | 
| 272 } |  | 
| 273 |  | 
| 274 bool PrefValueStore::GetValueFromStore( |  | 
| 275     const char* name, |  | 
| 276     PrefNotifier::PrefStoreType store, |  | 
| 277     Value** out_value) const { |  | 
| 278   // Only return true if we find a value and it is the correct type, so stale | 316   // Only return true if we find a value and it is the correct type, so stale | 
| 279   // values with the incorrect type will be ignored. | 317   // values with the incorrect type will be ignored. | 
| 280   if (pref_stores_[store].get() && | 318   const PrefStore* store = GetPrefStore(static_cast<PrefStoreType>(store_type)); | 
| 281       pref_stores_[store]->prefs()->Get(name, out_value)) { | 319   if (store && store->prefs()->Get(name, out_value)) { | 
| 282     // If the value is the sentinel that redirects to the default | 320     // If the value is the sentinel that redirects to the default store, | 
| 283     // store, re-fetch the value from the default store explicitly. | 321     // re-fetch the value from the default store explicitly. Because the default | 
| 284     // Because the default values are not available when creating | 322     // values are not available when creating stores, the default value must be | 
| 285     // stores, the default value must be fetched dynamically for every | 323     // fetched dynamically for every redirect. | 
| 286     // redirect. |  | 
| 287     if (PrefStore::IsUseDefaultSentinelValue(*out_value)) { | 324     if (PrefStore::IsUseDefaultSentinelValue(*out_value)) { | 
| 288       DCHECK(pref_stores_[PrefNotifier::DEFAULT_STORE].get()); | 325       store = GetPrefStore(DEFAULT_STORE); | 
| 289       if (!pref_stores_[PrefNotifier::DEFAULT_STORE]->prefs()->Get(name, | 326       if (!store || !store->prefs()->Get(name, out_value)) { | 
| 290                                                                    out_value)) { |  | 
| 291         *out_value = NULL; | 327         *out_value = NULL; | 
| 292         return false; | 328         return false; | 
| 293       } | 329       } | 
| 294       store = PrefNotifier::DEFAULT_STORE; | 330       store_type = DEFAULT_STORE; | 
| 295     } | 331     } | 
| 296     if (IsValidType(GetRegisteredType(name), (*out_value)->GetType(), store)) | 332     if (IsValidType(GetRegisteredType(name), | 
|  | 333                     (*out_value)->GetType(), | 
|  | 334                     store_type)) { | 
| 297       return true; | 335       return true; | 
|  | 336     } | 
| 298   } | 337   } | 
| 299   // No valid value found for the given preference name: set the return false. | 338   // No valid value found for the given preference name: set the return false. | 
| 300   *out_value = NULL; | 339   *out_value = NULL; | 
| 301   return false; | 340   return false; | 
| 302 } | 341 } | 
| 303 | 342 | 
| 304 void PrefValueStore::RefreshPolicyPrefsOnFileThread( | 343 void PrefValueStore::RefreshPolicyPrefsOnFileThread( | 
| 305     BrowserThread::ID calling_thread_id, | 344     BrowserThread::ID calling_thread_id, | 
| 306     PrefStore* new_managed_platform_pref_store, | 345     PrefStore* new_managed_platform_pref_store, | 
| 307     PrefStore* new_device_management_pref_store, | 346     PrefStore* new_device_management_pref_store, | 
| 308     PrefStore* new_recommended_pref_store, | 347     PrefStore* new_recommended_pref_store) { | 
| 309     AfterRefreshCallback* callback_pointer) { |  | 
| 310   scoped_ptr<AfterRefreshCallback> callback(callback_pointer); |  | 
| 311   DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE)); | 348   DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE)); | 
| 312   scoped_ptr<PrefStore> managed_platform_pref_store( | 349   scoped_ptr<PrefStore> managed_platform_pref_store( | 
| 313       new_managed_platform_pref_store); | 350       new_managed_platform_pref_store); | 
| 314   scoped_ptr<PrefStore> device_management_pref_store( | 351   scoped_ptr<PrefStore> device_management_pref_store( | 
| 315       new_device_management_pref_store); | 352       new_device_management_pref_store); | 
| 316   scoped_ptr<PrefStore> recommended_pref_store(new_recommended_pref_store); | 353   scoped_ptr<PrefStore> recommended_pref_store(new_recommended_pref_store); | 
| 317 | 354 | 
| 318   PrefStore::PrefReadError read_error = | 355   PrefStore::PrefReadError read_error = | 
| 319       new_managed_platform_pref_store->ReadPrefs(); | 356       new_managed_platform_pref_store->ReadPrefs(); | 
| 320   if (read_error != PrefStore::PREF_READ_ERROR_NONE) { | 357   if (read_error != PrefStore::PREF_READ_ERROR_NONE) { | 
| (...skipping 15 matching lines...) Expand all  Loading... | 
| 336                << read_error; | 373                << read_error; | 
| 337     return; | 374     return; | 
| 338   } | 375   } | 
| 339 | 376 | 
| 340   BrowserThread::PostTask( | 377   BrowserThread::PostTask( | 
| 341       calling_thread_id, FROM_HERE, | 378       calling_thread_id, FROM_HERE, | 
| 342       NewRunnableMethod(this, | 379       NewRunnableMethod(this, | 
| 343                         &PrefValueStore::RefreshPolicyPrefsCompletion, | 380                         &PrefValueStore::RefreshPolicyPrefsCompletion, | 
| 344                         managed_platform_pref_store.release(), | 381                         managed_platform_pref_store.release(), | 
| 345                         device_management_pref_store.release(), | 382                         device_management_pref_store.release(), | 
| 346                         recommended_pref_store.release(), | 383                         recommended_pref_store.release())); | 
| 347                         callback.release())); | 384 } | 
|  | 385 | 
|  | 386 void PrefValueStore::RefreshPolicyPrefs() { | 
|  | 387   using policy::ConfigurationPolicyPrefStore; | 
|  | 388   // Because loading of policy information must happen on the FILE | 
|  | 389   // thread, it's not possible to just replace the contents of the | 
|  | 390   // managed and recommended stores in place due to possible | 
|  | 391   // concurrent access from the UI thread. Instead, new stores are | 
|  | 392   // created and the refreshed policy read into them. The new stores | 
|  | 393   // are swapped with the old from a Task on the UI thread after the | 
|  | 394   // load is complete. | 
|  | 395   PrefStore* new_managed_platform_pref_store( | 
|  | 396       ConfigurationPolicyPrefStore::CreateManagedPlatformPolicyPrefStore()); | 
|  | 397   PrefStore* new_device_management_pref_store( | 
|  | 398       ConfigurationPolicyPrefStore::CreateDeviceManagementPolicyPrefStore( | 
|  | 399           profile_)); | 
|  | 400   PrefStore* new_recommended_pref_store( | 
|  | 401       ConfigurationPolicyPrefStore::CreateRecommendedPolicyPrefStore()); | 
|  | 402   BrowserThread::ID current_thread_id; | 
|  | 403   CHECK(BrowserThread::GetCurrentThreadIdentifier(¤t_thread_id)); | 
|  | 404   BrowserThread::PostTask( | 
|  | 405       BrowserThread::FILE, FROM_HERE, | 
|  | 406       NewRunnableMethod(this, | 
|  | 407                         &PrefValueStore::RefreshPolicyPrefsOnFileThread, | 
|  | 408                         current_thread_id, | 
|  | 409                         new_managed_platform_pref_store, | 
|  | 410                         new_device_management_pref_store, | 
|  | 411                         new_recommended_pref_store)); | 
| 348 } | 412 } | 
| 349 | 413 | 
| 350 void PrefValueStore::RefreshPolicyPrefsCompletion( | 414 void PrefValueStore::RefreshPolicyPrefsCompletion( | 
| 351     PrefStore* new_managed_platform_pref_store, | 415     PrefStore* new_managed_platform_pref_store, | 
| 352     PrefStore* new_device_management_pref_store, | 416     PrefStore* new_device_management_pref_store, | 
| 353     PrefStore* new_recommended_pref_store, | 417     PrefStore* new_recommended_pref_store) { | 
| 354     AfterRefreshCallback* callback_pointer) { |  | 
| 355   scoped_ptr<AfterRefreshCallback> callback(callback_pointer); |  | 
| 356 |  | 
| 357   // Determine the paths of all the changed preferences values in the three | 418   // Determine the paths of all the changed preferences values in the three | 
| 358   // policy-related stores (managed platform, device management and | 419   // policy-related stores (managed platform, device management and | 
| 359   // recommended). | 420   // recommended). | 
| 360   DictionaryValue* managed_platform_prefs_before( | 421   DictionaryValue* managed_platform_prefs_before( | 
| 361       pref_stores_[PrefNotifier::MANAGED_PLATFORM_STORE]->prefs()); | 422       GetPrefStore(MANAGED_PLATFORM_STORE)->prefs()); | 
| 362   DictionaryValue* managed_platform_prefs_after( | 423   DictionaryValue* managed_platform_prefs_after( | 
| 363       new_managed_platform_pref_store->prefs()); | 424       new_managed_platform_pref_store->prefs()); | 
| 364   DictionaryValue* device_management_prefs_before( | 425   DictionaryValue* device_management_prefs_before( | 
| 365       pref_stores_[PrefNotifier::DEVICE_MANAGEMENT_STORE]->prefs()); | 426       GetPrefStore(DEVICE_MANAGEMENT_STORE)->prefs()); | 
| 366   DictionaryValue* device_management_prefs_after( | 427   DictionaryValue* device_management_prefs_after( | 
| 367       new_device_management_pref_store->prefs()); | 428       new_device_management_pref_store->prefs()); | 
| 368   DictionaryValue* recommended_prefs_before( | 429   DictionaryValue* recommended_prefs_before( | 
| 369       pref_stores_[PrefNotifier::RECOMMENDED_STORE]->prefs()); | 430       GetPrefStore(RECOMMENDED_STORE)->prefs()); | 
| 370   DictionaryValue* recommended_prefs_after(new_recommended_pref_store->prefs()); | 431   DictionaryValue* recommended_prefs_after(new_recommended_pref_store->prefs()); | 
| 371 | 432 | 
| 372   std::vector<std::string> changed_managed_platform_paths; | 433   std::vector<std::string> changed_managed_platform_paths; | 
| 373   managed_platform_prefs_before->GetDifferingPaths(managed_platform_prefs_after, | 434   managed_platform_prefs_before->GetDifferingPaths(managed_platform_prefs_after, | 
| 374                                           &changed_managed_platform_paths); | 435                                           &changed_managed_platform_paths); | 
| 375 | 436 | 
| 376   std::vector<std::string> changed_device_management_paths; | 437   std::vector<std::string> changed_device_management_paths; | 
| 377   device_management_prefs_before->GetDifferingPaths( | 438   device_management_prefs_before->GetDifferingPaths( | 
| 378       device_management_prefs_after, | 439       device_management_prefs_after, | 
| 379       &changed_device_management_paths); | 440       &changed_device_management_paths); | 
| (...skipping 25 matching lines...) Expand all  Loading... | 
| 405                            changed_recommended_paths.begin(), | 466                            changed_recommended_paths.begin(), | 
| 406                            changed_recommended_paths.end(), | 467                            changed_recommended_paths.end(), | 
| 407                            changed_paths.begin()); | 468                            changed_paths.begin()); | 
| 408   changed_paths.resize(last_insert - changed_paths.begin()); | 469   changed_paths.resize(last_insert - changed_paths.begin()); | 
| 409 | 470 | 
| 410   last_insert = unique(changed_paths.begin(), changed_paths.end()); | 471   last_insert = unique(changed_paths.begin(), changed_paths.end()); | 
| 411   changed_paths.resize(last_insert - changed_paths.begin()); | 472   changed_paths.resize(last_insert - changed_paths.begin()); | 
| 412 | 473 | 
| 413   // Replace the old stores with the new and send notification of the changed | 474   // Replace the old stores with the new and send notification of the changed | 
| 414   // preferences. | 475   // preferences. | 
| 415   pref_stores_[PrefNotifier::MANAGED_PLATFORM_STORE].reset( | 476   InitPrefStore(MANAGED_PLATFORM_STORE, new_managed_platform_pref_store); | 
| 416       new_managed_platform_pref_store); | 477   InitPrefStore(DEVICE_MANAGEMENT_STORE, new_device_management_pref_store); | 
| 417   pref_stores_[PrefNotifier::DEVICE_MANAGEMENT_STORE].reset( | 478   InitPrefStore(RECOMMENDED_STORE, new_recommended_pref_store); | 
| 418       new_device_management_pref_store); | 479 | 
| 419   pref_stores_[PrefNotifier::RECOMMENDED_STORE].reset( | 480   std::vector<std::string>::const_iterator current; | 
| 420       new_recommended_pref_store); | 481   for (current = changed_paths.begin(); | 
| 421   callback->Run(changed_paths); | 482        current != changed_paths.end(); | 
|  | 483        ++current) { | 
|  | 484     pref_notifier_->OnPreferenceChanged(current->c_str()); | 
|  | 485   } | 
| 422 } | 486 } | 
| 423 | 487 | 
| 424 void PrefValueStore::RefreshPolicyPrefs( | 488 void PrefValueStore::Observe(NotificationType type, | 
| 425     AfterRefreshCallback* callback) { | 489                              const NotificationSource& source, | 
| 426   using policy::ConfigurationPolicyPrefStore; | 490                              const NotificationDetails& details) { | 
| 427   // Because loading of policy information must happen on the FILE | 491   if (type == NotificationType::POLICY_CHANGED) | 
| 428   // thread, it's not possible to just replace the contents of the | 492     RefreshPolicyPrefs(); | 
| 429   // managed and recommended stores in place due to possible |  | 
| 430   // concurrent access from the UI thread. Instead, new stores are |  | 
| 431   // created and the refreshed policy read into them. The new stores |  | 
| 432   // are swapped with the old from a Task on the UI thread after the |  | 
| 433   // load is complete. |  | 
| 434   PrefStore* new_managed_platform_pref_store( |  | 
| 435       ConfigurationPolicyPrefStore::CreateManagedPlatformPolicyPrefStore()); |  | 
| 436   PrefStore* new_device_management_pref_store( |  | 
| 437       ConfigurationPolicyPrefStore::CreateDeviceManagementPolicyPrefStore( |  | 
| 438           profile_)); |  | 
| 439   PrefStore* new_recommended_pref_store( |  | 
| 440       ConfigurationPolicyPrefStore::CreateRecommendedPolicyPrefStore()); |  | 
| 441   BrowserThread::ID current_thread_id; |  | 
| 442   CHECK(BrowserThread::GetCurrentThreadIdentifier(¤t_thread_id)); |  | 
| 443   BrowserThread::PostTask( |  | 
| 444       BrowserThread::FILE, FROM_HERE, |  | 
| 445       NewRunnableMethod(this, |  | 
| 446                         &PrefValueStore::RefreshPolicyPrefsOnFileThread, |  | 
| 447                         current_thread_id, |  | 
| 448                         new_managed_platform_pref_store, |  | 
| 449                         new_device_management_pref_store, |  | 
| 450                         new_recommended_pref_store, |  | 
| 451                         callback)); |  | 
| 452 } | 493 } | 
| 453 | 494 | 
| 454 bool PrefValueStore::HasPolicyConflictingUserProxySettings() { | 495 void PrefValueStore::OnPrefValueChanged(PrefValueStore::PrefStoreType type, | 
| 455   using policy::ConfigurationPolicyPrefStore; | 496                                         const std::string& key) { | 
| 456   ConfigurationPolicyPrefStore::ProxyPreferenceSet proxy_prefs; | 497   NotifyPrefChanged(key.c_str(), type); | 
| 457   ConfigurationPolicyPrefStore::GetProxyPreferenceSet(&proxy_prefs); |  | 
| 458   ConfigurationPolicyPrefStore::ProxyPreferenceSet::const_iterator i; |  | 
| 459   for (i = proxy_prefs.begin(); i != proxy_prefs.end(); ++i) { |  | 
| 460     if ((PrefValueInManagedPlatformStore(*i) || |  | 
| 461          PrefValueInDeviceManagementStore(*i)) && |  | 
| 462         PrefValueInStoreRange(*i, |  | 
| 463                               PrefNotifier::COMMAND_LINE_STORE, |  | 
| 464                               PrefNotifier::USER_STORE)) |  | 
| 465       return true; |  | 
| 466   } |  | 
| 467   return false; |  | 
| 468 } | 498 } | 
| 469 | 499 | 
| 470 PrefStore* PrefValueStore::GetExtensionPrefStore() const { | 500 void PrefValueStore::OnInitializationCompleted( | 
| 471   return pref_stores_[PrefNotifier::EXTENSION_STORE].get(); | 501     PrefValueStore::PrefStoreType type) { | 
|  | 502   CheckInitializationCompleted(); | 
| 472 } | 503 } | 
| 473 | 504 | 
| 474 PrefValueStore::PrefValueStore(PrefStore* managed_platform_prefs, | 505 void PrefValueStore::InitPrefStore(PrefValueStore::PrefStoreType type, | 
| 475                                PrefStore* device_management_prefs, | 506                                    PrefStore* pref_store) { | 
| 476                                PrefStore* extension_prefs, | 507   pref_stores_[type].Initialize(this, pref_store, type); | 
| 477                                PrefStore* command_line_prefs, |  | 
| 478                                PrefStore* user_prefs, |  | 
| 479                                PrefStore* recommended_prefs, |  | 
| 480                                PrefStore* default_prefs, |  | 
| 481                                Profile* profile) |  | 
| 482     : profile_(profile) { |  | 
| 483   // NULL default pref store is usually bad, but may be OK for some unit tests. |  | 
| 484   if (!default_prefs) |  | 
| 485     LOG(WARNING) << "default pref store is null"; |  | 
| 486   pref_stores_[PrefNotifier::MANAGED_PLATFORM_STORE].reset( |  | 
| 487       managed_platform_prefs); |  | 
| 488   pref_stores_[PrefNotifier::DEVICE_MANAGEMENT_STORE].reset( |  | 
| 489       device_management_prefs); |  | 
| 490   pref_stores_[PrefNotifier::EXTENSION_STORE].reset(extension_prefs); |  | 
| 491   pref_stores_[PrefNotifier::COMMAND_LINE_STORE].reset(command_line_prefs); |  | 
| 492   pref_stores_[PrefNotifier::USER_STORE].reset(user_prefs); |  | 
| 493   pref_stores_[PrefNotifier::RECOMMENDED_STORE].reset(recommended_prefs); |  | 
| 494   pref_stores_[PrefNotifier::DEFAULT_STORE].reset(default_prefs); |  | 
| 495 } | 508 } | 
|  | 509 | 
|  | 510 void PrefValueStore::CheckInitializationCompleted() { | 
|  | 511   for (size_t i = 0; i <= PREF_STORE_TYPE_MAX; ++i) { | 
|  | 512     PrefStore* store = GetPrefStore(static_cast<PrefStoreType>(i)); | 
|  | 513     if (store && !store->IsInitializationComplete()) | 
|  | 514       return; | 
|  | 515   } | 
|  | 516   pref_notifier_->OnInitializationCompleted(); | 
|  | 517 } | 
| OLD | NEW | 
|---|