Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / profiles / profile_impl.cc
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
3 // found in the LICENSE file.
4
5 #include "chrome/browser/profiles/profile_impl.h"
6
7 #include <vector>
8
9 #include "base/bind.h"
10 #include "base/callback.h"
11 #include "base/command_line.h"
12 #include "base/compiler_specific.h"
13 #include "base/debug/trace_event.h"
14 #include "base/environment.h"
15 #include "base/files/file_path.h"
16 #include "base/files/file_util.h"
17 #include "base/memory/scoped_ptr.h"
18 #include "base/path_service.h"
19 #include "base/prefs/json_pref_store.h"
20 #include "base/prefs/scoped_user_pref_update.h"
21 #include "base/strings/string_number_conversions.h"
22 #include "base/strings/string_util.h"
23 #include "base/strings/stringprintf.h"
24 #include "base/strings/utf_string_conversions.h"
25 #include "base/synchronization/waitable_event.h"
26 #include "base/threading/sequenced_worker_pool.h"
27 #include "base/version.h"
28 #include "chrome/browser/autocomplete/autocomplete_classifier.h"
29 #include "chrome/browser/autocomplete/shortcuts_backend.h"
30 #include "chrome/browser/background/background_contents_service_factory.h"
31 #include "chrome/browser/bookmarks/bookmark_model_factory.h"
32 #include "chrome/browser/browser_process.h"
33 #include "chrome/browser/chrome_notification_types.h"
34 #include "chrome/browser/content_settings/cookie_settings.h"
35 #include "chrome/browser/dom_distiller/profile_utils.h"
36 #include "chrome/browser/domain_reliability/service_factory.h"
37 #include "chrome/browser/download/chrome_download_manager_delegate.h"
38 #include "chrome/browser/download/download_service.h"
39 #include "chrome/browser/download/download_service_factory.h"
40 #include "chrome/browser/history/top_sites.h"
41 #include "chrome/browser/net/net_pref_observer.h"
42 #include "chrome/browser/net/predictor.h"
43 #include "chrome/browser/net/pref_proxy_config_tracker.h"
44 #include "chrome/browser/net/proxy_service_factory.h"
45 #include "chrome/browser/net/spdyproxy/data_reduction_proxy_chrome_configurator.h"
46 #include "chrome/browser/net/spdyproxy/data_reduction_proxy_chrome_settings.h"
47 #include "chrome/browser/net/spdyproxy/data_reduction_proxy_chrome_settings_factory.h"
48 #include "chrome/browser/net/ssl_config_service_manager.h"
49 #include "chrome/browser/plugins/chrome_plugin_service_filter.h"
50 #include "chrome/browser/plugins/plugin_prefs.h"
51 #include "chrome/browser/policy/profile_policy_connector.h"
52 #include "chrome/browser/policy/profile_policy_connector_factory.h"
53 #include "chrome/browser/prefs/browser_prefs.h"
54 #include "chrome/browser/prefs/chrome_pref_service_factory.h"
55 #include "chrome/browser/prefs/pref_service_syncable.h"
56 #include "chrome/browser/prefs/tracked/tracked_preference_validation_delegate.h"
57 #include "chrome/browser/prerender/prerender_manager_factory.h"
58 #include "chrome/browser/profiles/bookmark_model_loaded_observer.h"
59 #include "chrome/browser/profiles/chrome_version_service.h"
60 #include "chrome/browser/profiles/gaia_info_update_service_factory.h"
61 #include "chrome/browser/profiles/profile_destroyer.h"
62 #include "chrome/browser/profiles/profile_info_cache.h"
63 #include "chrome/browser/profiles/profile_manager.h"
64 #include "chrome/browser/profiles/profile_metrics.h"
65 #include "chrome/browser/safe_browsing/safe_browsing_service.h"
66 #include "chrome/browser/services/gcm/gcm_profile_service.h"
67 #include "chrome/browser/services/gcm/gcm_profile_service_factory.h"
68 #include "chrome/browser/services/gcm/push_messaging_service_impl.h"
69 #include "chrome/browser/sessions/session_service_factory.h"
70 #include "chrome/browser/signin/signin_ui_util.h"
71 #include "chrome/browser/ssl/chrome_ssl_host_state_delegate.h"
72 #include "chrome/browser/ssl/chrome_ssl_host_state_delegate_factory.h"
73 #include "chrome/browser/ui/startup/startup_browser_creator.h"
74 #include "chrome/browser/ui/zoom/chrome_zoom_level_prefs.h"
75 #include "chrome/common/chrome_constants.h"
76 #include "chrome/common/chrome_paths_internal.h"
77 #include "chrome/common/chrome_switches.h"
78 #include "chrome/common/chrome_version_info.h"
79 #include "chrome/common/pref_names.h"
80 #include "chrome/common/url_constants.h"
81 #include "chrome/grit/chromium_strings.h"
82 #include "components/bookmarks/browser/bookmark_model.h"
83 #include "components/content_settings/core/browser/host_content_settings_map.h"
84 #include "components/data_reduction_proxy/core/browser/data_reduction_proxy_prefs.h"
85 #include "components/data_reduction_proxy/core/browser/data_reduction_proxy_settings.h"
86 #include "components/data_reduction_proxy/core/browser/data_reduction_proxy_statistics_prefs.h"
87 #include "components/data_reduction_proxy/core/common/data_reduction_proxy_params.h"
88 #include "components/domain_reliability/monitor.h"
89 #include "components/domain_reliability/service.h"
90 #include "components/keyed_service/content/browser_context_dependency_manager.h"
91 #include "components/metrics/metrics_service.h"
92 #include "components/pref_registry/pref_registry_syncable.h"
93 #include "components/startup_metric_utils/startup_metric_utils.h"
94 #include "components/url_fixer/url_fixer.h"
95 #include "components/user_prefs/user_prefs.h"
96 #include "content/public/browser/browser_thread.h"
97 #include "content/public/browser/dom_storage_context.h"
98 #include "content/public/browser/host_zoom_map.h"
99 #include "content/public/browser/notification_service.h"
100 #include "content/public/browser/render_process_host.h"
101 #include "content/public/browser/storage_partition.h"
102 #include "content/public/browser/url_data_source.h"
103 #include "content/public/browser/user_metrics.h"
104 #include "content/public/common/content_constants.h"
105 #include "content/public/common/page_zoom.h"
106 #include "ui/base/l10n/l10n_util.h"
107
108 #if defined(OS_ANDROID)
109 #include "chrome/browser/media/protected_media_identifier_permission_context.h"
110 #include "chrome/browser/media/protected_media_identifier_permission_context_factory.h"
111 #endif
112
113 #if defined(OS_CHROMEOS)
114 #include "chrome/browser/chromeos/locale_change_guard.h"
115 #include "chrome/browser/chromeos/preferences.h"
116 #include "chrome/browser/chromeos/profiles/profile_helper.h"
117 #include "components/user_manager/user_manager.h"
118 #endif
119
120 #if defined(ENABLE_BACKGROUND)
121 #include "chrome/browser/background/background_mode_manager.h"
122 #endif
123
124 #if defined(ENABLE_CONFIGURATION_POLICY)
125 #include "chrome/browser/policy/schema_registry_service.h"
126 #include "chrome/browser/policy/schema_registry_service_factory.h"
127 #include "components/policy/core/browser/browser_policy_connector.h"
128 #if defined(OS_CHROMEOS)
129 #include "chrome/browser/chromeos/login/login_utils.h"
130 #include "chrome/browser/chromeos/policy/user_cloud_policy_manager_chromeos.h"
131 #include "chrome/browser/chromeos/policy/user_cloud_policy_manager_factory_chromeos.h"
132 #else
133 #include "chrome/browser/policy/cloud/user_cloud_policy_manager_factory.h"
134 #include "components/policy/core/common/cloud/user_cloud_policy_manager.h"
135 #endif
136 #endif
137
138 #if defined(ENABLE_EXTENSIONS)
139 #include "chrome/browser/extensions/extension_service.h"
140 #include "chrome/browser/extensions/extension_special_storage_policy.h"
141 #include "chrome/browser/ui/webui/extensions/extension_icon_source.h"
142 #include "extensions/browser/extension_pref_store.h"
143 #include "extensions/browser/extension_pref_value_map.h"
144 #include "extensions/browser/extension_pref_value_map_factory.h"
145 #include "extensions/browser/extension_system.h"
146 #include "extensions/browser/guest_view/guest_view_manager.h"
147 #endif
148
149 #if defined(ENABLE_MANAGED_USERS)
150 #include "chrome/browser/supervised_user/supervised_user_settings_service.h"
151 #include "chrome/browser/supervised_user/supervised_user_settings_service_factory.h"
152 #endif
153
154 using base::Time;
155 using base::TimeDelta;
156 using base::UserMetricsAction;
157 using content::BrowserThread;
158 using content::DownloadManagerDelegate;
159 using content::HostZoomMap;
160
161 namespace {
162
163 #if defined(ENABLE_SESSION_SERVICE)
164 // Delay, in milliseconds, before we explicitly create the SessionService.
165 const int kCreateSessionServiceDelayMS = 500;
166 #endif
167
168 // Text content of README file created in each profile directory. Both %s
169 // placeholders must contain the product name. This is not localizable and hence
170 // not in resources.
171 const char kReadmeText[] =
172     "%s settings and storage represent user-selected preferences and "
173     "information and MUST not be extracted, overwritten or modified except "
174     "through %s defined APIs.";
175
176 // Value written to prefs for EXIT_CRASHED and EXIT_SESSION_ENDED.
177 const char kPrefExitTypeCrashed[] = "Crashed";
178 const char kPrefExitTypeSessionEnded[] = "SessionEnded";
179
180 // Helper method needed because PostTask cannot currently take a Callback
181 // function with non-void return type.
182 void CreateDirectoryAndSignal(const base::FilePath& path,
183                               base::WaitableEvent* done_creating) {
184   DVLOG(1) << "Creating directory " << path.value();
185   base::CreateDirectory(path);
186   done_creating->Signal();
187 }
188
189 // Task that blocks the FILE thread until CreateDirectoryAndSignal() finishes on
190 // blocking I/O pool.
191 void BlockFileThreadOnDirectoryCreate(base::WaitableEvent* done_creating) {
192   done_creating->Wait();
193 }
194
195 // Initiates creation of profile directory on |sequenced_task_runner| and
196 // ensures that FILE thread is blocked until that operation finishes.
197 void CreateProfileDirectory(base::SequencedTaskRunner* sequenced_task_runner,
198                             const base::FilePath& path) {
199   base::WaitableEvent* done_creating = new base::WaitableEvent(false, false);
200   sequenced_task_runner->PostTask(FROM_HERE,
201                                   base::Bind(&CreateDirectoryAndSignal,
202                                              path,
203                                              done_creating));
204   // Block the FILE thread until directory is created on I/O pool to make sure
205   // that we don't attempt any operation until that part completes.
206   BrowserThread::PostTask(
207       BrowserThread::FILE, FROM_HERE,
208       base::Bind(&BlockFileThreadOnDirectoryCreate,
209                  base::Owned(done_creating)));
210 }
211
212 base::FilePath GetCachePath(const base::FilePath& base) {
213   return base.Append(chrome::kCacheDirname);
214 }
215
216 base::FilePath GetMediaCachePath(const base::FilePath& base) {
217   return base.Append(chrome::kMediaCacheDirname);
218 }
219
220 void EnsureReadmeFile(const base::FilePath& base) {
221   base::FilePath readme_path = base.Append(chrome::kReadmeFilename);
222   if (base::PathExists(readme_path))
223     return;
224   std::string product_name = l10n_util::GetStringUTF8(IDS_PRODUCT_NAME);
225   std::string readme_text = base::StringPrintf(
226       kReadmeText, product_name.c_str(), product_name.c_str());
227   if (base::WriteFile(readme_path, readme_text.data(), readme_text.size()) ==
228       -1) {
229     LOG(ERROR) << "Could not create README file.";
230   }
231 }
232
233 // Converts the kSessionExitedCleanly pref to the corresponding EXIT_TYPE.
234 Profile::ExitType SessionTypePrefValueToExitType(const std::string& value) {
235   if (value == kPrefExitTypeSessionEnded)
236     return Profile::EXIT_SESSION_ENDED;
237   if (value == kPrefExitTypeCrashed)
238     return Profile::EXIT_CRASHED;
239   return Profile::EXIT_NORMAL;
240 }
241
242 // Converts an ExitType into a string that is written to prefs.
243 std::string ExitTypeToSessionTypePrefValue(Profile::ExitType type) {
244   switch (type) {
245     case Profile::EXIT_NORMAL:
246         return ProfileImpl::kPrefExitTypeNormal;
247     case Profile::EXIT_SESSION_ENDED:
248       return kPrefExitTypeSessionEnded;
249     case Profile::EXIT_CRASHED:
250       return kPrefExitTypeCrashed;
251   }
252   NOTREACHED();
253   return std::string();
254 }
255
256 PrefStore* CreateExtensionPrefStore(Profile* profile,
257                                     bool incognito_pref_store) {
258 #if defined(ENABLE_EXTENSIONS)
259   return new ExtensionPrefStore(
260       ExtensionPrefValueMapFactory::GetForBrowserContext(profile),
261       incognito_pref_store);
262 #else
263   return NULL;
264 #endif
265 }
266
267 }  // namespace
268
269 // static
270 Profile* Profile::CreateProfile(const base::FilePath& path,
271                                 Delegate* delegate,
272                                 CreateMode create_mode) {
273   TRACE_EVENT_BEGIN1("browser",
274                      "Profile::CreateProfile",
275                      "profile_path",
276                      path.value().c_str());
277
278   // Get sequenced task runner for making sure that file operations of
279   // this profile (defined by |path|) are executed in expected order
280   // (what was previously assured by the FILE thread).
281   scoped_refptr<base::SequencedTaskRunner> sequenced_task_runner =
282       JsonPrefStore::GetTaskRunnerForFile(path,
283                                           BrowserThread::GetBlockingPool());
284   if (create_mode == CREATE_MODE_ASYNCHRONOUS) {
285     DCHECK(delegate);
286     CreateProfileDirectory(sequenced_task_runner.get(), path);
287   } else if (create_mode == CREATE_MODE_SYNCHRONOUS) {
288     if (!base::PathExists(path)) {
289       // TODO(tc): http://b/1094718 Bad things happen if we can't write to the
290       // profile directory.  We should eventually be able to run in this
291       // situation.
292       if (!base::CreateDirectory(path))
293         return NULL;
294     }
295   } else {
296     NOTREACHED();
297   }
298
299   return new ProfileImpl(
300       path, delegate, create_mode, sequenced_task_runner.get());
301 }
302
303 // static
304 int ProfileImpl::create_readme_delay_ms = 60000;
305
306 // static
307 const char* const ProfileImpl::kPrefExitTypeNormal = "Normal";
308
309 // static
310 void ProfileImpl::RegisterProfilePrefs(
311     user_prefs::PrefRegistrySyncable* registry) {
312   registry->RegisterBooleanPref(
313       prefs::kSavingBrowserHistoryDisabled,
314       false,
315       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
316   registry->RegisterBooleanPref(
317       prefs::kAllowDeletingBrowserHistory,
318       true,
319       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
320   registry->RegisterBooleanPref(
321       prefs::kSigninAllowed,
322       true,
323       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
324   registry->RegisterBooleanPref(
325       prefs::kForceSafeSearch,
326       false,
327       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
328   registry->RegisterBooleanPref(
329       prefs::kRecordHistory,
330       false,
331       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
332   registry->RegisterIntegerPref(
333       prefs::kProfileAvatarIndex,
334       -1,
335       user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
336   // Whether a profile is using an avatar without having explicitely chosen it
337   // (i.e. was assigned by default by legacy profile creation).
338   registry->RegisterBooleanPref(
339       prefs::kProfileUsingDefaultAvatar,
340       true,
341       user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
342   registry->RegisterBooleanPref(
343       prefs::kProfileUsingGAIAAvatar,
344       false,
345       user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
346   // Whether a profile is using a default avatar name (eg. Pickles or Person 1).
347   registry->RegisterBooleanPref(
348       prefs::kProfileUsingDefaultName,
349       true,
350       user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
351   registry->RegisterStringPref(
352       prefs::kSupervisedUserId,
353       std::string(),
354       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
355   registry->RegisterStringPref(prefs::kProfileName,
356                                std::string(),
357                                user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
358   registry->RegisterStringPref(prefs::kHomePage,
359                                std::string(),
360                                user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
361 #if defined(ENABLE_PRINTING)
362   registry->RegisterBooleanPref(
363       prefs::kPrintingEnabled,
364       true,
365       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
366 #endif
367   registry->RegisterBooleanPref(
368       prefs::kPrintPreviewDisabled,
369       false,
370       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
371   registry->RegisterBooleanPref(
372       prefs::kForceEphemeralProfiles,
373       false,
374       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
375
376   // Initialize the cache prefs.
377   registry->RegisterFilePathPref(
378       prefs::kDiskCacheDir,
379       base::FilePath(),
380       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
381   registry->RegisterIntegerPref(
382       prefs::kDiskCacheSize,
383       0,
384       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
385   registry->RegisterIntegerPref(
386       prefs::kMediaCacheSize,
387       0,
388       user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF);
389
390   // Deprecated. Kept around for migration.
391   registry->RegisterBooleanPref(
392       prefs::kClearSiteDataOnExit,
393       false,
394       user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
395 }
396
397 ProfileImpl::ProfileImpl(
398     const base::FilePath& path,
399     Delegate* delegate,
400     CreateMode create_mode,
401     base::SequencedTaskRunner* sequenced_task_runner)
402     : path_(path),
403       pref_registry_(new user_prefs::PrefRegistrySyncable),
404       io_data_(this),
405       host_content_settings_map_(NULL),
406       last_session_exit_type_(EXIT_NORMAL),
407       start_time_(Time::Now()),
408       delegate_(delegate),
409       predictor_(NULL) {
410   TRACE_EVENT0("browser", "ProfileImpl::ctor")
411   DCHECK(!path.empty()) << "Using an empty path will attempt to write " <<
412                             "profile files to the root directory!";
413
414 #if defined(ENABLE_SESSION_SERVICE)
415   create_session_service_timer_.Start(FROM_HERE,
416       TimeDelta::FromMilliseconds(kCreateSessionServiceDelayMS), this,
417       &ProfileImpl::EnsureSessionServiceCreated);
418 #endif
419
420   // Determine if prefetch is enabled for this profile.
421   // If not profile_manager is present, it means we are in a unittest.
422   const CommandLine* command_line = CommandLine::ForCurrentProcess();
423   predictor_ = chrome_browser_net::Predictor::CreatePredictor(
424       !command_line->HasSwitch(switches::kDisablePreconnect),
425       !command_line->HasSwitch(switches::kDnsPrefetchDisable),
426       g_browser_process->profile_manager() == NULL);
427
428   // If we are creating the profile synchronously, then we should load the
429   // policy data immediately.
430   bool force_immediate_policy_load = (create_mode == CREATE_MODE_SYNCHRONOUS);
431 #if defined(ENABLE_CONFIGURATION_POLICY)
432   policy::BrowserPolicyConnector* connector =
433       g_browser_process->browser_policy_connector();
434   schema_registry_service_ =
435       policy::SchemaRegistryServiceFactory::CreateForContext(
436           this, connector->GetChromeSchema(), connector->GetSchemaRegistry());
437 #if defined(OS_CHROMEOS)
438   cloud_policy_manager_ =
439       policy::UserCloudPolicyManagerFactoryChromeOS::CreateForProfile(
440           this, force_immediate_policy_load, sequenced_task_runner);
441 #else
442   cloud_policy_manager_ =
443       policy::UserCloudPolicyManagerFactory::CreateForOriginalBrowserContext(
444           this,
445           force_immediate_policy_load,
446           sequenced_task_runner,
447           BrowserThread::GetMessageLoopProxyForThread(BrowserThread::FILE),
448           BrowserThread::GetMessageLoopProxyForThread(BrowserThread::IO));
449 #endif
450 #endif
451   profile_policy_connector_ =
452       policy::ProfilePolicyConnectorFactory::CreateForProfile(
453           this, force_immediate_policy_load);
454
455   DCHECK(create_mode == CREATE_MODE_ASYNCHRONOUS ||
456          create_mode == CREATE_MODE_SYNCHRONOUS);
457   bool async_prefs = create_mode == CREATE_MODE_ASYNCHRONOUS;
458
459 #if defined(OS_CHROMEOS)
460   if (chromeos::ProfileHelper::IsSigninProfile(this))
461     chrome::RegisterLoginProfilePrefs(pref_registry_.get());
462   else
463 #endif
464   chrome::RegisterUserProfilePrefs(pref_registry_.get());
465
466   BrowserContextDependencyManager::GetInstance()->
467       RegisterProfilePrefsForServices(this, pref_registry_.get());
468
469   SupervisedUserSettingsService* supervised_user_settings = NULL;
470 #if defined(ENABLE_MANAGED_USERS)
471   supervised_user_settings =
472       SupervisedUserSettingsServiceFactory::GetForProfile(this);
473   supervised_user_settings->Init(
474       path_, sequenced_task_runner, create_mode == CREATE_MODE_SYNCHRONOUS);
475 #endif
476
477   scoped_refptr<SafeBrowsingService> safe_browsing_service(
478       g_browser_process->safe_browsing_service());
479   if (safe_browsing_service.get()) {
480     pref_validation_delegate_ =
481         safe_browsing_service->CreatePreferenceValidationDelegate(this).Pass();
482   }
483
484   {
485     // On startup, preference loading is always synchronous so a scoped timer
486     // will work here.
487     startup_metric_utils::ScopedSlowStartupUMA
488         scoped_timer("Startup.SlowStartupPreferenceLoading");
489     prefs_ = chrome_prefs::CreateProfilePrefs(
490         path_,
491         sequenced_task_runner,
492         pref_validation_delegate_.get(),
493         profile_policy_connector_->policy_service(),
494         supervised_user_settings,
495         CreateExtensionPrefStore(this, false),
496         pref_registry_,
497         async_prefs).Pass();
498     // Register on BrowserContext.
499     user_prefs::UserPrefs::Set(this, prefs_.get());
500   }
501
502   startup_metric_utils::ScopedSlowStartupUMA
503       scoped_timer("Startup.SlowStartupFinalProfileInit");
504   if (async_prefs) {
505     // Wait for the notification that prefs has been loaded
506     // (successfully or not).  Note that we can use base::Unretained
507     // because the PrefService is owned by this class and lives on
508     // the same thread.
509     prefs_->AddPrefInitObserver(base::Bind(&ProfileImpl::OnPrefsLoaded,
510                                            base::Unretained(this)));
511   } else {
512     // Prefs were loaded synchronously so we can continue directly.
513     OnPrefsLoaded(true);
514   }
515 }
516
517 void ProfileImpl::DoFinalInit() {
518   TRACE_EVENT0("browser", "ProfileImpl::DoFinalInit")
519   PrefService* prefs = GetPrefs();
520   pref_change_registrar_.Init(prefs);
521   pref_change_registrar_.Add(
522       prefs::kGoogleServicesUsername,
523       base::Bind(&ProfileImpl::UpdateProfileUserNameCache,
524                  base::Unretained(this)));
525   pref_change_registrar_.Add(
526       prefs::kSupervisedUserId,
527       base::Bind(&ProfileImpl::UpdateProfileSupervisedUserIdCache,
528                  base::Unretained(this)));
529
530   // Changes in the profile avatar.
531   pref_change_registrar_.Add(
532       prefs::kProfileAvatarIndex,
533       base::Bind(&ProfileImpl::UpdateProfileAvatarCache,
534                  base::Unretained(this)));
535   pref_change_registrar_.Add(
536       prefs::kProfileUsingDefaultAvatar,
537       base::Bind(&ProfileImpl::UpdateProfileAvatarCache,
538                  base::Unretained(this)));
539   pref_change_registrar_.Add(
540       prefs::kProfileUsingGAIAAvatar,
541       base::Bind(&ProfileImpl::UpdateProfileAvatarCache,
542                  base::Unretained(this)));
543
544   // Changes in the profile name.
545   pref_change_registrar_.Add(
546       prefs::kProfileUsingDefaultName,
547       base::Bind(&ProfileImpl::UpdateProfileNameCache,
548                  base::Unretained(this)));
549   pref_change_registrar_.Add(
550       prefs::kProfileName,
551       base::Bind(&ProfileImpl::UpdateProfileNameCache,
552                  base::Unretained(this)));
553
554   pref_change_registrar_.Add(
555       prefs::kForceEphemeralProfiles,
556       base::Bind(&ProfileImpl::UpdateProfileIsEphemeralCache,
557                  base::Unretained(this)));
558
559   // It would be nice to use PathService for fetching this directory, but
560   // the cache directory depends on the profile directory, which isn't available
561   // to PathService.
562   chrome::GetUserCacheDirectory(path_, &base_cache_path_);
563   // Always create the cache directory asynchronously.
564   scoped_refptr<base::SequencedTaskRunner> sequenced_task_runner =
565       JsonPrefStore::GetTaskRunnerForFile(base_cache_path_,
566                                           BrowserThread::GetBlockingPool());
567   CreateProfileDirectory(sequenced_task_runner.get(), base_cache_path_);
568
569   // Now that the profile is hooked up to receive pref change notifications to
570   // kGoogleServicesUsername, initialize components that depend on it to reflect
571   // the current value.
572   UpdateProfileUserNameCache();
573   UpdateProfileSupervisedUserIdCache();
574   UpdateProfileIsEphemeralCache();
575   GAIAInfoUpdateServiceFactory::GetForProfile(this);
576
577   PrefService* local_state = g_browser_process->local_state();
578   ssl_config_service_manager_.reset(
579       SSLConfigServiceManager::CreateDefaultManager(local_state));
580
581 #if defined(ENABLE_BACKGROUND)
582   // Initialize the BackgroundModeManager - this has to be done here before
583   // InitExtensions() is called because it relies on receiving notifications
584   // when extensions are loaded. BackgroundModeManager is not needed under
585   // ChromeOS because Chrome is always running, no need for special keep-alive
586   // or launch-on-startup support unless kKeepAliveForTest is set.
587   bool init_background_mode_manager = true;
588 #if defined(OS_CHROMEOS)
589   if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kKeepAliveForTest))
590     init_background_mode_manager = false;
591 #endif
592   if (init_background_mode_manager) {
593     if (g_browser_process->background_mode_manager())
594       g_browser_process->background_mode_manager()->RegisterProfile(this);
595   }
596 #endif  // defined(ENABLE_BACKGROUND)
597
598   base::FilePath cookie_path = GetPath();
599   cookie_path = cookie_path.Append(chrome::kCookieFilename);
600   base::FilePath channel_id_path = GetPath();
601   channel_id_path = channel_id_path.Append(chrome::kChannelIDFilename);
602   base::FilePath cache_path = base_cache_path_;
603   int cache_max_size;
604   GetCacheParameters(false, &cache_path, &cache_max_size);
605   cache_path = GetCachePath(cache_path);
606
607   base::FilePath media_cache_path = base_cache_path_;
608   int media_cache_max_size;
609   GetCacheParameters(true, &media_cache_path, &media_cache_max_size);
610   media_cache_path = GetMediaCachePath(media_cache_path);
611
612   base::FilePath extensions_cookie_path = GetPath();
613   extensions_cookie_path =
614       extensions_cookie_path.Append(chrome::kExtensionsCookieFilename);
615
616   base::FilePath infinite_cache_path = GetPath();
617   infinite_cache_path =
618       infinite_cache_path.Append(FILE_PATH_LITERAL("Infinite Cache"));
619
620 #if defined(OS_ANDROID)
621   SessionStartupPref::Type startup_pref_type =
622       SessionStartupPref::GetDefaultStartupType();
623 #else
624   SessionStartupPref::Type startup_pref_type =
625       StartupBrowserCreator::GetSessionStartupPref(
626           *CommandLine::ForCurrentProcess(), this).type;
627 #endif
628   content::CookieStoreConfig::SessionCookieMode session_cookie_mode =
629       content::CookieStoreConfig::PERSISTANT_SESSION_COOKIES;
630   if (GetLastSessionExitType() == Profile::EXIT_CRASHED ||
631       startup_pref_type == SessionStartupPref::LAST) {
632     session_cookie_mode = content::CookieStoreConfig::RESTORED_SESSION_COOKIES;
633   }
634
635   InitHostZoomMap();
636
637   base::Callback<void(bool)> data_reduction_proxy_unavailable;
638   scoped_ptr<data_reduction_proxy::DataReductionProxyParams>
639       data_reduction_proxy_params;
640   scoped_ptr<DataReductionProxyChromeConfigurator> chrome_configurator;
641   scoped_ptr<data_reduction_proxy::DataReductionProxyStatisticsPrefs>
642       data_reduction_proxy_statistics_prefs;
643   DataReductionProxyChromeSettings* data_reduction_proxy_chrome_settings =
644       DataReductionProxyChromeSettingsFactory::GetForBrowserContext(this);
645   data_reduction_proxy_params =
646       data_reduction_proxy_chrome_settings->params()->Clone();
647   data_reduction_proxy_unavailable =
648       base::Bind(
649           &data_reduction_proxy::DataReductionProxySettings::SetUnreachable,
650           base::Unretained(data_reduction_proxy_chrome_settings));
651   // The configurator is used by DataReductionProxyChromeSettings and
652   // ProfileIOData. Ownership is passed to the latter via ProfileIOData::Handle,
653   // which is only destroyed after BrowserContextKeyedServices,
654   // including DataReductionProxyChromeSettings.
655   chrome_configurator.reset(
656       new DataReductionProxyChromeConfigurator(
657           prefs_.get(),
658           BrowserThread::GetMessageLoopProxyForThread(BrowserThread::IO)));
659   // Retain a raw pointer to use for initialization of data reduction proxy
660   // settings after ownership is passed.
661   DataReductionProxyChromeConfigurator*
662       data_reduction_proxy_chrome_configurator = chrome_configurator.get();
663 #if defined(OS_ANDROID) || defined(OS_IOS)
664   // On mobile we write data reduction proxy prefs directly to the pref service.
665   // On desktop we store data reduction proxy prefs in memory, writing to disk
666   // every 60 minutes and on termination. Shutdown hooks must be added for
667   // Android and iOS in order for non-zero delays to be supported.
668   // (http://crbug.com/408264)
669   base::TimeDelta commit_delay = base::TimeDelta();
670 #else
671   base::TimeDelta commit_delay = base::TimeDelta::FromMinutes(60);
672 #endif
673   // TODO(bengr): Remove this in M-43.
674   data_reduction_proxy::MigrateStatisticsPrefs(g_browser_process->local_state(),
675                                                prefs_.get());
676   data_reduction_proxy_statistics_prefs =
677       scoped_ptr<data_reduction_proxy::DataReductionProxyStatisticsPrefs>(
678           new data_reduction_proxy::DataReductionProxyStatisticsPrefs(
679               prefs_.get(),
680               base::MessageLoopProxy::current(),
681               commit_delay));
682   data_reduction_proxy_chrome_settings->SetDataReductionProxyStatisticsPrefs(
683       data_reduction_proxy_statistics_prefs.get());
684
685   // Make sure we initialize the ProfileIOData after everything else has been
686   // initialized that we might be reading from the IO thread.
687
688   io_data_.Init(cookie_path, channel_id_path, cache_path,
689                 cache_max_size, media_cache_path, media_cache_max_size,
690                 extensions_cookie_path, GetPath(), infinite_cache_path,
691                 predictor_, session_cookie_mode, GetSpecialStoragePolicy(),
692                 CreateDomainReliabilityMonitor(local_state),
693                 data_reduction_proxy_unavailable,
694                 chrome_configurator.Pass(),
695                 data_reduction_proxy_params.Pass(),
696                 data_reduction_proxy_statistics_prefs.Pass());
697   data_reduction_proxy_chrome_settings->InitDataReductionProxySettings(
698       data_reduction_proxy_chrome_configurator,
699       prefs_.get(),
700       g_browser_process->local_state(),
701       GetRequestContext());
702
703 #if defined(ENABLE_PLUGINS)
704   ChromePluginServiceFilter::GetInstance()->RegisterResourceContext(
705       PluginPrefs::GetForProfile(this).get(),
706       io_data_.GetResourceContextNoInit());
707 #endif
708
709   // Delay README creation to not impact startup performance.
710   BrowserThread::PostDelayedTask(
711         BrowserThread::FILE, FROM_HERE,
712         base::Bind(&EnsureReadmeFile, GetPath()),
713         base::TimeDelta::FromMilliseconds(create_readme_delay_ms));
714
715   TRACE_EVENT0("browser", "ProfileImpl::SetSaveSessionStorageOnDisk");
716   content::BrowserContext::GetDefaultStoragePartition(this)->
717       GetDOMStorageContext()->SetSaveSessionStorageOnDisk();
718
719   // The DomDistillerViewerSource is not a normal WebUI so it must be registered
720   // as a URLDataSource early.
721   RegisterDomDistillerViewerSource(this);
722
723   // Creation has been finished.
724   TRACE_EVENT_END1("browser",
725                    "Profile::CreateProfile",
726                    "profile_path",
727                    path_.value().c_str());
728
729 #if defined(OS_CHROMEOS)
730   if (chromeos::LoginUtils::Get()->RestartToApplyPerSessionFlagsIfNeed(this,
731                                                                        true)) {
732     return;
733   }
734 #endif
735
736   if (delegate_) {
737     TRACE_EVENT0("browser", "ProfileImpl::DoFileInit:DelegateOnProfileCreated")
738     delegate_->OnProfileCreated(this, true, IsNewProfile());
739   }
740
741   content::NotificationService::current()->Notify(
742       chrome::NOTIFICATION_PROFILE_CREATED,
743       content::Source<Profile>(this),
744       content::NotificationService::NoDetails());
745
746 #if !defined(OS_CHROMEOS)
747   // Listen for bookmark model load, to bootstrap the sync service.
748   // On CrOS sync service will be initialized after sign in.
749   BookmarkModel* model = BookmarkModelFactory::GetForProfile(this);
750   model->AddObserver(new BookmarkModelLoadedObserver(this));
751 #endif
752
753   gcm::PushMessagingServiceImpl::InitializeForProfile(this);
754
755 #if !defined(OS_ANDROID) && !defined(OS_CHROMEOS) && !defined(OS_IOS)
756   signin_ui_util::InitializePrefsForProfile(this);
757 #endif
758 }
759
760 void ProfileImpl::InitHostZoomMap() {
761   HostZoomMap* host_zoom_map = HostZoomMap::GetDefaultForBrowserContext(this);
762   DCHECK(!zoom_level_prefs_);
763   zoom_level_prefs_.reset(
764       new chrome::ChromeZoomLevelPrefs(prefs_.get(), GetPath()));
765   zoom_level_prefs_->InitPrefsAndCopyToHostZoomMap(GetPath(), host_zoom_map);
766
767   // TODO(wjmaclean): Remove this. crbug.com/420643
768   chrome::MigrateProfileZoomLevelPrefs(this);
769 }
770
771 base::FilePath ProfileImpl::last_selected_directory() {
772   return GetPrefs()->GetFilePath(prefs::kSelectFileLastDirectory);
773 }
774
775 void ProfileImpl::set_last_selected_directory(const base::FilePath& path) {
776   GetPrefs()->SetFilePath(prefs::kSelectFileLastDirectory, path);
777 }
778
779 ProfileImpl::~ProfileImpl() {
780   MaybeSendDestroyedNotification();
781
782   bool prefs_loaded = prefs_->GetInitializationStatus() !=
783       PrefService::INITIALIZATION_STATUS_WAITING;
784
785 #if defined(ENABLE_SESSION_SERVICE)
786   StopCreateSessionServiceTimer();
787 #endif
788
789   // Remove pref observers
790   pref_change_registrar_.RemoveAll();
791
792 #if defined(ENABLE_PLUGINS)
793   ChromePluginServiceFilter::GetInstance()->UnregisterResourceContext(
794       io_data_.GetResourceContextNoInit());
795 #endif
796
797   // Destroy OTR profile and its profile services first.
798   if (off_the_record_profile_) {
799     ProfileDestroyer::DestroyOffTheRecordProfileNow(
800         off_the_record_profile_.get());
801   } else {
802 #if defined(ENABLE_EXTENSIONS)
803     ExtensionPrefValueMapFactory::GetForBrowserContext(this)->
804         ClearAllIncognitoSessionOnlyPreferences();
805 #endif
806   }
807
808   BrowserContextDependencyManager::GetInstance()->DestroyBrowserContextServices(
809       this);
810
811   if (top_sites_.get())
812     top_sites_->Shutdown();
813
814   if (pref_proxy_config_tracker_)
815     pref_proxy_config_tracker_->DetachFromPrefService();
816
817   if (host_content_settings_map_.get())
818     host_content_settings_map_->ShutdownOnUIThread();
819
820   // This causes the Preferences file to be written to disk.
821   if (prefs_loaded)
822     SetExitType(EXIT_NORMAL);
823 }
824
825 std::string ProfileImpl::GetProfileName() {
826   return GetPrefs()->GetString(prefs::kGoogleServicesUsername);
827 }
828
829 Profile::ProfileType ProfileImpl::GetProfileType() const {
830   return REGULAR_PROFILE;
831 }
832
833 base::FilePath ProfileImpl::GetPath() const {
834   return path_;
835 }
836
837 scoped_refptr<base::SequencedTaskRunner> ProfileImpl::GetIOTaskRunner() {
838   return JsonPrefStore::GetTaskRunnerForFile(
839       GetPath(), BrowserThread::GetBlockingPool());
840 }
841
842 bool ProfileImpl::IsOffTheRecord() const {
843   return false;
844 }
845
846 Profile* ProfileImpl::GetOffTheRecordProfile() {
847   if (!off_the_record_profile_) {
848     scoped_ptr<Profile> p(CreateOffTheRecordProfile());
849     off_the_record_profile_.swap(p);
850
851     content::NotificationService::current()->Notify(
852         chrome::NOTIFICATION_PROFILE_CREATED,
853         content::Source<Profile>(off_the_record_profile_.get()),
854         content::NotificationService::NoDetails());
855   }
856   return off_the_record_profile_.get();
857 }
858
859 void ProfileImpl::DestroyOffTheRecordProfile() {
860   off_the_record_profile_.reset();
861 #if defined(ENABLE_EXTENSIONS)
862   ExtensionPrefValueMapFactory::GetForBrowserContext(this)->
863       ClearAllIncognitoSessionOnlyPreferences();
864 #endif
865 }
866
867 bool ProfileImpl::HasOffTheRecordProfile() {
868   return off_the_record_profile_.get() != NULL;
869 }
870
871 Profile* ProfileImpl::GetOriginalProfile() {
872   return this;
873 }
874
875 bool ProfileImpl::IsSupervised() {
876   return !GetPrefs()->GetString(prefs::kSupervisedUserId).empty();
877 }
878
879 ExtensionSpecialStoragePolicy*
880     ProfileImpl::GetExtensionSpecialStoragePolicy() {
881 #if defined(ENABLE_EXTENSIONS)
882   if (!extension_special_storage_policy_.get()) {
883     TRACE_EVENT0("browser", "ProfileImpl::GetExtensionSpecialStoragePolicy")
884     extension_special_storage_policy_ = new ExtensionSpecialStoragePolicy(
885         CookieSettings::Factory::GetForProfile(this).get());
886   }
887   return extension_special_storage_policy_.get();
888 #else
889   return NULL;
890 #endif
891 }
892
893 void ProfileImpl::OnPrefsLoaded(bool success) {
894   TRACE_EVENT0("browser", "ProfileImpl::OnPrefsLoaded")
895   if (!success) {
896     if (delegate_)
897       delegate_->OnProfileCreated(this, false, false);
898     return;
899   }
900
901   // TODO(mirandac): remove migration code after 6 months (crbug.com/69995).
902   if (g_browser_process->local_state())
903     chrome::MigrateBrowserPrefs(this, g_browser_process->local_state());
904   // TODO(ivankr): remove cleanup code eventually (crbug.com/165672).
905   chrome::MigrateUserPrefs(this);
906
907   // |kSessionExitType| was added after |kSessionExitedCleanly|. If the pref
908   // value is empty fallback to checking for |kSessionExitedCleanly|.
909   const std::string exit_type_pref_value(
910       prefs_->GetString(prefs::kSessionExitType));
911   if (exit_type_pref_value.empty()) {
912     last_session_exit_type_ =
913         prefs_->GetBoolean(prefs::kSessionExitedCleanly) ?
914           EXIT_NORMAL : EXIT_CRASHED;
915   } else {
916     last_session_exit_type_ =
917         SessionTypePrefValueToExitType(exit_type_pref_value);
918   }
919   // Mark the session as open.
920   prefs_->SetString(prefs::kSessionExitType, kPrefExitTypeCrashed);
921   // Force this to true in case we fallback and use it.
922   // TODO(sky): remove this in a couple of releases (m28ish).
923   prefs_->SetBoolean(prefs::kSessionExitedCleanly, true);
924
925 #if defined(OS_ANDROID) && defined(FULL_SAFE_BROWSING)
926   // Clear safe browsing setting in the case we need to roll back
927   // for users enrolled in Finch trial before.
928   if (!SafeBrowsingService::IsEnabledByFieldTrial())
929     prefs_->ClearPref(prefs::kSafeBrowsingEnabled);
930 #endif
931
932   g_browser_process->profile_manager()->InitProfileUserPrefs(this);
933
934   BrowserContextDependencyManager::GetInstance()->CreateBrowserContextServices(
935       this);
936
937   DCHECK(!net_pref_observer_);
938   {
939     TRACE_EVENT0("browser", "ProfileImpl::OnPrefsLoaded:NetPrefObserver")
940     net_pref_observer_.reset(new NetPrefObserver(prefs_.get()));
941   }
942
943   chrome_prefs::SchedulePrefsFilePathVerification(path_);
944
945   ChromeVersionService::OnProfileLoaded(prefs_.get(), IsNewProfile());
946   DoFinalInit();
947 }
948
949 bool ProfileImpl::WasCreatedByVersionOrLater(const std::string& version) {
950   Version profile_version(ChromeVersionService::GetVersion(prefs_.get()));
951   Version arg_version(version);
952   return (profile_version.CompareTo(arg_version) >= 0);
953 }
954
955 void ProfileImpl::SetExitType(ExitType exit_type) {
956 #if defined(OS_CHROMEOS)
957   if (chromeos::ProfileHelper::IsSigninProfile(this))
958     return;
959 #endif
960   if (!prefs_)
961     return;
962   ExitType current_exit_type = SessionTypePrefValueToExitType(
963       prefs_->GetString(prefs::kSessionExitType));
964   // This may be invoked multiple times during shutdown. Only persist the value
965   // first passed in (unless it's a reset to the crash state, which happens when
966   // foregrounding the app on mobile).
967   if (exit_type == EXIT_CRASHED || current_exit_type == EXIT_CRASHED) {
968     prefs_->SetString(prefs::kSessionExitType,
969                       ExitTypeToSessionTypePrefValue(exit_type));
970
971     // NOTE: If you change what thread this writes on, be sure and update
972     // chrome::SessionEnding().
973     prefs_->CommitPendingWrite();
974   }
975 }
976
977 Profile::ExitType ProfileImpl::GetLastSessionExitType() {
978   // last_session_exited_cleanly_ is set when the preferences are loaded. Force
979   // it to be set by asking for the prefs.
980   GetPrefs();
981   return last_session_exit_type_;
982 }
983
984 PrefService* ProfileImpl::GetPrefs() {
985   DCHECK(prefs_);  // Should explicitly be initialized.
986   return prefs_.get();
987 }
988
989 chrome::ChromeZoomLevelPrefs* ProfileImpl::GetZoomLevelPrefs() {
990   return zoom_level_prefs_.get();
991 }
992
993 PrefService* ProfileImpl::GetOffTheRecordPrefs() {
994   DCHECK(prefs_);
995   if (!otr_prefs_) {
996     // The new ExtensionPrefStore is ref_counted and the new PrefService
997     // stores a reference so that we do not leak memory here.
998     otr_prefs_.reset(prefs_->CreateIncognitoPrefService(
999         CreateExtensionPrefStore(this, true)));
1000   }
1001   return otr_prefs_.get();
1002 }
1003
1004 net::URLRequestContextGetter* ProfileImpl::CreateRequestContext(
1005     content::ProtocolHandlerMap* protocol_handlers,
1006     content::URLRequestInterceptorScopedVector request_interceptors) {
1007   return io_data_.CreateMainRequestContextGetter(
1008       protocol_handlers,
1009       request_interceptors.Pass(),
1010       g_browser_process->local_state(),
1011       g_browser_process->io_thread()).get();
1012 }
1013
1014 net::URLRequestContextGetter* ProfileImpl::GetRequestContext() {
1015   return GetDefaultStoragePartition(this)->GetURLRequestContext();
1016 }
1017
1018 net::URLRequestContextGetter* ProfileImpl::GetRequestContextForRenderProcess(
1019     int renderer_child_id) {
1020   content::RenderProcessHost* rph = content::RenderProcessHost::FromID(
1021       renderer_child_id);
1022
1023   return rph->GetStoragePartition()->GetURLRequestContext();
1024 }
1025
1026 net::URLRequestContextGetter* ProfileImpl::GetMediaRequestContext() {
1027   // Return the default media context.
1028   return io_data_.GetMediaRequestContextGetter().get();
1029 }
1030
1031 net::URLRequestContextGetter*
1032 ProfileImpl::GetMediaRequestContextForRenderProcess(
1033     int renderer_child_id) {
1034   content::RenderProcessHost* rph = content::RenderProcessHost::FromID(
1035       renderer_child_id);
1036   content::StoragePartition* storage_partition = rph->GetStoragePartition();
1037
1038   return storage_partition->GetMediaURLRequestContext();
1039 }
1040
1041 net::URLRequestContextGetter*
1042 ProfileImpl::GetMediaRequestContextForStoragePartition(
1043     const base::FilePath& partition_path,
1044     bool in_memory) {
1045   return io_data_
1046       .GetIsolatedMediaRequestContextGetter(partition_path, in_memory).get();
1047 }
1048
1049 content::ResourceContext* ProfileImpl::GetResourceContext() {
1050   return io_data_.GetResourceContext();
1051 }
1052
1053 net::URLRequestContextGetter* ProfileImpl::GetRequestContextForExtensions() {
1054   return io_data_.GetExtensionsRequestContextGetter().get();
1055 }
1056
1057 net::URLRequestContextGetter*
1058 ProfileImpl::CreateRequestContextForStoragePartition(
1059     const base::FilePath& partition_path,
1060     bool in_memory,
1061     content::ProtocolHandlerMap* protocol_handlers,
1062     content::URLRequestInterceptorScopedVector request_interceptors) {
1063   return io_data_.CreateIsolatedAppRequestContextGetter(
1064       partition_path,
1065       in_memory,
1066       protocol_handlers,
1067       request_interceptors.Pass()).get();
1068 }
1069
1070 net::SSLConfigService* ProfileImpl::GetSSLConfigService() {
1071   // If ssl_config_service_manager_ is null, this typically means that some
1072   // KeyedService is trying to create a RequestContext at startup,
1073   // but SSLConfigServiceManager is not initialized until DoFinalInit() which is
1074   // invoked after all KeyedServices have been initialized (see
1075   // http://crbug.com/171406).
1076   DCHECK(ssl_config_service_manager_) <<
1077       "SSLConfigServiceManager is not initialized yet";
1078   return ssl_config_service_manager_->Get();
1079 }
1080
1081 HostContentSettingsMap* ProfileImpl::GetHostContentSettingsMap() {
1082   DCHECK_CURRENTLY_ON(BrowserThread::UI);
1083   if (!host_content_settings_map_.get()) {
1084     host_content_settings_map_ = new HostContentSettingsMap(GetPrefs(), false);
1085   }
1086   return host_content_settings_map_.get();
1087 }
1088
1089 content::BrowserPluginGuestManager* ProfileImpl::GetGuestManager() {
1090 #if defined(ENABLE_EXTENSIONS)
1091   return extensions::GuestViewManager::FromBrowserContext(this);
1092 #else
1093   return NULL;
1094 #endif
1095 }
1096
1097 DownloadManagerDelegate* ProfileImpl::GetDownloadManagerDelegate() {
1098   return DownloadServiceFactory::GetForBrowserContext(this)->
1099       GetDownloadManagerDelegate();
1100 }
1101
1102 storage::SpecialStoragePolicy* ProfileImpl::GetSpecialStoragePolicy() {
1103 #if defined(ENABLE_EXTENSIONS)
1104   return GetExtensionSpecialStoragePolicy();
1105 #else
1106   return NULL;
1107 #endif
1108 }
1109
1110 content::PushMessagingService* ProfileImpl::GetPushMessagingService() {
1111   return gcm::GCMProfileServiceFactory::GetForProfile(
1112       this)->push_messaging_service();
1113 }
1114
1115 content::SSLHostStateDelegate* ProfileImpl::GetSSLHostStateDelegate() {
1116   return ChromeSSLHostStateDelegateFactory::GetForProfile(this);
1117 }
1118
1119 bool ProfileImpl::IsSameProfile(Profile* profile) {
1120   if (profile == static_cast<Profile*>(this))
1121     return true;
1122   Profile* otr_profile = off_the_record_profile_.get();
1123   return otr_profile && profile == otr_profile;
1124 }
1125
1126 Time ProfileImpl::GetStartTime() const {
1127   return start_time_;
1128 }
1129
1130 history::TopSites* ProfileImpl::GetTopSites() {
1131   if (!top_sites_.get()) {
1132     top_sites_ = history::TopSites::Create(
1133         this, GetPath().Append(chrome::kTopSitesFilename));
1134   }
1135   return top_sites_.get();
1136 }
1137
1138 history::TopSites* ProfileImpl::GetTopSitesWithoutCreating() {
1139   return top_sites_.get();
1140 }
1141
1142 #if defined(ENABLE_SESSION_SERVICE)
1143 void ProfileImpl::StopCreateSessionServiceTimer() {
1144   create_session_service_timer_.Stop();
1145 }
1146
1147 void ProfileImpl::EnsureSessionServiceCreated() {
1148   SessionServiceFactory::GetForProfile(this);
1149 }
1150 #endif
1151
1152 #if defined(OS_CHROMEOS)
1153 void ProfileImpl::ChangeAppLocale(
1154     const std::string& new_locale, AppLocaleChangedVia via) {
1155   if (new_locale.empty()) {
1156     NOTREACHED();
1157     return;
1158   }
1159   PrefService* local_state = g_browser_process->local_state();
1160   DCHECK(local_state);
1161   if (local_state->IsManagedPreference(prefs::kApplicationLocale))
1162     return;
1163   std::string pref_locale = GetPrefs()->GetString(prefs::kApplicationLocale);
1164   bool do_update_pref = true;
1165   switch (via) {
1166     case APP_LOCALE_CHANGED_VIA_SETTINGS:
1167     case APP_LOCALE_CHANGED_VIA_REVERT: {
1168       // We keep kApplicationLocaleBackup value as a reference.  In case value
1169       // of kApplicationLocale preference would change due to sync from other
1170       // device then kApplicationLocaleBackup value will trigger and allow us to
1171       // show notification about automatic locale change in LocaleChangeGuard.
1172       GetPrefs()->SetString(prefs::kApplicationLocaleBackup, new_locale);
1173       GetPrefs()->ClearPref(prefs::kApplicationLocaleAccepted);
1174       // We maintain kApplicationLocale property in both a global storage
1175       // and user's profile.  Global property determines locale of login screen,
1176       // while user's profile determines his personal locale preference.
1177       break;
1178     }
1179     case APP_LOCALE_CHANGED_VIA_LOGIN:
1180     case APP_LOCALE_CHANGED_VIA_PUBLIC_SESSION_LOGIN: {
1181       if (!pref_locale.empty()) {
1182         DCHECK(pref_locale == new_locale);
1183         std::string accepted_locale =
1184             GetPrefs()->GetString(prefs::kApplicationLocaleAccepted);
1185         if (accepted_locale == new_locale) {
1186           // If locale is accepted then we do not want to show LocaleChange
1187           // notification.  This notification is triggered by different values
1188           // of kApplicationLocaleBackup and kApplicationLocale preferences,
1189           // so make them identical.
1190           GetPrefs()->SetString(prefs::kApplicationLocaleBackup, new_locale);
1191         } else {
1192           // Back up locale of login screen.
1193           std::string cur_locale = g_browser_process->GetApplicationLocale();
1194           GetPrefs()->SetString(prefs::kApplicationLocaleBackup, cur_locale);
1195           if (locale_change_guard_ == NULL)
1196             locale_change_guard_.reset(new chromeos::LocaleChangeGuard(this));
1197           locale_change_guard_->PrepareChangingLocale(cur_locale, new_locale);
1198         }
1199       } else {
1200         std::string cur_locale = g_browser_process->GetApplicationLocale();
1201         std::string backup_locale =
1202             GetPrefs()->GetString(prefs::kApplicationLocaleBackup);
1203         // Profile synchronization takes time and is not completed at that
1204         // moment at first login.  So we initialize locale preference in steps:
1205         // (1) first save it to temporary backup;
1206         // (2) on next login we assume that synchronization is already completed
1207         //     and we may finalize initialization.
1208         GetPrefs()->SetString(prefs::kApplicationLocaleBackup, cur_locale);
1209         if (!new_locale.empty())
1210           GetPrefs()->SetString(prefs::kApplicationLocale, new_locale);
1211         else if (!backup_locale.empty())
1212           GetPrefs()->SetString(prefs::kApplicationLocale, backup_locale);
1213         do_update_pref = false;
1214       }
1215       break;
1216     }
1217     case APP_LOCALE_CHANGED_VIA_UNKNOWN:
1218     default: {
1219       NOTREACHED();
1220       break;
1221     }
1222   }
1223   if (do_update_pref)
1224     GetPrefs()->SetString(prefs::kApplicationLocale, new_locale);
1225   if (via != APP_LOCALE_CHANGED_VIA_PUBLIC_SESSION_LOGIN)
1226     local_state->SetString(prefs::kApplicationLocale, new_locale);
1227
1228   if (user_manager::UserManager::Get()->GetOwnerEmail() ==
1229       chromeos::ProfileHelper::Get()->GetUserByProfile(this)->email())
1230     local_state->SetString(prefs::kOwnerLocale, new_locale);
1231 }
1232
1233 void ProfileImpl::OnLogin() {
1234   if (locale_change_guard_ == NULL)
1235     locale_change_guard_.reset(new chromeos::LocaleChangeGuard(this));
1236   locale_change_guard_->OnLogin();
1237 }
1238
1239 void ProfileImpl::InitChromeOSPreferences() {
1240   chromeos_preferences_.reset(new chromeos::Preferences());
1241   chromeos_preferences_->Init(
1242       this, chromeos::ProfileHelper::Get()->GetUserByProfile(this));
1243 }
1244
1245 #endif  // defined(OS_CHROMEOS)
1246
1247 PrefProxyConfigTracker* ProfileImpl::GetProxyConfigTracker() {
1248   if (!pref_proxy_config_tracker_)
1249     pref_proxy_config_tracker_.reset(CreateProxyConfigTracker());
1250   return pref_proxy_config_tracker_.get();
1251 }
1252
1253 chrome_browser_net::Predictor* ProfileImpl::GetNetworkPredictor() {
1254   return predictor_;
1255 }
1256
1257 DevToolsNetworkController* ProfileImpl::GetDevToolsNetworkController() {
1258   return io_data_.GetDevToolsNetworkController();
1259 }
1260
1261 void ProfileImpl::ClearNetworkingHistorySince(
1262     base::Time time,
1263     const base::Closure& completion) {
1264   io_data_.ClearNetworkingHistorySince(time, completion);
1265 }
1266
1267 GURL ProfileImpl::GetHomePage() {
1268   // --homepage overrides any preferences.
1269   const CommandLine& command_line = *CommandLine::ForCurrentProcess();
1270   if (command_line.HasSwitch(switches::kHomePage)) {
1271     // TODO(evanm): clean up usage of DIR_CURRENT.
1272     //   http://code.google.com/p/chromium/issues/detail?id=60630
1273     // For now, allow this code to call getcwd().
1274     base::ThreadRestrictions::ScopedAllowIO allow_io;
1275
1276     base::FilePath browser_directory;
1277     PathService::Get(base::DIR_CURRENT, &browser_directory);
1278     GURL home_page(url_fixer::FixupRelativeFile(
1279         browser_directory,
1280         command_line.GetSwitchValuePath(switches::kHomePage)));
1281     if (home_page.is_valid())
1282       return home_page;
1283   }
1284
1285   if (GetPrefs()->GetBoolean(prefs::kHomePageIsNewTabPage))
1286     return GURL(chrome::kChromeUINewTabURL);
1287   GURL home_page(url_fixer::FixupURL(GetPrefs()->GetString(prefs::kHomePage),
1288                                      std::string()));
1289   if (!home_page.is_valid())
1290     return GURL(chrome::kChromeUINewTabURL);
1291   return home_page;
1292 }
1293
1294 void ProfileImpl::UpdateProfileUserNameCache() {
1295   ProfileManager* profile_manager = g_browser_process->profile_manager();
1296   ProfileInfoCache& cache = profile_manager->GetProfileInfoCache();
1297   size_t index = cache.GetIndexOfProfileWithPath(GetPath());
1298   if (index != std::string::npos) {
1299     std::string user_name =
1300         GetPrefs()->GetString(prefs::kGoogleServicesUsername);
1301     cache.SetUserNameOfProfileAtIndex(index, base::UTF8ToUTF16(user_name));
1302     ProfileMetrics::UpdateReportedProfilesStatistics(profile_manager);
1303   }
1304 }
1305
1306 void ProfileImpl::UpdateProfileSupervisedUserIdCache() {
1307   ProfileManager* profile_manager = g_browser_process->profile_manager();
1308   ProfileInfoCache& cache = profile_manager->GetProfileInfoCache();
1309   size_t index = cache.GetIndexOfProfileWithPath(GetPath());
1310   if (index != std::string::npos) {
1311     std::string supervised_user_id =
1312         GetPrefs()->GetString(prefs::kSupervisedUserId);
1313     cache.SetSupervisedUserIdOfProfileAtIndex(index, supervised_user_id);
1314     ProfileMetrics::UpdateReportedProfilesStatistics(profile_manager);
1315   }
1316 }
1317
1318 void ProfileImpl::UpdateProfileNameCache() {
1319   ProfileManager* profile_manager = g_browser_process->profile_manager();
1320   ProfileInfoCache& cache = profile_manager->GetProfileInfoCache();
1321   size_t index = cache.GetIndexOfProfileWithPath(GetPath());
1322   if (index != std::string::npos) {
1323     std::string profile_name =
1324         GetPrefs()->GetString(prefs::kProfileName);
1325     cache.SetNameOfProfileAtIndex(index, base::UTF8ToUTF16(profile_name));
1326     bool default_name =
1327         GetPrefs()->GetBoolean(prefs::kProfileUsingDefaultName);
1328     cache.SetProfileIsUsingDefaultNameAtIndex(index, default_name);
1329   }
1330 }
1331
1332 void ProfileImpl::UpdateProfileAvatarCache() {
1333   ProfileManager* profile_manager = g_browser_process->profile_manager();
1334   ProfileInfoCache& cache = profile_manager->GetProfileInfoCache();
1335   size_t index = cache.GetIndexOfProfileWithPath(GetPath());
1336   if (index != std::string::npos) {
1337     size_t avatar_index =
1338         GetPrefs()->GetInteger(prefs::kProfileAvatarIndex);
1339     cache.SetAvatarIconOfProfileAtIndex(index, avatar_index);
1340     bool default_avatar =
1341         GetPrefs()->GetBoolean(prefs::kProfileUsingDefaultAvatar);
1342     cache.SetProfileIsUsingDefaultAvatarAtIndex(index, default_avatar);
1343     bool gaia_avatar =
1344         GetPrefs()->GetBoolean(prefs::kProfileUsingGAIAAvatar);
1345     cache.SetIsUsingGAIAPictureOfProfileAtIndex(index, gaia_avatar);
1346   }
1347 }
1348
1349 void ProfileImpl::UpdateProfileIsEphemeralCache() {
1350   ProfileManager* profile_manager = g_browser_process->profile_manager();
1351   ProfileInfoCache& cache = profile_manager->GetProfileInfoCache();
1352   size_t index = cache.GetIndexOfProfileWithPath(GetPath());
1353   if (index != std::string::npos) {
1354     bool is_ephemeral = GetPrefs()->GetBoolean(prefs::kForceEphemeralProfiles);
1355     cache.SetProfileIsEphemeralAtIndex(index, is_ephemeral);
1356   }
1357 }
1358
1359 // Gets the cache parameters from the command line. If |is_media_context| is
1360 // set to true then settings for the media context type is what we need,
1361 // |cache_path| will be set to the user provided path, or will not be touched if
1362 // there is not an argument. |max_size| will be the user provided value or zero
1363 // by default.
1364 void ProfileImpl::GetCacheParameters(bool is_media_context,
1365                                      base::FilePath* cache_path,
1366                                      int* max_size) {
1367   DCHECK(cache_path);
1368   DCHECK(max_size);
1369   base::FilePath path(prefs_->GetFilePath(prefs::kDiskCacheDir));
1370   if (!path.empty())
1371     *cache_path = path;
1372   *max_size = is_media_context ? prefs_->GetInteger(prefs::kMediaCacheSize) :
1373                                  prefs_->GetInteger(prefs::kDiskCacheSize);
1374 }
1375
1376 PrefProxyConfigTracker* ProfileImpl::CreateProxyConfigTracker() {
1377 #if defined(OS_CHROMEOS)
1378   if (chromeos::ProfileHelper::IsSigninProfile(this)) {
1379     return ProxyServiceFactory::CreatePrefProxyConfigTrackerOfLocalState(
1380         g_browser_process->local_state());
1381   }
1382 #endif  // defined(OS_CHROMEOS)
1383   return ProxyServiceFactory::CreatePrefProxyConfigTrackerOfProfile(
1384       GetPrefs(), g_browser_process->local_state());
1385 }
1386
1387 scoped_ptr<domain_reliability::DomainReliabilityMonitor>
1388 ProfileImpl::CreateDomainReliabilityMonitor(PrefService* local_state) {
1389   domain_reliability::DomainReliabilityService* service =
1390       domain_reliability::DomainReliabilityServiceFactory::GetInstance()->
1391           GetForBrowserContext(this);
1392   if (!service)
1393     return scoped_ptr<domain_reliability::DomainReliabilityMonitor>();
1394
1395   return service->CreateMonitor(
1396       BrowserThread::GetMessageLoopProxyForThread(BrowserThread::IO));
1397 }