OLD | NEW |
---|---|
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/prefs/pref_service.h" | 5 #include "chrome/browser/prefs/pref_service.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 #include <string> | 8 #include <string> |
9 | 9 |
10 #include "base/command_line.h" | 10 #include "base/command_line.h" |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
70 NOTREACHED() << | 70 NOTREACHED() << |
71 "list and dictionary types cannot have default locale values"; | 71 "list and dictionary types cannot have default locale values"; |
72 } | 72 } |
73 } | 73 } |
74 NOTREACHED(); | 74 NOTREACHED(); |
75 return Value::CreateNullValue(); | 75 return Value::CreateNullValue(); |
76 } | 76 } |
77 | 77 |
78 // Forwards a notification after a PostMessage so that we can wait for the | 78 // Forwards a notification after a PostMessage so that we can wait for the |
79 // MessageLoop to run. | 79 // MessageLoop to run. |
80 void NotifyReadError(PrefService* pref, int message_id) { | 80 void NotifyReadError(int message_id) { |
81 ShowProfileErrorDialog(message_id); | 81 ShowProfileErrorDialog(message_id); |
82 } | 82 } |
83 | 83 |
84 // Shows notifications which correspond to PersistentPrefStore's reading errors. | |
85 class ReadErrorHandler : public PersistentPrefStore::ReadErrorDelegate { | |
86 public: | |
87 virtual void OnError(PersistentPrefStore::PrefReadError error) { | |
88 if (error != PersistentPrefStore::PREF_READ_ERROR_NONE) { | |
89 // Failing to load prefs on startup is a bad thing(TM). See bug 38352 for | |
90 // an example problem that this can cause. | |
91 // Do some diagnosis and try to avoid losing data. | |
92 int message_id = 0; | |
93 if (error <= PersistentPrefStore::PREF_READ_ERROR_JSON_TYPE) { | |
94 message_id = IDS_PREFERENCES_CORRUPT_ERROR; | |
95 } else if (error != PersistentPrefStore::PREF_READ_ERROR_NO_FILE) { | |
96 message_id = IDS_PREFERENCES_UNREADABLE_ERROR; | |
97 } | |
98 | |
99 if (message_id) { | |
100 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, | |
101 NewRunnableFunction(&NotifyReadError, message_id)); | |
102 } | |
103 UMA_HISTOGRAM_ENUMERATION("PrefService.ReadError", error, 20); | |
104 } | |
105 } | |
106 }; | |
107 | |
84 } // namespace | 108 } // namespace |
85 | 109 |
86 // static | 110 // static |
87 PrefService* PrefService::CreatePrefService(const FilePath& pref_filename, | 111 PrefService* PrefService::CreatePrefService(const FilePath& pref_filename, |
88 PrefStore* extension_prefs, | 112 PrefStore* extension_prefs, |
89 Profile* profile) { | 113 Profile* profile, |
90 return CreatePrefServiceAsync(pref_filename, extension_prefs, profile, NULL); | 114 bool async) { |
91 } | |
92 | |
93 // static | |
94 PrefService* PrefService::CreatePrefServiceAsync( | |
95 const FilePath& pref_filename, | |
96 PrefStore* extension_prefs, | |
97 Profile* profile, | |
98 PrefServiceDelegate* delegate) { | |
99 using policy::ConfigurationPolicyPrefStore; | 115 using policy::ConfigurationPolicyPrefStore; |
100 | 116 |
101 #if defined(OS_LINUX) | 117 #if defined(OS_LINUX) |
102 // We'd like to see what fraction of our users have the preferences | 118 // We'd like to see what fraction of our users have the preferences |
103 // stored on a network file system, as we've had no end of troubles | 119 // stored on a network file system, as we've had no end of troubles |
104 // with NFS/AFS. | 120 // with NFS/AFS. |
105 // TODO(evanm): remove this once we've collected state. | 121 // TODO(evanm): remove this once we've collected state. |
106 file_util::FileSystemType fstype; | 122 file_util::FileSystemType fstype; |
107 if (file_util::GetFileSystemType(pref_filename.DirName(), &fstype)) { | 123 if (file_util::GetFileSystemType(pref_filename.DirName(), &fstype)) { |
108 UMA_HISTOGRAM_ENUMERATION("PrefService.FileSystemType", | 124 UMA_HISTOGRAM_ENUMERATION("PrefService.FileSystemType", |
(...skipping 11 matching lines...) Expand all Loading... | |
120 JsonPrefStore* user = new JsonPrefStore( | 136 JsonPrefStore* user = new JsonPrefStore( |
121 pref_filename, | 137 pref_filename, |
122 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::FILE)); | 138 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::FILE)); |
123 ConfigurationPolicyPrefStore* recommended_platform = | 139 ConfigurationPolicyPrefStore* recommended_platform = |
124 ConfigurationPolicyPrefStore::CreateRecommendedPlatformPolicyPrefStore(); | 140 ConfigurationPolicyPrefStore::CreateRecommendedPlatformPolicyPrefStore(); |
125 ConfigurationPolicyPrefStore* recommended_cloud = | 141 ConfigurationPolicyPrefStore* recommended_cloud = |
126 ConfigurationPolicyPrefStore::CreateRecommendedCloudPolicyPrefStore( | 142 ConfigurationPolicyPrefStore::CreateRecommendedCloudPolicyPrefStore( |
127 profile); | 143 profile); |
128 DefaultPrefStore* default_pref_store = new DefaultPrefStore(); | 144 DefaultPrefStore* default_pref_store = new DefaultPrefStore(); |
129 | 145 |
130 return new PrefService(managed_platform, managed_cloud, extension_prefs, | 146 return new PrefService( |
131 command_line, user, recommended_platform, | 147 managed_platform, managed_cloud, extension_prefs, |
132 recommended_cloud, default_pref_store, delegate); | 148 command_line, user, recommended_platform, |
149 recommended_cloud, default_pref_store, async); | |
133 } | 150 } |
134 | 151 |
135 PrefService* PrefService::CreateIncognitoPrefService( | 152 PrefService* PrefService::CreateIncognitoPrefService( |
136 PrefStore* incognito_extension_prefs) { | 153 PrefStore* incognito_extension_prefs) { |
137 return new PrefService(*this, incognito_extension_prefs); | 154 return new PrefService(*this, incognito_extension_prefs); |
138 } | 155 } |
139 | 156 |
140 PrefService::PrefService(PrefStore* managed_platform_prefs, | 157 PrefService::PrefService(PrefStore* managed_platform_prefs, |
141 PrefStore* managed_cloud_prefs, | 158 PrefStore* managed_cloud_prefs, |
142 PrefStore* extension_prefs, | 159 PrefStore* extension_prefs, |
143 PrefStore* command_line_prefs, | 160 PrefStore* command_line_prefs, |
144 PersistentPrefStore* user_prefs, | 161 PersistentPrefStore* user_prefs, |
145 PrefStore* recommended_platform_prefs, | 162 PrefStore* recommended_platform_prefs, |
146 PrefStore* recommended_cloud_prefs, | 163 PrefStore* recommended_cloud_prefs, |
147 DefaultPrefStore* default_store, | 164 DefaultPrefStore* default_store, |
148 PrefServiceDelegate* delegate) | 165 bool async) |
149 : user_pref_store_(user_prefs), | 166 : user_pref_store_(user_prefs), |
150 default_store_(default_store), | 167 default_store_(default_store) { |
151 delegate_(delegate) { | |
152 pref_notifier_.reset(new PrefNotifierImpl(this)); | 168 pref_notifier_.reset(new PrefNotifierImpl(this)); |
153 pref_value_store_.reset( | 169 pref_value_store_.reset( |
154 new PrefValueStore(managed_platform_prefs, | 170 new PrefValueStore(managed_platform_prefs, |
155 managed_cloud_prefs, | 171 managed_cloud_prefs, |
156 extension_prefs, | 172 extension_prefs, |
157 command_line_prefs, | 173 command_line_prefs, |
158 user_pref_store_, | 174 user_pref_store_, |
159 recommended_platform_prefs, | 175 recommended_platform_prefs, |
160 recommended_cloud_prefs, | 176 recommended_cloud_prefs, |
161 default_store, | 177 default_store, |
162 pref_notifier_.get())); | 178 pref_notifier_.get())); |
163 InitFromStorage(); | 179 InitFromStorage(async); |
164 } | 180 } |
165 | 181 |
166 PrefService::PrefService(const PrefService& original, | 182 PrefService::PrefService(const PrefService& original, |
167 PrefStore* incognito_extension_prefs) | 183 PrefStore* incognito_extension_prefs) |
168 : user_pref_store_( | 184 : user_pref_store_( |
169 new OverlayPersistentPrefStore(original.user_pref_store_.get())), | 185 new OverlayPersistentPrefStore(original.user_pref_store_.get())), |
170 default_store_(original.default_store_.get()), | 186 default_store_(original.default_store_.get()) { |
171 delegate_(NULL) { | |
172 pref_notifier_.reset(new PrefNotifierImpl(this)); | 187 pref_notifier_.reset(new PrefNotifierImpl(this)); |
173 pref_value_store_.reset(original.pref_value_store_->CloneAndSpecialize( | 188 pref_value_store_.reset(original.pref_value_store_->CloneAndSpecialize( |
174 NULL, // managed_platform_prefs | 189 NULL, // managed_platform_prefs |
175 NULL, // managed_cloud_prefs | 190 NULL, // managed_cloud_prefs |
176 incognito_extension_prefs, | 191 incognito_extension_prefs, |
177 NULL, // command_line_prefs | 192 NULL, // command_line_prefs |
178 user_pref_store_.get(), | 193 user_pref_store_.get(), |
179 NULL, // recommended_platform_prefs | 194 NULL, // recommended_platform_prefs |
180 NULL, // recommended_cloud_prefs | 195 NULL, // recommended_cloud_prefs |
181 default_store_.get(), | 196 default_store_.get(), |
182 pref_notifier_.get())); | 197 pref_notifier_.get())); |
183 InitFromStorage(); | |
184 } | 198 } |
185 | 199 |
186 PrefService::~PrefService() { | 200 PrefService::~PrefService() { |
187 DCHECK(CalledOnValidThread()); | 201 DCHECK(CalledOnValidThread()); |
188 STLDeleteContainerPointers(prefs_.begin(), prefs_.end()); | 202 STLDeleteContainerPointers(prefs_.begin(), prefs_.end()); |
189 prefs_.clear(); | 203 prefs_.clear(); |
190 | 204 |
191 // Reset pointers so accesses after destruction reliably crash. | 205 // Reset pointers so accesses after destruction reliably crash. |
192 pref_value_store_.reset(); | 206 pref_value_store_.reset(); |
193 user_pref_store_ = NULL; | 207 user_pref_store_ = NULL; |
194 default_store_ = NULL; | 208 default_store_ = NULL; |
195 } | 209 } |
196 | 210 |
197 void PrefService::OnPrefsRead(PersistentPrefStore::PrefReadError error, | 211 void PrefService::InitFromStorage(bool async) { |
198 bool no_dir) { | 212 if (!async) { |
199 if (no_dir) { | 213 user_pref_store_->ReadPrefs(); |
Mattias Nissler (ping if slow)
2011/05/07 00:24:14
Need to call the error handler here!
altimofeev
2011/05/10 11:10:22
Good point, thanks!
Done.
| |
200 // Bad news. When profile is created, the process that creates the directory | |
201 // is explicitly started. So if directory is missing it probably means that | |
202 // Chromium hasn't sufficient privileges. | |
203 CHECK(delegate_); | |
204 delegate_->OnPrefsLoaded(this, false); | |
205 return; | |
206 } | |
207 | |
208 if (error != PersistentPrefStore::PREF_READ_ERROR_NONE) { | |
209 // Failing to load prefs on startup is a bad thing(TM). See bug 38352 for | |
210 // an example problem that this can cause. | |
211 // Do some diagnosis and try to avoid losing data. | |
212 int message_id = 0; | |
213 if (error <= PersistentPrefStore::PREF_READ_ERROR_JSON_TYPE) { | |
214 message_id = IDS_PREFERENCES_CORRUPT_ERROR; | |
215 } else if (error != PersistentPrefStore::PREF_READ_ERROR_NO_FILE) { | |
216 message_id = IDS_PREFERENCES_UNREADABLE_ERROR; | |
217 } | |
218 | |
219 if (message_id) { | |
220 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, | |
221 NewRunnableFunction(&NotifyReadError, this, message_id)); | |
222 } | |
223 UMA_HISTOGRAM_ENUMERATION("PrefService.ReadError", error, 20); | |
224 } | |
225 | |
226 if (delegate_) | |
227 delegate_->OnPrefsLoaded(this, true); | |
228 } | |
229 | |
230 void PrefService::InitFromStorage() { | |
231 if (!delegate_) { | |
232 const PersistentPrefStore::PrefReadError error = | |
233 user_pref_store_->ReadPrefs(); | |
234 OnPrefsRead(error, false); | |
235 } else { | 214 } else { |
236 // todo(altimofeev): move this method to PersistentPrefStore interface. | 215 // Guarantee that initialization happens after this function returned. |
237 (static_cast<JsonPrefStore*>(user_pref_store_.get()))->ReadPrefs(this); | 216 MessageLoop::current()->PostTask( |
217 FROM_HERE, | |
218 NewRunnableMethod(user_pref_store_.get(), | |
219 &PersistentPrefStore::ReadPrefsAsync, | |
220 new ReadErrorHandler())); | |
238 } | 221 } |
239 } | 222 } |
240 | 223 |
241 bool PrefService::ReloadPersistentPrefs() { | 224 bool PrefService::ReloadPersistentPrefs() { |
242 return user_pref_store_->ReadPrefs() == | 225 return user_pref_store_->ReadPrefs() == |
243 PersistentPrefStore::PREF_READ_ERROR_NONE; | 226 PersistentPrefStore::PREF_READ_ERROR_NONE; |
244 } | 227 } |
245 | 228 |
246 bool PrefService::SavePersistentPrefs() { | 229 bool PrefService::SavePersistentPrefs() { |
247 DCHECK(CalledOnValidThread()); | 230 DCHECK(CalledOnValidThread()); |
(...skipping 434 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
682 return pref_value_store()->PrefValueFromDefaultStore(name_.c_str()); | 665 return pref_value_store()->PrefValueFromDefaultStore(name_.c_str()); |
683 } | 666 } |
684 | 667 |
685 bool PrefService::Preference::IsUserModifiable() const { | 668 bool PrefService::Preference::IsUserModifiable() const { |
686 return pref_value_store()->PrefValueUserModifiable(name_.c_str()); | 669 return pref_value_store()->PrefValueUserModifiable(name_.c_str()); |
687 } | 670 } |
688 | 671 |
689 bool PrefService::Preference::IsExtensionModifiable() const { | 672 bool PrefService::Preference::IsExtensionModifiable() const { |
690 return pref_value_store()->PrefValueExtensionModifiable(name_.c_str()); | 673 return pref_value_store()->PrefValueExtensionModifiable(name_.c_str()); |
691 } | 674 } |
OLD | NEW |