blob: f2c276e6253d0b5bfc01b25009db3c459a989d9f [file] [log] [blame]
[email protected]f2a893c2011-01-05 09:38:071// Copyright (c) 2011 The Chromium Authors. All rights reserved.
license.botbf09a502008-08-24 00:55:552// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commit09911bf2008-07-26 23:55:294
5#include "chrome/browser/browser_process_impl.h"
6
[email protected]3cdacd42010-04-30 18:55:537#include <map>
[email protected]68f88b992011-05-07 02:01:398#include <set>
9#include <vector>
[email protected]3cdacd42010-04-30 18:55:5310
initial.commit09911bf2008-07-26 23:55:2911#include "base/command_line.h"
[email protected]6641bf662009-08-21 00:34:0912#include "base/file_util.h"
initial.commit09911bf2008-07-26 23:55:2913#include "base/path_service.h"
[email protected]985655a2011-02-23 09:54:2514#include "base/synchronization/waitable_event.h"
[email protected]c6032e82010-09-13 20:06:0515#include "base/task.h"
[email protected]34b99632011-01-01 01:01:0616#include "base/threading/thread.h"
17#include "base/threading/thread_restrictions.h"
[email protected]e13ad79b2010-07-22 21:36:5018#include "chrome/browser/automation/automation_provider_list.h"
[email protected]b443cb042009-12-15 22:05:0919#include "chrome/browser/browser_main.h"
[email protected]0ac83682010-01-22 17:46:2720#include "chrome/browser/browser_process_sub_thread.h"
[email protected]ac262c9f2008-10-19 17:45:2121#include "chrome/browser/browser_trial.h"
[email protected]9678cb42011-01-31 18:49:4222#include "chrome/browser/debugger/browser_list_tabcontents_provider.h"
[email protected]5613126e2011-01-31 15:27:5523#include "chrome/browser/debugger/devtools_http_protocol_handler.h"
[email protected]40ecc902009-03-16 13:42:4724#include "chrome/browser/debugger/devtools_manager.h"
[email protected]5613126e2011-01-31 15:27:5525#include "chrome/browser/debugger/devtools_protocol_handler.h"
[email protected]6c69796d2010-07-16 21:41:1626#include "chrome/browser/download/download_file_manager.h"
[email protected]5ba0a2c2009-02-19 01:19:3427#include "chrome/browser/download/save_file_manager.h"
[email protected]3ce02412011-03-01 12:01:1528#include "chrome/browser/extensions/extension_event_router_forwarder.h"
[email protected]fc4facd2011-03-22 23:18:5029#include "chrome/browser/extensions/extension_tab_id_map.h"
[email protected]214538842011-04-01 18:47:2430#include "chrome/browser/extensions/user_script_listener.h"
[email protected]815856722011-04-13 17:19:1931#include "chrome/browser/first_run/upgrade_util.h"
[email protected]f7578f52010-08-30 22:22:4932#include "chrome/browser/google/google_url_tracker.h"
[email protected]dcefa302009-05-20 00:24:3933#include "chrome/browser/icon_manager.h"
[email protected]c4ff4952010-01-08 19:12:4734#include "chrome/browser/intranet_redirect_detector.h"
[email protected]0ac83682010-01-22 17:46:2735#include "chrome/browser/io_thread.h"
[email protected]dc6f4962009-02-13 01:25:5036#include "chrome/browser/metrics/metrics_service.h"
[email protected]0b565182011-03-02 18:11:1537#include "chrome/browser/metrics/thread_watcher.h"
[email protected]b2fcd0e2010-12-01 15:19:4038#include "chrome/browser/net/chrome_net_log.h"
[email protected]3530cd92010-06-27 06:22:0139#include "chrome/browser/net/predictor_api.h"
[email protected]d393a0fd2009-05-13 23:32:0140#include "chrome/browser/net/sdch_dictionary_fetcher.h"
[email protected]29672ab2009-10-30 03:44:0341#include "chrome/browser/notifications/notification_ui_manager.h"
[email protected]838dd914a2011-05-09 02:50:5842#include "chrome/browser/platform_util.h"
[email protected]6618d1d2010-12-15 21:18:4743#include "chrome/browser/plugin_data_remover.h"
[email protected]985655a2011-02-23 09:54:2544#include "chrome/browser/policy/browser_policy_connector.h"
[email protected]caf63aea2011-04-26 11:04:1045#include "chrome/browser/prefs/browser_prefs.h"
[email protected]37858e52010-08-26 00:22:0246#include "chrome/browser/prefs/pref_service.h"
[email protected]68f88b992011-05-07 02:01:3947#include "chrome/browser/printing/background_printing_manager.h"
[email protected]e06131d2010-02-10 18:40:3348#include "chrome/browser/printing/print_job_manager.h"
[email protected]dbeebd52010-11-16 20:34:1649#include "chrome/browser/printing/print_preview_tab_controller.h"
[email protected]8ecad5e2010-12-02 21:18:3350#include "chrome/browser/profiles/profile_manager.h"
[email protected]a7a5e992010-12-09 23:39:5151#include "chrome/browser/safe_browsing/client_side_detection_service.h"
[email protected]81218f42009-02-05 18:48:0852#include "chrome/browser/safe_browsing/safe_browsing_service.h"
[email protected]e450fa62011-02-01 12:52:5653#include "chrome/browser/shell_integration.h"
[email protected]8b8e7c92010-08-19 18:05:5654#include "chrome/browser/sidebar/sidebar_manager.h"
[email protected]0b4d3382010-07-14 16:13:0455#include "chrome/browser/tab_closeable_state_watcher.h"
[email protected]71b73f02011-04-06 15:57:2956#include "chrome/browser/ui/browser_list.h"
[email protected]4ef795df2010-02-03 02:35:0857#include "chrome/common/chrome_constants.h"
initial.commit09911bf2008-07-26 23:55:2958#include "chrome/common/chrome_paths.h"
59#include "chrome/common/chrome_switches.h"
[email protected]f1b6de22010-03-06 12:13:4760#include "chrome/common/extensions/extension_l10n_util.h"
[email protected]985655a2011-02-23 09:54:2561#include "chrome/common/extensions/extension_resource.h"
[email protected]ea587b02010-05-21 15:01:3562#include "chrome/common/json_pref_store.h"
initial.commit09911bf2008-07-26 23:55:2963#include "chrome/common/pref_names.h"
[email protected]5c08f222010-09-22 09:37:2164#include "chrome/common/switch_utils.h"
[email protected]985655a2011-02-23 09:54:2565#include "chrome/common/url_constants.h"
[email protected]bd48c2b02010-04-09 20:32:4266#include "chrome/installer/util/google_update_constants.h"
[email protected]a01efd22011-03-01 00:38:3267#include "content/browser/browser_child_process_host.h"
68#include "content/browser/browser_thread.h"
[email protected]419a0572011-04-18 22:21:4669#include "content/browser/child_process_security_policy.h"
[email protected]d9f37932011-05-09 20:09:2470#include "content/browser/gpu/gpu_process_host_ui_shim.h"
[email protected]a01efd22011-03-01 00:38:3271#include "content/browser/plugin_service.h"
72#include "content/browser/renderer_host/render_process_host.h"
73#include "content/browser/renderer_host/resource_dispatcher_host.h"
[email protected]f20d7332011-03-08 21:11:5374#include "content/common/notification_service.h"
[email protected]d55aaa132009-09-28 21:08:0475#include "ipc/ipc_logging.h"
[email protected]abe2c032011-03-31 18:49:3476#include "net/url_request/url_request_context_getter.h"
[email protected]2dfeaf92011-01-10 21:08:2177#include "ui/base/clipboard/clipboard.h"
[email protected]c051a1b2011-01-21 23:30:1778#include "ui/base/l10n/l10n_util.h"
[email protected]4ef795df2010-02-03 02:35:0879#include "webkit/database/database_tracker.h"
[email protected]b112a4c2009-02-01 20:24:0180
81#if defined(OS_WIN)
[email protected]2362e4f2009-05-08 00:34:0582#include "views/focus/view_storage.h"
[email protected]86230b92009-11-23 20:38:3883#endif
84
[email protected]d55aaa132009-09-28 21:08:0485#if defined(IPC_MESSAGE_LOG_ENABLED)
[email protected]ff47b2962011-03-07 23:51:4986#include "content/common/child_process_messages.h"
[email protected]d55aaa132009-09-28 21:08:0487#endif
88
[email protected]db0e86dd2011-03-16 14:47:2189#if defined(OS_CHROMEOS)
90#include "chrome/browser/chromeos/proxy_config_service_impl.h"
[email protected]2d14b3732011-05-10 16:48:4491#include "chrome/browser/chromeos/web_socket_proxy_controller.h"
[email protected]db0e86dd2011-03-16 14:47:2192#endif // defined(OS_CHROMEOS)
93
[email protected]3cdacd42010-04-30 18:55:5394#if (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)
95// How often to check if the persistent instance of Chrome needs to restart
96// to install an update.
97static const int kUpdateCheckIntervalHours = 6;
98#endif
99
[email protected]c6032e82010-09-13 20:06:05100#if defined(USE_X11)
101// How long to wait for the File thread to complete during EndSession, on
102// Linux. We have a timeout here because we're unable to run the UI messageloop
103// and there's some deadlock risk. Our only option is to exit anyway.
104static const int kEndSessionTimeoutSeconds = 10;
105#endif
106
[email protected]bb975362009-01-21 01:00:22107BrowserProcessImpl::BrowserProcessImpl(const CommandLine& command_line)
initial.commit09911bf2008-07-26 23:55:29108 : created_resource_dispatcher_host_(false),
109 created_metrics_service_(false),
110 created_io_thread_(false),
111 created_file_thread_(false),
112 created_db_thread_(false),
[email protected]914511712009-11-23 19:42:33113 created_process_launcher_thread_(false),
[email protected]875ee822010-05-18 20:58:01114 created_cache_thread_(false),
[email protected]7a31f7c2011-03-21 23:22:04115 created_gpu_thread_(false),
[email protected]0b565182011-03-02 18:11:15116 created_watchdog_thread_(false),
[email protected]2d14b3732011-05-10 16:48:44117#if defined(OS_CHROMEOS)
118 created_web_socket_proxy_thread_(false),
119#endif
initial.commit09911bf2008-07-26 23:55:29120 created_profile_manager_(false),
121 created_local_state_(false),
[email protected]b112a4c2009-02-01 20:24:01122 created_icon_manager_(false),
[email protected]40ecc902009-03-16 13:42:47123 created_devtools_manager_(false),
[email protected]8b8e7c92010-08-19 18:05:56124 created_sidebar_manager_(false),
[email protected]985655a2011-02-23 09:54:25125 created_browser_policy_connector_(false),
[email protected]29672ab2009-10-30 03:44:03126 created_notification_ui_manager_(false),
[email protected]a7a5e992010-12-09 23:39:51127 created_safe_browsing_detection_service_(false),
initial.commit09911bf2008-07-26 23:55:29128 module_ref_count_(0),
[email protected]afd20c022010-06-10 00:48:20129 did_start_(false),
[email protected]1b2db1a2008-08-08 17:46:13130 checked_for_new_frames_(false),
[email protected]4747caf2011-03-23 20:09:21131 using_new_frames_(false) {
initial.commit09911bf2008-07-26 23:55:29132 g_browser_process = this;
[email protected]2dfeaf92011-01-10 21:08:21133 clipboard_.reset(new ui::Clipboard);
initial.commit09911bf2008-07-26 23:55:29134 main_notification_service_.reset(new NotificationService);
135
[email protected]6618d1d2010-12-15 21:18:47136 notification_registrar_.Add(this,
137 NotificationType::APP_TERMINATING,
138 NotificationService::AllSources());
139
initial.commit09911bf2008-07-26 23:55:29140 // Must be created after the NotificationService.
141 print_job_manager_.reset(new printing::PrintJobManager);
142
[email protected]b797e152009-01-23 16:06:14143 shutdown_event_.reset(new base::WaitableEvent(true, false));
[email protected]b2fcd0e2010-12-01 15:19:40144
145 net_log_.reset(new ChromeNetLog);
[email protected]3ce02412011-03-01 12:01:15146
147 extension_event_router_forwarder_ = new ExtensionEventRouterForwarder;
[email protected]fc4facd2011-03-22 23:18:50148
149 ExtensionTabIdMap::GetInstance()->Init();
initial.commit09911bf2008-07-26 23:55:29150}
151
152BrowserProcessImpl::~BrowserProcessImpl() {
[email protected]4ef795df2010-02-03 02:35:08153 FilePath profile_path;
154 bool clear_local_state_on_exit;
155
156 // Store the profile path for clearing local state data on exit.
157 clear_local_state_on_exit = ShouldClearLocalState(&profile_path);
158
[email protected]2d14b3732011-05-10 16:48:44159#if defined(OS_CHROMEOS)
160 if (web_socket_proxy_thread_.get())
161 chromeos::WebSocketProxyController::Shutdown();
162 web_socket_proxy_thread_.reset();
163#endif
164
initial.commit09911bf2008-07-26 23:55:29165 // Delete the AutomationProviderList before NotificationService,
166 // since it may try to unregister notifications
167 // Both NotificationService and AutomationProvider are singleton instances in
168 // the BrowserProcess. Since AutomationProvider may have some active
169 // notification observers, it is essential that it gets destroyed before the
170 // NotificationService. NotificationService won't be destroyed until after
171 // this destructor is run.
172 automation_provider_list_.reset();
173
[email protected]d393a0fd2009-05-13 23:32:01174 // We need to shutdown the SdchDictionaryFetcher as it regularly holds
175 // a pointer to a URLFetcher, and that URLFetcher (upon destruction) will do
176 // a PostDelayedTask onto the IO thread. This shutdown call will both discard
177 // any pending URLFetchers, and avoid creating any more.
178 SdchDictionaryFetcher::Shutdown();
179
[email protected]51ac040762011-01-20 02:01:04180 // We need to destroy the MetricsService, GoogleURLTracker,
181 // IntranetRedirectDetector, and SafeBrowsing ClientSideDetectionService
182 // before the io_thread_ gets destroyed, since their destructors can call the
183 // URLFetcher destructor, which does a PostDelayedTask operation on the IO
184 // thread. (The IO thread will handle that URLFetcher operation before going
185 // away.)
initial.commit09911bf2008-07-26 23:55:29186 metrics_service_.reset();
187 google_url_tracker_.reset();
[email protected]c4ff4952010-01-08 19:12:47188 intranet_redirect_detector_.reset();
[email protected]51ac040762011-01-20 02:01:04189 safe_browsing_detection_service_.reset();
initial.commit09911bf2008-07-26 23:55:29190
[email protected]d8a899c2010-09-21 04:50:33191 // Need to clear the desktop notification balloons before the io_thread_ and
192 // before the profiles, since if there are any still showing we will access
193 // those things during teardown.
194 notification_ui_manager_.reset();
195
initial.commit09911bf2008-07-26 23:55:29196 // Need to clear profiles (download managers) before the io_thread_.
197 profile_manager_.reset();
198
199 // Debugger must be cleaned up before IO thread and NotificationService.
[email protected]5613126e2011-01-31 15:27:55200 if (devtools_http_handler_.get()) {
201 devtools_http_handler_->Stop();
202 devtools_http_handler_ = NULL;
203 }
204 if (devtools_legacy_handler_.get()) {
205 devtools_legacy_handler_->Stop();
206 devtools_legacy_handler_ = NULL;
207 }
initial.commit09911bf2008-07-26 23:55:29208
209 if (resource_dispatcher_host_.get()) {
210 // Need to tell Safe Browsing Service that the IO thread is going away
211 // since it cached a pointer to it.
212 if (resource_dispatcher_host()->safe_browsing_service())
213 resource_dispatcher_host()->safe_browsing_service()->ShutDown();
214
215 // Cancel pending requests and prevent new requests.
216 resource_dispatcher_host()->Shutdown();
217 }
218
[email protected]fc4facd2011-03-22 23:18:50219 ExtensionTabIdMap::GetInstance()->Shutdown();
220
[email protected]985655a2011-02-23 09:54:25221 // The policy providers managed by |browser_policy_connector_| need to shut
222 // down while the IO and FILE threads are still alive.
223 browser_policy_connector_.reset();
[email protected]f2a893c2011-01-05 09:38:07224
[email protected]753efc42010-03-09 19:52:16225#if defined(USE_X11)
[email protected]4c3cd7412009-04-22 17:56:06226 // The IO thread must outlive the BACKGROUND_X11 thread.
227 background_x11_thread_.reset();
228#endif
229
[email protected]6618d1d2010-12-15 21:18:47230 // Wait for removing plugin data to finish before shutting down the IO thread.
231 WaitForPluginDataRemoverToFinish();
232
[email protected]7a31f7c2011-03-21 23:22:04233 // Destroying the GpuProcessHostUIShims on the UI thread posts a task to
234 // delete related objects on the GPU thread. This must be done before
235 // stopping the GPU thread. The GPU thread will close IPC channels to renderer
236 // processes so this has to happen before stopping the IO thread.
237 GpuProcessHostUIShim::DestroyAll();
238 gpu_thread_.reset();
239
initial.commit09911bf2008-07-26 23:55:29240 // Need to stop io_thread_ before resource_dispatcher_host_, since
241 // io_thread_ may still deref ResourceDispatcherHost and handle resource
242 // request before going away.
[email protected]0ac83682010-01-22 17:46:27243 io_thread_.reset();
initial.commit09911bf2008-07-26 23:55:29244
[email protected]875ee822010-05-18 20:58:01245 // The IO thread was the only user of this thread.
246 cache_thread_.reset();
247
[email protected]914511712009-11-23 19:42:33248 // Stop the process launcher thread after the IO thread, in case the IO thread
249 // posted a task to terminate a process on the process launcher thread.
250 process_launcher_thread_.reset();
251
initial.commit09911bf2008-07-26 23:55:29252 // Clean up state that lives on the file_thread_ before it goes away.
253 if (resource_dispatcher_host_.get()) {
254 resource_dispatcher_host()->download_file_manager()->Shutdown();
255 resource_dispatcher_host()->save_file_manager()->Shutdown();
256 }
257
258 // Need to stop the file_thread_ here to force it to process messages in its
259 // message loop from the previous call to shutdown the DownloadFileManager,
260 // SaveFileManager and SessionService.
261 file_thread_.reset();
262
263 // With the file_thread_ flushed, we can release any icon resources.
264 icon_manager_.reset();
265
266 // Need to destroy ResourceDispatcherHost before PluginService and
[email protected]49f28bc72010-02-04 00:10:01267 // SafeBrowsingService, since it caches a pointer to it. This also
268 // causes the webkit thread to terminate.
initial.commit09911bf2008-07-26 23:55:29269 resource_dispatcher_host_.reset();
270
271 // Wait for the pending print jobs to finish.
272 print_job_manager_->OnQuit();
273 print_job_manager_.reset();
274
[email protected]0b4d3382010-07-14 16:13:04275 // Destroy TabCloseableStateWatcher before NotificationService since the
276 // former registers for notifications.
277 tab_closeable_state_watcher_.reset();
278
initial.commit09911bf2008-07-26 23:55:29279 // Now OK to destroy NotificationService.
280 main_notification_service_.reset();
281
[email protected]49f28bc72010-02-04 00:10:01282 // Prior to clearing local state, we want to complete tasks pending
283 // on the db thread too.
284 db_thread_.reset();
285
[email protected]0b565182011-03-02 18:11:15286 // Stop the watchdog thread after stopping other threads.
287 watchdog_thread_.reset();
288
[email protected]49f28bc72010-02-04 00:10:01289 // At this point, no render process exist and the file, io, db, and
290 // webkit threads in this process have all terminated, so it's safe
291 // to access local state data such as cookies, database, or local storage.
292 if (clear_local_state_on_exit)
293 ClearLocalState(profile_path);
294
initial.commit09911bf2008-07-26 23:55:29295 g_browser_process = NULL;
296}
297
[email protected]c6032e82010-09-13 20:06:05298#if defined(OS_WIN)
[email protected]295039bd2008-08-15 04:32:57299// Send a QuitTask to the given MessageLoop.
300static void PostQuit(MessageLoop* message_loop) {
301 message_loop->PostTask(FROM_HERE, new MessageLoop::QuitTask());
302}
[email protected]c6032e82010-09-13 20:06:05303#elif defined(USE_X11)
304static void Signal(base::WaitableEvent* event) {
305 event->Signal();
306}
307#endif
initial.commit09911bf2008-07-26 23:55:29308
[email protected]b443cb042009-12-15 22:05:09309unsigned int BrowserProcessImpl::AddRefModule() {
310 DCHECK(CalledOnValidThread());
[email protected]afd20c022010-06-10 00:48:20311 did_start_ = true;
[email protected]b443cb042009-12-15 22:05:09312 module_ref_count_++;
313 return module_ref_count_;
314}
315
316unsigned int BrowserProcessImpl::ReleaseModule() {
317 DCHECK(CalledOnValidThread());
[email protected]760d970a2010-05-18 00:39:18318 DCHECK_NE(0u, module_ref_count_);
[email protected]b443cb042009-12-15 22:05:09319 module_ref_count_--;
320 if (0 == module_ref_count_) {
[email protected]7d038c32010-12-14 00:40:00321 // Allow UI and IO threads to do blocking IO on shutdown, since we do a lot
322 // of it on shutdown for valid reasons.
323 base::ThreadRestrictions::SetIOAllowed(true);
324 io_thread()->message_loop()->PostTask(
325 FROM_HERE,
326 NewRunnableFunction(&base::ThreadRestrictions::SetIOAllowed, true));
[email protected]b443cb042009-12-15 22:05:09327 MessageLoop::current()->PostTask(
[email protected]34f73fb2010-03-24 20:50:34328 FROM_HERE, NewRunnableFunction(DidEndMainMessageLoop));
[email protected]b443cb042009-12-15 22:05:09329 MessageLoop::current()->Quit();
330 }
331 return module_ref_count_;
332}
333
initial.commit09911bf2008-07-26 23:55:29334void BrowserProcessImpl::EndSession() {
[email protected]c6032e82010-09-13 20:06:05335#if defined(OS_WIN) || defined(USE_X11)
[email protected]d65cab7a2008-08-12 01:25:41336 // Notify we are going away.
[email protected]c6032e82010-09-13 20:06:05337 shutdown_event_->Signal();
[email protected]b112a4c2009-02-01 20:24:01338#endif
[email protected]d65cab7a2008-08-12 01:25:41339
initial.commit09911bf2008-07-26 23:55:29340 // Mark all the profiles as clean.
341 ProfileManager* pm = profile_manager();
[email protected]844a1002011-04-19 11:37:21342 std::vector<Profile*> profiles(pm->GetLoadedProfiles());
343 for (size_t i = 0; i < profiles.size(); ++i)
344 profiles[i]->MarkAsCleanShutdown();
initial.commit09911bf2008-07-26 23:55:29345
346 // Tell the metrics service it was cleanly shutdown.
347 MetricsService* metrics = g_browser_process->metrics_service();
348 if (metrics && local_state()) {
initial.commit09911bf2008-07-26 23:55:29349 metrics->RecordStartOfSessionEnd();
350
351 // MetricsService lazily writes to prefs, force it to write now.
[email protected]6faa0e0d2009-04-28 06:50:36352 local_state()->SavePersistentPrefs();
initial.commit09911bf2008-07-26 23:55:29353 }
354
355 // We must write that the profile and metrics service shutdown cleanly,
356 // otherwise on startup we'll think we crashed. So we block until done and
357 // then proceed with normal shutdown.
[email protected]c6032e82010-09-13 20:06:05358#if defined(USE_X11)
359 // Can't run a local loop on linux. Instead create a waitable event.
360 base::WaitableEvent done_writing(false, false);
[email protected]d04e7662010-10-10 22:24:48361 BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
[email protected]c6032e82010-09-13 20:06:05362 NewRunnableFunction(Signal, &done_writing));
363 done_writing.TimedWait(
364 base::TimeDelta::FromSeconds(kEndSessionTimeoutSeconds));
365#elif defined(OS_WIN)
[email protected]d04e7662010-10-10 22:24:48366 BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
[email protected]295039bd2008-08-15 04:32:57367 NewRunnableFunction(PostQuit, MessageLoop::current()));
initial.commit09911bf2008-07-26 23:55:29368 MessageLoop::current()->Run();
[email protected]c6032e82010-09-13 20:06:05369#else
370 NOTIMPLEMENTED();
371#endif
initial.commit09911bf2008-07-26 23:55:29372}
373
[email protected]e13ad79b2010-07-22 21:36:50374ResourceDispatcherHost* BrowserProcessImpl::resource_dispatcher_host() {
375 DCHECK(CalledOnValidThread());
376 if (!created_resource_dispatcher_host_)
377 CreateResourceDispatcherHost();
378 return resource_dispatcher_host_.get();
379}
380
381MetricsService* BrowserProcessImpl::metrics_service() {
382 DCHECK(CalledOnValidThread());
383 if (!created_metrics_service_)
384 CreateMetricsService();
385 return metrics_service_.get();
386}
387
388IOThread* BrowserProcessImpl::io_thread() {
389 DCHECK(CalledOnValidThread());
390 if (!created_io_thread_)
391 CreateIOThread();
392 return io_thread_.get();
393}
394
395base::Thread* BrowserProcessImpl::file_thread() {
396 DCHECK(CalledOnValidThread());
397 if (!created_file_thread_)
398 CreateFileThread();
399 return file_thread_.get();
400}
401
402base::Thread* BrowserProcessImpl::db_thread() {
403 DCHECK(CalledOnValidThread());
404 if (!created_db_thread_)
405 CreateDBThread();
406 return db_thread_.get();
407}
408
409base::Thread* BrowserProcessImpl::process_launcher_thread() {
410 DCHECK(CalledOnValidThread());
411 if (!created_process_launcher_thread_)
412 CreateProcessLauncherThread();
413 return process_launcher_thread_.get();
414}
415
416base::Thread* BrowserProcessImpl::cache_thread() {
417 DCHECK(CalledOnValidThread());
418 if (!created_cache_thread_)
419 CreateCacheThread();
420 return cache_thread_.get();
421}
422
[email protected]7a31f7c2011-03-21 23:22:04423base::Thread* BrowserProcessImpl::gpu_thread() {
424 DCHECK(CalledOnValidThread());
425 if (!created_gpu_thread_)
426 CreateGpuThread();
427 return gpu_thread_.get();
428}
429
[email protected]e13ad79b2010-07-22 21:36:50430#if defined(USE_X11)
431base::Thread* BrowserProcessImpl::background_x11_thread() {
432 DCHECK(CalledOnValidThread());
433 // The BACKGROUND_X11 thread is created when the IO thread is created.
434 if (!created_io_thread_)
435 CreateIOThread();
436 return background_x11_thread_.get();
437}
438#endif
439
[email protected]0b565182011-03-02 18:11:15440WatchDogThread* BrowserProcessImpl::watchdog_thread() {
441 DCHECK(CalledOnValidThread());
442 if (!created_watchdog_thread_)
443 CreateWatchdogThread();
444 DCHECK(watchdog_thread_.get() != NULL);
445 return watchdog_thread_.get();
446}
447
[email protected]2d14b3732011-05-10 16:48:44448#if defined(OS_CHROMEOS)
449base::Thread* BrowserProcessImpl::web_socket_proxy_thread() {
450 DCHECK(CalledOnValidThread());
451 if (!created_web_socket_proxy_thread_)
452 CreateWebSocketProxyThread();
453 DCHECK(web_socket_proxy_thread_.get() != NULL);
454 return web_socket_proxy_thread_.get();
455}
456#endif
457
[email protected]e13ad79b2010-07-22 21:36:50458ProfileManager* BrowserProcessImpl::profile_manager() {
459 DCHECK(CalledOnValidThread());
460 if (!created_profile_manager_)
461 CreateProfileManager();
462 return profile_manager_.get();
463}
464
465PrefService* BrowserProcessImpl::local_state() {
466 DCHECK(CalledOnValidThread());
467 if (!created_local_state_)
468 CreateLocalState();
469 return local_state_.get();
470}
471
472DevToolsManager* BrowserProcessImpl::devtools_manager() {
473 DCHECK(CalledOnValidThread());
474 if (!created_devtools_manager_)
475 CreateDevToolsManager();
476 return devtools_manager_.get();
477}
478
[email protected]8b8e7c92010-08-19 18:05:56479SidebarManager* BrowserProcessImpl::sidebar_manager() {
480 DCHECK(CalledOnValidThread());
481 if (!created_sidebar_manager_)
482 CreateSidebarManager();
483 return sidebar_manager_.get();
484}
485
[email protected]2dfeaf92011-01-10 21:08:21486ui::Clipboard* BrowserProcessImpl::clipboard() {
[email protected]e13ad79b2010-07-22 21:36:50487 DCHECK(CalledOnValidThread());
488 return clipboard_.get();
489}
490
[email protected]abe2c032011-03-31 18:49:34491net::URLRequestContextGetter* BrowserProcessImpl::system_request_context() {
[email protected]db0e86dd2011-03-16 14:47:21492 DCHECK(CalledOnValidThread());
493 return io_thread()->system_url_request_context_getter();
494}
495
496#if defined(OS_CHROMEOS)
497chromeos::ProxyConfigServiceImpl*
498BrowserProcessImpl::chromeos_proxy_config_service_impl() {
499 DCHECK(CalledOnValidThread());
500 if (!chromeos_proxy_config_service_impl_) {
501 chromeos_proxy_config_service_impl_ =
502 new chromeos::ProxyConfigServiceImpl();
503 }
504 return chromeos_proxy_config_service_impl_;
505}
506#endif // defined(OS_CHROMEOS)
507
[email protected]3ce02412011-03-01 12:01:15508ExtensionEventRouterForwarder*
509BrowserProcessImpl::extension_event_router_forwarder() {
510 return extension_event_router_forwarder_.get();
511}
512
[email protected]e13ad79b2010-07-22 21:36:50513NotificationUIManager* BrowserProcessImpl::notification_ui_manager() {
514 DCHECK(CalledOnValidThread());
515 if (!created_notification_ui_manager_)
516 CreateNotificationUIManager();
517 return notification_ui_manager_.get();
518}
519
[email protected]985655a2011-02-23 09:54:25520policy::BrowserPolicyConnector* BrowserProcessImpl::browser_policy_connector() {
[email protected]f2a893c2011-01-05 09:38:07521 DCHECK(CalledOnValidThread());
[email protected]985655a2011-02-23 09:54:25522 if (!created_browser_policy_connector_) {
523 DCHECK(browser_policy_connector_.get() == NULL);
524 created_browser_policy_connector_ = true;
[email protected]d9ee002c2011-04-27 12:52:54525 browser_policy_connector_.reset(policy::BrowserPolicyConnector::Create());
[email protected]f2a893c2011-01-05 09:38:07526 }
[email protected]985655a2011-02-23 09:54:25527 return browser_policy_connector_.get();
[email protected]f2a893c2011-01-05 09:38:07528}
529
[email protected]e13ad79b2010-07-22 21:36:50530IconManager* BrowserProcessImpl::icon_manager() {
531 DCHECK(CalledOnValidThread());
532 if (!created_icon_manager_)
533 CreateIconManager();
534 return icon_manager_.get();
535}
536
537ThumbnailGenerator* BrowserProcessImpl::GetThumbnailGenerator() {
538 return &thumbnail_generator_;
539}
540
541AutomationProviderList* BrowserProcessImpl::InitAutomationProviderList() {
542 DCHECK(CalledOnValidThread());
543 if (automation_provider_list_.get() == NULL) {
544 automation_provider_list_.reset(AutomationProviderList::GetInstance());
545 }
546 return automation_provider_list_.get();
547}
548
[email protected]5613126e2011-01-31 15:27:55549void BrowserProcessImpl::InitDevToolsHttpProtocolHandler(
[email protected]01000cf12011-02-04 11:39:22550 const std::string& ip,
[email protected]5613126e2011-01-31 15:27:55551 int port,
552 const std::string& frontend_url) {
[email protected]e13ad79b2010-07-22 21:36:50553 DCHECK(CalledOnValidThread());
[email protected]5613126e2011-01-31 15:27:55554 devtools_http_handler_ =
[email protected]01000cf12011-02-04 11:39:22555 DevToolsHttpProtocolHandler::Start(ip,
556 port,
[email protected]9678cb42011-01-31 18:49:42557 frontend_url,
558 new BrowserListTabContentsProvider());
[email protected]5613126e2011-01-31 15:27:55559}
560
561void BrowserProcessImpl::InitDevToolsLegacyProtocolHandler(int port) {
562 DCHECK(CalledOnValidThread());
563 devtools_legacy_handler_ = DevToolsProtocolHandler::Start(port);
[email protected]e13ad79b2010-07-22 21:36:50564}
565
566bool BrowserProcessImpl::IsShuttingDown() {
567 DCHECK(CalledOnValidThread());
568 return did_start_ && 0 == module_ref_count_;
569}
570
initial.commit09911bf2008-07-26 23:55:29571printing::PrintJobManager* BrowserProcessImpl::print_job_manager() {
572 // TODO(abarth): DCHECK(CalledOnValidThread());
[email protected]d8922f22010-05-07 00:57:27573 // http://code.google.com/p/chromium/issues/detail?id=6828
initial.commit09911bf2008-07-26 23:55:29574 // print_job_manager_ is initialized in the constructor and destroyed in the
575 // destructor, so it should always be valid.
576 DCHECK(print_job_manager_.get());
577 return print_job_manager_.get();
578}
579
[email protected]dbeebd52010-11-16 20:34:16580printing::PrintPreviewTabController*
581 BrowserProcessImpl::print_preview_tab_controller() {
582 DCHECK(CalledOnValidThread());
583 if (!print_preview_tab_controller_.get())
584 CreatePrintPreviewTabController();
585 return print_preview_tab_controller_.get();
586}
587
[email protected]68f88b992011-05-07 02:01:39588printing::BackgroundPrintingManager*
589 BrowserProcessImpl::background_printing_manager() {
590 DCHECK(CalledOnValidThread());
591 if (!background_printing_manager_.get())
592 CreateBackgroundPrintingManager();
593 return background_printing_manager_.get();
594}
595
[email protected]e13ad79b2010-07-22 21:36:50596GoogleURLTracker* BrowserProcessImpl::google_url_tracker() {
597 DCHECK(CalledOnValidThread());
598 if (!google_url_tracker_.get())
599 CreateGoogleURLTracker();
600 return google_url_tracker_.get();
601}
602
603IntranetRedirectDetector* BrowserProcessImpl::intranet_redirect_detector() {
604 DCHECK(CalledOnValidThread());
605 if (!intranet_redirect_detector_.get())
606 CreateIntranetRedirectDetector();
607 return intranet_redirect_detector_.get();
608}
609
610const std::string& BrowserProcessImpl::GetApplicationLocale() {
611 DCHECK(!locale_.empty());
612 return locale_;
613}
614
615void BrowserProcessImpl::SetApplicationLocale(const std::string& locale) {
616 locale_ = locale;
617 extension_l10n_util::SetProcessLocale(locale);
618}
619
[email protected]073ed7b2010-09-27 09:20:02620DownloadStatusUpdater* BrowserProcessImpl::download_status_updater() {
621 return &download_status_updater_;
622}
623
[email protected]e13ad79b2010-07-22 21:36:50624base::WaitableEvent* BrowserProcessImpl::shutdown_event() {
625 return shutdown_event_.get();
626}
627
628TabCloseableStateWatcher* BrowserProcessImpl::tab_closeable_state_watcher() {
629 DCHECK(CalledOnValidThread());
630 if (!tab_closeable_state_watcher_.get())
631 CreateTabCloseableStateWatcher();
632 return tab_closeable_state_watcher_.get();
633}
634
[email protected]a7a5e992010-12-09 23:39:51635safe_browsing::ClientSideDetectionService*
636 BrowserProcessImpl::safe_browsing_detection_service() {
637 DCHECK(CalledOnValidThread());
638 if (!created_safe_browsing_detection_service_) {
639 CreateSafeBrowsingDetectionService();
640 }
641 return safe_browsing_detection_service_.get();
642}
643
[email protected]8b08a47f2011-02-25 12:36:37644bool BrowserProcessImpl::plugin_finder_disabled() const {
645 return *plugin_finder_disabled_pref_;
646}
647
[email protected]6618d1d2010-12-15 21:18:47648void BrowserProcessImpl::Observe(NotificationType type,
649 const NotificationSource& source,
650 const NotificationDetails& details) {
651 if (type == NotificationType::APP_TERMINATING) {
652 Profile* profile = ProfileManager::GetDefaultProfile();
653 if (profile) {
654 PrefService* prefs = profile->GetPrefs();
[email protected]2ffc3c6c2011-01-14 12:50:24655 if (prefs->GetBoolean(prefs::kClearSiteDataOnExit) &&
[email protected]6618d1d2010-12-15 21:18:47656 local_state()->GetBoolean(prefs::kClearPluginLSODataEnabled)) {
657 plugin_data_remover_ = new PluginDataRemover();
[email protected]c7d58d62011-01-21 10:27:18658 if (!plugin_data_remover_mime_type().empty())
659 plugin_data_remover_->set_mime_type(plugin_data_remover_mime_type());
660 plugin_data_remover_->StartRemoving(base::Time());
[email protected]6618d1d2010-12-15 21:18:47661 }
662 }
[email protected]e450fa62011-02-01 12:52:56663 } else if (type == NotificationType::PREF_CHANGED) {
664 std::string* pref = Details<std::string>(details).ptr();
665 if (*pref == prefs::kDefaultBrowserSettingEnabled) {
666 if (local_state_->GetBoolean(prefs::kDefaultBrowserSettingEnabled))
667 ShellIntegration::SetAsDefaultBrowser();
[email protected]419a0572011-04-18 22:21:46668 } else if (*pref == prefs::kDisabledSchemes) {
669 ApplyDisabledSchemesPolicy();
[email protected]e450fa62011-02-01 12:52:56670 }
[email protected]6618d1d2010-12-15 21:18:47671 } else {
672 NOTREACHED();
673 }
674}
675
676void BrowserProcessImpl::WaitForPluginDataRemoverToFinish() {
[email protected]c7d58d62011-01-21 10:27:18677 if (plugin_data_remover_.get())
678 plugin_data_remover_->Wait();
[email protected]6618d1d2010-12-15 21:18:47679}
680
[email protected]e13ad79b2010-07-22 21:36:50681#if (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)
682void BrowserProcessImpl::StartAutoupdateTimer() {
683 autoupdate_timer_.Start(
684 base::TimeDelta::FromHours(kUpdateCheckIntervalHours),
685 this,
686 &BrowserProcessImpl::OnAutoupdateTimer);
687}
688#endif
689
[email protected]d6f37fc2011-02-13 23:58:41690ChromeNetLog* BrowserProcessImpl::net_log() {
691 return net_log_.get();
692}
693
[email protected]4ef795df2010-02-03 02:35:08694void BrowserProcessImpl::ClearLocalState(const FilePath& profile_path) {
[email protected]72cfd90f2010-02-06 03:08:04695 webkit_database::DatabaseTracker::ClearLocalState(profile_path);
[email protected]4ef795df2010-02-03 02:35:08696}
697
698bool BrowserProcessImpl::ShouldClearLocalState(FilePath* profile_path) {
699 FilePath user_data_dir;
700 Profile* profile;
701
[email protected]09584972010-07-03 00:00:59702 // Check for the existence of a profile manager. When quitting early,
[email protected]ed0cf562010-02-05 22:50:41703 // e.g. because another chrome instance is running, or when invoked with
704 // options such as --uninstall or --try-chrome-again=0, the profile manager
705 // does not exist yet.
706 if (!profile_manager_.get())
707 return false;
708
[email protected]4ef795df2010-02-03 02:35:08709 PathService::Get(chrome::DIR_USER_DATA, &user_data_dir);
710 profile = profile_manager_->GetDefaultProfile(user_data_dir);
[email protected]7bfc674322010-03-05 00:20:57711 if (!profile)
712 return false;
[email protected]4ef795df2010-02-03 02:35:08713 *profile_path = profile->GetPath();
714 return profile->GetPrefs()->GetBoolean(prefs::kClearSiteDataOnExit);
715}
716
initial.commit09911bf2008-07-26 23:55:29717void BrowserProcessImpl::CreateResourceDispatcherHost() {
718 DCHECK(!created_resource_dispatcher_host_ &&
719 resource_dispatcher_host_.get() == NULL);
720 created_resource_dispatcher_host_ = true;
721
[email protected]214538842011-04-01 18:47:24722 // UserScriptListener will delete itself.
723 ResourceQueue::DelegateSet resource_queue_delegates;
724 resource_queue_delegates.insert(new UserScriptListener());
725
726 resource_dispatcher_host_.reset(
727 new ResourceDispatcherHost(resource_queue_delegates));
initial.commit09911bf2008-07-26 23:55:29728 resource_dispatcher_host_->Initialize();
729}
730
731void BrowserProcessImpl::CreateMetricsService() {
732 DCHECK(!created_metrics_service_ && metrics_service_.get() == NULL);
733 created_metrics_service_ = true;
734
735 metrics_service_.reset(new MetricsService);
736}
737
738void BrowserProcessImpl::CreateIOThread() {
739 DCHECK(!created_io_thread_ && io_thread_.get() == NULL);
740 created_io_thread_ = true;
741
742 // Prior to starting the io thread, we create the plugin service as
743 // it is predominantly used from the io thread, but must be created
744 // on the main thread. The service ctor is inexpensive and does not
745 // invoke the io_thread() accessor.
746 PluginService::GetInstance();
747
[email protected]753efc42010-03-09 19:52:16748#if defined(USE_X11)
[email protected]4c3cd7412009-04-22 17:56:06749 // The lifetime of the BACKGROUND_X11 thread is a subset of the IO thread so
750 // we start it now.
751 scoped_ptr<base::Thread> background_x11_thread(
[email protected]d04e7662010-10-10 22:24:48752 new BrowserProcessSubThread(BrowserThread::BACKGROUND_X11));
[email protected]4c3cd7412009-04-22 17:56:06753 if (!background_x11_thread->Start())
754 return;
755 background_x11_thread_.swap(background_x11_thread);
756#endif
757
[email protected]3ce02412011-03-01 12:01:15758 scoped_ptr<IOThread> thread(new IOThread(
759 local_state(), net_log_.get(), extension_event_router_forwarder_.get()));
[email protected]ab820df2008-08-26 05:55:10760 base::Thread::Options options;
761 options.message_loop_type = MessageLoop::TYPE_IO;
762 if (!thread->StartWithOptions(options))
initial.commit09911bf2008-07-26 23:55:29763 return;
764 io_thread_.swap(thread);
765}
766
767void BrowserProcessImpl::CreateFileThread() {
768 DCHECK(!created_file_thread_ && file_thread_.get() == NULL);
769 created_file_thread_ = true;
770
[email protected]ab820df2008-08-26 05:55:10771 scoped_ptr<base::Thread> thread(
[email protected]d04e7662010-10-10 22:24:48772 new BrowserProcessSubThread(BrowserThread::FILE));
[email protected]a1db3842008-09-17 22:04:06773 base::Thread::Options options;
[email protected]9e549b582009-02-05 21:13:39774#if defined(OS_WIN)
775 // On Windows, the FILE thread needs to be have a UI message loop which pumps
776 // messages in such a way that Google Update can communicate back to us.
[email protected]a1db3842008-09-17 22:04:06777 options.message_loop_type = MessageLoop::TYPE_UI;
[email protected]9e549b582009-02-05 21:13:39778#else
779 options.message_loop_type = MessageLoop::TYPE_IO;
780#endif
[email protected]a1db3842008-09-17 22:04:06781 if (!thread->StartWithOptions(options))
initial.commit09911bf2008-07-26 23:55:29782 return;
783 file_thread_.swap(thread);
784}
785
[email protected]2d14b3732011-05-10 16:48:44786#if defined(OS_CHROMEOS)
787void BrowserProcessImpl::CreateWebSocketProxyThread() {
788 DCHECK(!created_web_socket_proxy_thread_);
789 DCHECK(web_socket_proxy_thread_.get() == NULL);
790 created_web_socket_proxy_thread_ = true;
791
792 scoped_ptr<base::Thread> thread(
793 new BrowserProcessSubThread(BrowserThread::WEB_SOCKET_PROXY));
794 base::Thread::Options options;
795 options.message_loop_type = MessageLoop::TYPE_IO;
796 if (!thread->StartWithOptions(options))
797 return;
798 web_socket_proxy_thread_.swap(thread);
799}
800#endif
801
initial.commit09911bf2008-07-26 23:55:29802void BrowserProcessImpl::CreateDBThread() {
803 DCHECK(!created_db_thread_ && db_thread_.get() == NULL);
804 created_db_thread_ = true;
805
[email protected]ab820df2008-08-26 05:55:10806 scoped_ptr<base::Thread> thread(
[email protected]d04e7662010-10-10 22:24:48807 new BrowserProcessSubThread(BrowserThread::DB));
initial.commit09911bf2008-07-26 23:55:29808 if (!thread->Start())
809 return;
810 db_thread_.swap(thread);
811}
812
[email protected]914511712009-11-23 19:42:33813void BrowserProcessImpl::CreateProcessLauncherThread() {
814 DCHECK(!created_process_launcher_thread_ && !process_launcher_thread_.get());
815 created_process_launcher_thread_ = true;
816
817 scoped_ptr<base::Thread> thread(
[email protected]d04e7662010-10-10 22:24:48818 new BrowserProcessSubThread(BrowserThread::PROCESS_LAUNCHER));
[email protected]914511712009-11-23 19:42:33819 if (!thread->Start())
820 return;
821 process_launcher_thread_.swap(thread);
822}
823
[email protected]875ee822010-05-18 20:58:01824void BrowserProcessImpl::CreateCacheThread() {
825 DCHECK(!created_cache_thread_ && !cache_thread_.get());
826 created_cache_thread_ = true;
827
828 scoped_ptr<base::Thread> thread(
[email protected]75096332010-11-09 03:28:13829 new BrowserThread(BrowserThread::CACHE));
[email protected]875ee822010-05-18 20:58:01830 base::Thread::Options options;
831 options.message_loop_type = MessageLoop::TYPE_IO;
832 if (!thread->StartWithOptions(options))
833 return;
834 cache_thread_.swap(thread);
835}
836
[email protected]7a31f7c2011-03-21 23:22:04837void BrowserProcessImpl::CreateGpuThread() {
838 DCHECK(!created_gpu_thread_ && !gpu_thread_.get());
839 created_gpu_thread_ = true;
840
841 scoped_ptr<base::Thread> thread(new BrowserThread(BrowserThread::GPU));
842
843 base::Thread::Options options;
844#if defined(OS_WIN)
845 // On Windows the GPU thread needs to pump the compositor child window's
846 // message loop. TODO(apatrick): make this an IO thread if / when we get rid
847 // of this child window. Unfortunately it might always be necessary for
848 // Windows XP because we cannot share the backing store textures between
849 // processes.
850 options.message_loop_type = MessageLoop::TYPE_UI;
851#else
852 options.message_loop_type = MessageLoop::TYPE_IO;
853#endif
854
855 if (!thread->StartWithOptions(options))
856 return;
857 gpu_thread_.swap(thread);
858}
859
[email protected]0b565182011-03-02 18:11:15860void BrowserProcessImpl::CreateWatchdogThread() {
861 DCHECK(!created_watchdog_thread_ && watchdog_thread_.get() == NULL);
862 created_watchdog_thread_ = true;
863
864 scoped_ptr<WatchDogThread> thread(new WatchDogThread());
865 if (!thread->Start())
866 return;
867 watchdog_thread_.swap(thread);
868}
869
initial.commit09911bf2008-07-26 23:55:29870void BrowserProcessImpl::CreateProfileManager() {
871 DCHECK(!created_profile_manager_ && profile_manager_.get() == NULL);
872 created_profile_manager_ = true;
873
874 profile_manager_.reset(new ProfileManager());
875}
876
877void BrowserProcessImpl::CreateLocalState() {
878 DCHECK(!created_local_state_ && local_state_.get() == NULL);
879 created_local_state_ = true;
880
[email protected]b9636002009-03-04 00:05:25881 FilePath local_state_path;
initial.commit09911bf2008-07-26 23:55:29882 PathService::Get(chrome::FILE_LOCAL_STATE, &local_state_path);
[email protected]f2d1f612010-12-09 15:10:17883 local_state_.reset(
884 PrefService::CreatePrefService(local_state_path, NULL, NULL));
[email protected]492d2142010-09-10 13:55:18885
[email protected]caf63aea2011-04-26 11:04:10886 // Initialize the prefs of the local state.
887 browser::RegisterLocalState(local_state_.get());
888
[email protected]2a7e7c152010-10-01 20:12:09889 pref_change_registrar_.Init(local_state_.get());
890
[email protected]f16b9662011-04-27 10:06:07891 print_job_manager_->InitOnUIThread(local_state_.get());
[email protected]e450fa62011-02-01 12:52:56892
893 // Initialize the notification for the default browser setting policy.
894 local_state_->RegisterBooleanPref(prefs::kDefaultBrowserSettingEnabled,
895 false);
896 if (local_state_->IsManagedPreference(prefs::kDefaultBrowserSettingEnabled)) {
897 if (local_state_->GetBoolean(prefs::kDefaultBrowserSettingEnabled))
898 ShellIntegration::SetAsDefaultBrowser();
899 }
900 pref_change_registrar_.Add(prefs::kDefaultBrowserSettingEnabled, this);
[email protected]8b08a47f2011-02-25 12:36:37901
902 // Initialize the preference for the plugin finder policy.
903 // This preference is only needed on the IO thread so make it available there.
904 local_state_->RegisterBooleanPref(prefs::kDisablePluginFinder, false);
905 plugin_finder_disabled_pref_.Init(prefs::kDisablePluginFinder,
906 local_state_.get(), NULL);
907 plugin_finder_disabled_pref_.MoveToThread(BrowserThread::IO);
[email protected]419a0572011-04-18 22:21:46908
[email protected]b99c41c2011-04-27 15:18:48909 // This is observed by ChildProcessSecurityPolicy, which lives in content/
910 // though, so it can't register itself.
[email protected]419a0572011-04-18 22:21:46911 local_state_->RegisterListPref(prefs::kDisabledSchemes);
[email protected]b99c41c2011-04-27 15:18:48912 pref_change_registrar_.Add(prefs::kDisabledSchemes, this);
[email protected]419a0572011-04-18 22:21:46913 ApplyDisabledSchemesPolicy();
[email protected]fd6159a2010-09-03 09:38:39914}
initial.commit09911bf2008-07-26 23:55:29915
initial.commit09911bf2008-07-26 23:55:29916void BrowserProcessImpl::CreateIconManager() {
917 DCHECK(!created_icon_manager_ && icon_manager_.get() == NULL);
918 created_icon_manager_ = true;
919 icon_manager_.reset(new IconManager);
920}
921
[email protected]40ecc902009-03-16 13:42:47922void BrowserProcessImpl::CreateDevToolsManager() {
[email protected]73ee01522009-06-05 10:13:44923 DCHECK(devtools_manager_.get() == NULL);
[email protected]40ecc902009-03-16 13:42:47924 created_devtools_manager_ = true;
[email protected]73ee01522009-06-05 10:13:44925 devtools_manager_ = new DevToolsManager();
[email protected]40ecc902009-03-16 13:42:47926}
927
[email protected]8b8e7c92010-08-19 18:05:56928void BrowserProcessImpl::CreateSidebarManager() {
929 DCHECK(sidebar_manager_.get() == NULL);
930 created_sidebar_manager_ = true;
931 sidebar_manager_ = new SidebarManager();
932}
933
initial.commit09911bf2008-07-26 23:55:29934void BrowserProcessImpl::CreateGoogleURLTracker() {
935 DCHECK(google_url_tracker_.get() == NULL);
936 scoped_ptr<GoogleURLTracker> google_url_tracker(new GoogleURLTracker);
937 google_url_tracker_.swap(google_url_tracker);
938}
[email protected]6641bf662009-08-21 00:34:09939
[email protected]c4ff4952010-01-08 19:12:47940void BrowserProcessImpl::CreateIntranetRedirectDetector() {
941 DCHECK(intranet_redirect_detector_.get() == NULL);
942 scoped_ptr<IntranetRedirectDetector> intranet_redirect_detector(
943 new IntranetRedirectDetector);
944 intranet_redirect_detector_.swap(intranet_redirect_detector);
945}
946
[email protected]29672ab2009-10-30 03:44:03947void BrowserProcessImpl::CreateNotificationUIManager() {
948 DCHECK(notification_ui_manager_.get() == NULL);
[email protected]b0b2a3dd2011-01-06 00:30:05949 notification_ui_manager_.reset(NotificationUIManager::Create(local_state()));
950
[email protected]29672ab2009-10-30 03:44:03951 created_notification_ui_manager_ = true;
952}
953
[email protected]0b4d3382010-07-14 16:13:04954void BrowserProcessImpl::CreateTabCloseableStateWatcher() {
955 DCHECK(tab_closeable_state_watcher_.get() == NULL);
956 tab_closeable_state_watcher_.reset(TabCloseableStateWatcher::Create());
957}
958
[email protected]dbeebd52010-11-16 20:34:16959void BrowserProcessImpl::CreatePrintPreviewTabController() {
960 DCHECK(print_preview_tab_controller_.get() == NULL);
961 print_preview_tab_controller_ = new printing::PrintPreviewTabController();
962}
963
[email protected]68f88b992011-05-07 02:01:39964void BrowserProcessImpl::CreateBackgroundPrintingManager() {
965 DCHECK(background_printing_manager_.get() == NULL);
966 background_printing_manager_.reset(new printing::BackgroundPrintingManager());
967}
968
[email protected]a7a5e992010-12-09 23:39:51969void BrowserProcessImpl::CreateSafeBrowsingDetectionService() {
970 DCHECK(safe_browsing_detection_service_.get() == NULL);
971 // Set this flag to true so that we don't retry indefinitely to
972 // create the service class if there was an error.
973 created_safe_browsing_detection_service_ = true;
974
975 FilePath model_file_path;
976 Profile* profile = profile_manager() ?
977 profile_manager()->GetDefaultProfile() : NULL;
978 if (IsSafeBrowsingDetectionServiceEnabled() &&
979 PathService::Get(chrome::DIR_USER_DATA, &model_file_path) &&
980 profile && profile->GetRequestContext()) {
981 safe_browsing_detection_service_.reset(
982 safe_browsing::ClientSideDetectionService::Create(
983 model_file_path.Append(chrome::kSafeBrowsingPhishingModelFilename),
984 profile->GetRequestContext()));
985 }
986}
987
988bool BrowserProcessImpl::IsSafeBrowsingDetectionServiceEnabled() {
989 // The safe browsing client-side detection is enabled only if the switch is
[email protected]42930de42011-01-13 23:26:28990 // enabled and when safe browsing related stats is allowed to be collected.
[email protected]838dd914a2011-05-09 02:50:58991 // For now we only enable client-side detection on the canary, dev and beta
992 // channel.
[email protected]d081d192011-04-01 02:33:24993#ifdef OS_CHROMEOS
994 return false;
995#else
[email protected]838dd914a2011-05-09 02:50:58996 std::string channel = platform_util::GetVersionStringModifier();
[email protected]d081d192011-04-01 02:33:24997 return !CommandLine::ForCurrentProcess()->HasSwitch(
998 switches::kDisableClientSidePhishingDetection) &&
[email protected]42930de42011-01-13 23:26:28999 resource_dispatcher_host()->safe_browsing_service() &&
[email protected]838dd914a2011-05-09 02:50:581000 resource_dispatcher_host()->safe_browsing_service()->CanReportStats() &&
1001 (channel == "beta" || channel == "dev" || channel == "canary");
[email protected]d081d192011-04-01 02:33:241002#endif
[email protected]a7a5e992010-12-09 23:39:511003}
1004
[email protected]419a0572011-04-18 22:21:461005void BrowserProcessImpl::ApplyDisabledSchemesPolicy() {
1006 std::set<std::string> schemes;
[email protected]b99c41c2011-04-27 15:18:481007 const ListValue* scheme_list = local_state_->GetList(prefs::kDisabledSchemes);
1008 for (ListValue::const_iterator iter = scheme_list->begin();
1009 iter != scheme_list->end(); ++iter) {
[email protected]419a0572011-04-18 22:21:461010 std::string scheme;
1011 if ((*iter)->GetAsString(&scheme))
1012 schemes.insert(scheme);
1013 }
1014 ChildProcessSecurityPolicy::GetInstance()->RegisterDisabledSchemes(schemes);
1015}
1016
[email protected]6641bf662009-08-21 00:34:091017// The BrowserProcess object must outlive the file thread so we use traits
1018// which don't do any management.
[email protected]c56428f22010-06-16 02:17:231019DISABLE_RUNNABLE_METHOD_REFCOUNT(BrowserProcessImpl);
[email protected]6641bf662009-08-21 00:34:091020
[email protected]d55aaa132009-09-28 21:08:041021#if defined(IPC_MESSAGE_LOG_ENABLED)
1022
1023void BrowserProcessImpl::SetIPCLoggingEnabled(bool enable) {
1024 // First enable myself.
1025 if (enable)
[email protected]8e8bb6d2010-12-13 08:18:551026 IPC::Logging::GetInstance()->Enable();
[email protected]d55aaa132009-09-28 21:08:041027 else
[email protected]8e8bb6d2010-12-13 08:18:551028 IPC::Logging::GetInstance()->Disable();
[email protected]d55aaa132009-09-28 21:08:041029
1030 // Now tell subprocesses. Messages to ChildProcess-derived
1031 // processes must be done on the IO thread.
1032 io_thread()->message_loop()->PostTask
1033 (FROM_HERE,
1034 NewRunnableMethod(
1035 this,
1036 &BrowserProcessImpl::SetIPCLoggingEnabledForChildProcesses,
1037 enable));
1038
1039 // Finally, tell the renderers which don't derive from ChildProcess.
1040 // Messages to the renderers must be done on the UI (main) thread.
[email protected]019191a2009-10-02 20:37:271041 for (RenderProcessHost::iterator i(RenderProcessHost::AllHostsIterator());
1042 !i.IsAtEnd(); i.Advance())
[email protected]ff47b2962011-03-07 23:51:491043 i.GetCurrentValue()->Send(new ChildProcessMsg_SetIPCLoggingEnabled(enable));
[email protected]d55aaa132009-09-28 21:08:041044}
1045
1046// Helper for SetIPCLoggingEnabled.
1047void BrowserProcessImpl::SetIPCLoggingEnabledForChildProcesses(bool enabled) {
[email protected]d04e7662010-10-10 22:24:481048 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
[email protected]d55aaa132009-09-28 21:08:041049
[email protected]d27893f62010-07-03 05:47:421050 BrowserChildProcessHost::Iterator i; // default constr references a singleton
[email protected]34cf97d2009-09-29 22:46:111051 while (!i.Done()) {
[email protected]ff47b2962011-03-07 23:51:491052 i->Send(new ChildProcessMsg_SetIPCLoggingEnabled(enabled));
[email protected]34cf97d2009-09-29 22:46:111053 ++i;
[email protected]d55aaa132009-09-28 21:08:041054 }
1055}
1056
1057#endif // IPC_MESSAGE_LOG_ENABLED
1058
[email protected]3cdacd42010-04-30 18:55:531059// Mac is currently not supported.
1060#if (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)
[email protected]bd48c2b02010-04-09 20:32:421061
1062bool BrowserProcessImpl::CanAutorestartForUpdate() const {
1063 // Check if browser is in the background and if it needs to be restarted to
1064 // apply a pending update.
[email protected]c10fa3952010-08-24 16:52:531065 return BrowserList::size() == 0 && BrowserList::WillKeepAlive() &&
[email protected]815856722011-04-13 17:19:191066 upgrade_util::IsUpdatePendingRestart();
[email protected]bd48c2b02010-04-09 20:32:421067}
1068
[email protected]5c08f222010-09-22 09:37:211069// Switches to add when auto-restarting Chrome.
[email protected]6c10c972010-08-11 04:15:471070const char* const kSwitchesToAddOnAutorestart[] = {
[email protected]f9a06842010-08-21 00:32:401071 switches::kNoStartupWindow
[email protected]bd48c2b02010-04-09 20:32:421072};
1073
1074void BrowserProcessImpl::RestartPersistentInstance() {
1075 CommandLine* old_cl = CommandLine::ForCurrentProcess();
[email protected]3cdacd42010-04-30 18:55:531076 scoped_ptr<CommandLine> new_cl(new CommandLine(old_cl->GetProgram()));
[email protected]bd48c2b02010-04-09 20:32:421077
1078 std::map<std::string, CommandLine::StringType> switches =
1079 old_cl->GetSwitches();
1080
[email protected]5c08f222010-09-22 09:37:211081 switches::RemoveSwitchesForAutostart(&switches);
[email protected]bd48c2b02010-04-09 20:32:421082
1083 // Append the rest of the switches (along with their values, if any)
1084 // to the new command line
1085 for (std::map<std::string, CommandLine::StringType>::const_iterator i =
1086 switches.begin(); i != switches.end(); ++i) {
1087 CommandLine::StringType switch_value = i->second;
1088 if (switch_value.length() > 0) {
[email protected]05076ba22010-07-30 05:59:571089 new_cl->AppendSwitchNative(i->first, i->second);
[email protected]bd48c2b02010-04-09 20:32:421090 } else {
[email protected]3cdacd42010-04-30 18:55:531091 new_cl->AppendSwitch(i->first);
[email protected]bd48c2b02010-04-09 20:32:421092 }
1093 }
1094
[email protected]6c10c972010-08-11 04:15:471095 // Ensure that our desired switches are set on the new process.
[email protected]5c08f222010-09-22 09:37:211096 for (size_t i = 0; i < arraysize(kSwitchesToAddOnAutorestart); ++i) {
[email protected]6c10c972010-08-11 04:15:471097 if (!new_cl->HasSwitch(kSwitchesToAddOnAutorestart[i]))
1098 new_cl->AppendSwitch(kSwitchesToAddOnAutorestart[i]);
1099 }
[email protected]bd48c2b02010-04-09 20:32:421100
[email protected]3cdacd42010-04-30 18:55:531101 DLOG(WARNING) << "Shutting down current instance of the browser.";
1102 BrowserList::CloseAllBrowsersAndExit();
1103
1104 // Transfer ownership to Upgrade.
[email protected]815856722011-04-13 17:19:191105 upgrade_util::SetNewCommandLine(new_cl.release());
[email protected]bd48c2b02010-04-09 20:32:421106}
1107
1108void BrowserProcessImpl::OnAutoupdateTimer() {
1109 if (CanAutorestartForUpdate()) {
[email protected]3cdacd42010-04-30 18:55:531110 DLOG(WARNING) << "Detected update. Restarting browser.";
[email protected]bd48c2b02010-04-09 20:32:421111 RestartPersistentInstance();
1112 }
1113}
1114
[email protected]3cdacd42010-04-30 18:55:531115#endif // (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)