blob: 52421fff44bf3f4c188474e5155b2fbc6b422cec [file] [log] [blame]
[email protected]c4ff4952010-01-08 19:12:471// Copyright (c) 2010 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>
8
[email protected]90f39902009-10-03 04:25:379#include "app/clipboard/clipboard.h"
[email protected]a92b8642009-05-05 23:38:5610#include "app/l10n_util.h"
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]ac262c9f2008-10-19 17:45:2114#include "base/thread.h"
[email protected]1c4947f2009-01-15 22:25:1115#include "base/waitable_event.h"
[email protected]0082d7e0d2010-02-27 14:34:1216#include "chrome/browser/appcache/chrome_appcache_service.h"
[email protected]bd48c2b02010-04-09 20:32:4217#include "chrome/browser/browser_list.h"
[email protected]b443cb042009-12-15 22:05:0918#include "chrome/browser/browser_main.h"
[email protected]0ac83682010-01-22 17:46:2719#include "chrome/browser/browser_process_sub_thread.h"
[email protected]ac262c9f2008-10-19 17:45:2120#include "chrome/browser/browser_trial.h"
[email protected]dcddcdb02010-02-23 09:10:1321#include "chrome/browser/child_process_host.h"
initial.commit09911bf2008-07-26 23:55:2922#include "chrome/browser/chrome_thread.h"
[email protected]4ab4b0f2009-02-10 18:54:5023#include "chrome/browser/debugger/debugger_wrapper.h"
[email protected]40ecc902009-03-16 13:42:4724#include "chrome/browser/debugger/devtools_manager.h"
[email protected]b7f05882009-02-22 01:21:5625#include "chrome/browser/download/download_file.h"
[email protected]5ba0a2c2009-02-19 01:19:3426#include "chrome/browser/download/save_file_manager.h"
[email protected]bd48c2b02010-04-09 20:32:4227#include "chrome/browser/first_run.h"
initial.commit09911bf2008-07-26 23:55:2928#include "chrome/browser/google_url_tracker.h"
[email protected]dcefa302009-05-20 00:24:3929#include "chrome/browser/icon_manager.h"
[email protected]4ef795df2010-02-03 02:35:0830#include "chrome/browser/in_process_webkit/dom_storage_context.h"
[email protected]c4ff4952010-01-08 19:12:4731#include "chrome/browser/intranet_redirect_detector.h"
[email protected]0ac83682010-01-22 17:46:2732#include "chrome/browser/io_thread.h"
[email protected]dc6f4962009-02-13 01:25:5033#include "chrome/browser/metrics/metrics_service.h"
[email protected]3530cd92010-06-27 06:22:0134#include "chrome/browser/net/predictor_api.h"
[email protected]d393a0fd2009-05-13 23:32:0135#include "chrome/browser/net/sdch_dictionary_fetcher.h"
[email protected]4ef795df2010-02-03 02:35:0836#include "chrome/browser/net/sqlite_persistent_cookie_store.h"
[email protected]29672ab2009-10-30 03:44:0337#include "chrome/browser/notifications/notification_ui_manager.h"
[email protected]fd49e2d2009-02-20 17:21:3038#include "chrome/browser/plugin_service.h"
[email protected]052313b2010-02-19 09:43:0839#include "chrome/browser/pref_service.h"
[email protected]e06131d2010-02-10 18:40:3340#include "chrome/browser/printing/print_job_manager.h"
initial.commit09911bf2008-07-26 23:55:2941#include "chrome/browser/profile_manager.h"
[email protected]8c8657d62009-01-16 18:31:2642#include "chrome/browser/renderer_host/render_process_host.h"
[email protected]81218f42009-02-05 18:48:0843#include "chrome/browser/renderer_host/resource_dispatcher_host.h"
44#include "chrome/browser/safe_browsing/safe_browsing_service.h"
[email protected]ccb55cf52010-03-06 22:02:0445#include "chrome/browser/status_icons/status_tray_manager.h"
[email protected]4ef795df2010-02-03 02:35:0846#include "chrome/common/chrome_constants.h"
initial.commit09911bf2008-07-26 23:55:2947#include "chrome/common/chrome_paths.h"
48#include "chrome/common/chrome_switches.h"
[email protected]27fbccc2010-03-25 03:00:4949#include "chrome/common/extensions/extension_resource.h"
[email protected]f1b6de22010-03-06 12:13:4750#include "chrome/common/extensions/extension_l10n_util.h"
[email protected]ea587b02010-05-21 15:01:3551#include "chrome/common/json_pref_store.h"
initial.commit09911bf2008-07-26 23:55:2952#include "chrome/common/notification_service.h"
53#include "chrome/common/pref_names.h"
[email protected]4ef795df2010-02-03 02:35:0854#include "chrome/common/url_constants.h"
[email protected]bd48c2b02010-04-09 20:32:4255#include "chrome/installer/util/google_update_constants.h"
[email protected]d55aaa132009-09-28 21:08:0456#include "ipc/ipc_logging.h"
[email protected]4ef795df2010-02-03 02:35:0857#include "webkit/database/database_tracker.h"
[email protected]b112a4c2009-02-01 20:24:0158
59#if defined(OS_WIN)
[email protected]2362e4f2009-05-08 00:34:0560#include "views/focus/view_storage.h"
[email protected]86230b92009-11-23 20:38:3861#endif
62
[email protected]d55aaa132009-09-28 21:08:0463#if defined(IPC_MESSAGE_LOG_ENABLED)
64#include "chrome/common/plugin_messages.h"
65#include "chrome/common/render_messages.h"
66#endif
67
[email protected]3cdacd42010-04-30 18:55:5368#if (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)
69// How often to check if the persistent instance of Chrome needs to restart
70// to install an update.
71static const int kUpdateCheckIntervalHours = 6;
72#endif
73
[email protected]bb975362009-01-21 01:00:2274BrowserProcessImpl::BrowserProcessImpl(const CommandLine& command_line)
initial.commit09911bf2008-07-26 23:55:2975 : created_resource_dispatcher_host_(false),
76 created_metrics_service_(false),
77 created_io_thread_(false),
78 created_file_thread_(false),
79 created_db_thread_(false),
[email protected]914511712009-11-23 19:42:3380 created_process_launcher_thread_(false),
[email protected]875ee822010-05-18 20:58:0181 created_cache_thread_(false),
initial.commit09911bf2008-07-26 23:55:2982 created_profile_manager_(false),
83 created_local_state_(false),
[email protected]b112a4c2009-02-01 20:24:0184 created_icon_manager_(false),
85 created_debugger_wrapper_(false),
[email protected]40ecc902009-03-16 13:42:4786 created_devtools_manager_(false),
[email protected]29672ab2009-10-30 03:44:0387 created_notification_ui_manager_(false),
initial.commit09911bf2008-07-26 23:55:2988 module_ref_count_(0),
[email protected]afd20c022010-06-10 00:48:2089 did_start_(false),
[email protected]1b2db1a2008-08-08 17:46:1390 checked_for_new_frames_(false),
[email protected]6641bf662009-08-21 00:34:0991 using_new_frames_(false),
92 have_inspector_files_(true) {
initial.commit09911bf2008-07-26 23:55:2993 g_browser_process = this;
[email protected]1b8d02f12009-05-05 04:14:1194 clipboard_.reset(new Clipboard);
initial.commit09911bf2008-07-26 23:55:2995 main_notification_service_.reset(new NotificationService);
96
97 // Must be created after the NotificationService.
98 print_job_manager_.reset(new printing::PrintJobManager);
99
[email protected]b797e152009-01-23 16:06:14100 shutdown_event_.reset(new base::WaitableEvent(true, false));
initial.commit09911bf2008-07-26 23:55:29101}
102
103BrowserProcessImpl::~BrowserProcessImpl() {
[email protected]4ef795df2010-02-03 02:35:08104 FilePath profile_path;
105 bool clear_local_state_on_exit;
106
107 // Store the profile path for clearing local state data on exit.
108 clear_local_state_on_exit = ShouldClearLocalState(&profile_path);
109
initial.commit09911bf2008-07-26 23:55:29110 // Delete the AutomationProviderList before NotificationService,
111 // since it may try to unregister notifications
112 // Both NotificationService and AutomationProvider are singleton instances in
113 // the BrowserProcess. Since AutomationProvider may have some active
114 // notification observers, it is essential that it gets destroyed before the
115 // NotificationService. NotificationService won't be destroyed until after
116 // this destructor is run.
117 automation_provider_list_.reset();
118
[email protected]d393a0fd2009-05-13 23:32:01119 // We need to shutdown the SdchDictionaryFetcher as it regularly holds
120 // a pointer to a URLFetcher, and that URLFetcher (upon destruction) will do
121 // a PostDelayedTask onto the IO thread. This shutdown call will both discard
122 // any pending URLFetchers, and avoid creating any more.
123 SdchDictionaryFetcher::Shutdown();
124
[email protected]c4ff4952010-01-08 19:12:47125 // We need to destroy the MetricsService, GoogleURLTracker, and
126 // IntranetRedirectDetector before the io_thread_ gets destroyed, since their
127 // destructors can call the URLFetcher destructor, which does a
128 // PostDelayedTask operation on the IO thread. (The IO thread will handle
129 // that URLFetcher operation before going away.)
initial.commit09911bf2008-07-26 23:55:29130 metrics_service_.reset();
131 google_url_tracker_.reset();
[email protected]c4ff4952010-01-08 19:12:47132 intranet_redirect_detector_.reset();
initial.commit09911bf2008-07-26 23:55:29133
134 // Need to clear profiles (download managers) before the io_thread_.
135 profile_manager_.reset();
136
137 // Debugger must be cleaned up before IO thread and NotificationService.
138 debugger_wrapper_ = NULL;
139
140 if (resource_dispatcher_host_.get()) {
141 // Need to tell Safe Browsing Service that the IO thread is going away
142 // since it cached a pointer to it.
143 if (resource_dispatcher_host()->safe_browsing_service())
144 resource_dispatcher_host()->safe_browsing_service()->ShutDown();
145
146 // Cancel pending requests and prevent new requests.
147 resource_dispatcher_host()->Shutdown();
148 }
149
[email protected]753efc42010-03-09 19:52:16150#if defined(USE_X11)
[email protected]4c3cd7412009-04-22 17:56:06151 // The IO thread must outlive the BACKGROUND_X11 thread.
152 background_x11_thread_.reset();
153#endif
154
initial.commit09911bf2008-07-26 23:55:29155 // Need to stop io_thread_ before resource_dispatcher_host_, since
156 // io_thread_ may still deref ResourceDispatcherHost and handle resource
157 // request before going away.
[email protected]0ac83682010-01-22 17:46:27158 io_thread_.reset();
initial.commit09911bf2008-07-26 23:55:29159
[email protected]875ee822010-05-18 20:58:01160 // The IO thread was the only user of this thread.
161 cache_thread_.reset();
162
[email protected]914511712009-11-23 19:42:33163 // Stop the process launcher thread after the IO thread, in case the IO thread
164 // posted a task to terminate a process on the process launcher thread.
165 process_launcher_thread_.reset();
166
initial.commit09911bf2008-07-26 23:55:29167 // Clean up state that lives on the file_thread_ before it goes away.
168 if (resource_dispatcher_host_.get()) {
169 resource_dispatcher_host()->download_file_manager()->Shutdown();
170 resource_dispatcher_host()->save_file_manager()->Shutdown();
171 }
172
173 // Need to stop the file_thread_ here to force it to process messages in its
174 // message loop from the previous call to shutdown the DownloadFileManager,
175 // SaveFileManager and SessionService.
176 file_thread_.reset();
177
178 // With the file_thread_ flushed, we can release any icon resources.
179 icon_manager_.reset();
180
181 // Need to destroy ResourceDispatcherHost before PluginService and
[email protected]49f28bc72010-02-04 00:10:01182 // SafeBrowsingService, since it caches a pointer to it. This also
183 // causes the webkit thread to terminate.
initial.commit09911bf2008-07-26 23:55:29184 resource_dispatcher_host_.reset();
185
186 // Wait for the pending print jobs to finish.
187 print_job_manager_->OnQuit();
188 print_job_manager_.reset();
189
initial.commit09911bf2008-07-26 23:55:29190 // Now OK to destroy NotificationService.
191 main_notification_service_.reset();
192
[email protected]49f28bc72010-02-04 00:10:01193 // Prior to clearing local state, we want to complete tasks pending
194 // on the db thread too.
195 db_thread_.reset();
196
197 // At this point, no render process exist and the file, io, db, and
198 // webkit threads in this process have all terminated, so it's safe
199 // to access local state data such as cookies, database, or local storage.
200 if (clear_local_state_on_exit)
201 ClearLocalState(profile_path);
202
initial.commit09911bf2008-07-26 23:55:29203 g_browser_process = NULL;
204}
205
[email protected]295039bd2008-08-15 04:32:57206// Send a QuitTask to the given MessageLoop.
207static void PostQuit(MessageLoop* message_loop) {
208 message_loop->PostTask(FROM_HERE, new MessageLoop::QuitTask());
209}
initial.commit09911bf2008-07-26 23:55:29210
[email protected]b443cb042009-12-15 22:05:09211unsigned int BrowserProcessImpl::AddRefModule() {
212 DCHECK(CalledOnValidThread());
[email protected]afd20c022010-06-10 00:48:20213 did_start_ = true;
[email protected]b443cb042009-12-15 22:05:09214 module_ref_count_++;
215 return module_ref_count_;
216}
217
218unsigned int BrowserProcessImpl::ReleaseModule() {
219 DCHECK(CalledOnValidThread());
[email protected]760d970a2010-05-18 00:39:18220 DCHECK_NE(0u, module_ref_count_);
[email protected]b443cb042009-12-15 22:05:09221 module_ref_count_--;
222 if (0 == module_ref_count_) {
223 MessageLoop::current()->PostTask(
[email protected]34f73fb2010-03-24 20:50:34224 FROM_HERE, NewRunnableFunction(DidEndMainMessageLoop));
[email protected]b443cb042009-12-15 22:05:09225 MessageLoop::current()->Quit();
226 }
227 return module_ref_count_;
228}
229
initial.commit09911bf2008-07-26 23:55:29230void BrowserProcessImpl::EndSession() {
[email protected]b112a4c2009-02-01 20:24:01231#if defined(OS_WIN)
[email protected]d65cab7a2008-08-12 01:25:41232 // Notify we are going away.
[email protected]b797e152009-01-23 16:06:14233 ::SetEvent(shutdown_event_->handle());
[email protected]b112a4c2009-02-01 20:24:01234#endif
[email protected]d65cab7a2008-08-12 01:25:41235
initial.commit09911bf2008-07-26 23:55:29236 // Mark all the profiles as clean.
237 ProfileManager* pm = profile_manager();
238 for (ProfileManager::const_iterator i = pm->begin(); i != pm->end(); ++i)
239 (*i)->MarkAsCleanShutdown();
240
241 // Tell the metrics service it was cleanly shutdown.
242 MetricsService* metrics = g_browser_process->metrics_service();
243 if (metrics && local_state()) {
244 metrics->RecordCleanShutdown();
245
246 metrics->RecordStartOfSessionEnd();
247
248 // MetricsService lazily writes to prefs, force it to write now.
[email protected]6faa0e0d2009-04-28 06:50:36249 local_state()->SavePersistentPrefs();
initial.commit09911bf2008-07-26 23:55:29250 }
251
252 // We must write that the profile and metrics service shutdown cleanly,
253 // otherwise on startup we'll think we crashed. So we block until done and
254 // then proceed with normal shutdown.
255 g_browser_process->file_thread()->message_loop()->PostTask(FROM_HERE,
[email protected]295039bd2008-08-15 04:32:57256 NewRunnableFunction(PostQuit, MessageLoop::current()));
initial.commit09911bf2008-07-26 23:55:29257 MessageLoop::current()->Run();
258}
259
260printing::PrintJobManager* BrowserProcessImpl::print_job_manager() {
261 // TODO(abarth): DCHECK(CalledOnValidThread());
[email protected]d8922f22010-05-07 00:57:27262 // http://code.google.com/p/chromium/issues/detail?id=6828
initial.commit09911bf2008-07-26 23:55:29263 // print_job_manager_ is initialized in the constructor and destroyed in the
264 // destructor, so it should always be valid.
265 DCHECK(print_job_manager_.get());
266 return print_job_manager_.get();
267}
268
[email protected]4ef795df2010-02-03 02:35:08269void BrowserProcessImpl::ClearLocalState(const FilePath& profile_path) {
270 SQLitePersistentCookieStore::ClearLocalState(profile_path.Append(
271 chrome::kCookieFilename));
272 DOMStorageContext::ClearLocalState(profile_path, chrome::kExtensionScheme);
[email protected]72cfd90f2010-02-06 03:08:04273 webkit_database::DatabaseTracker::ClearLocalState(profile_path);
[email protected]10c934052010-02-04 19:58:31274 ChromeAppCacheService::ClearLocalState(profile_path);
[email protected]4ef795df2010-02-03 02:35:08275}
276
277bool BrowserProcessImpl::ShouldClearLocalState(FilePath* profile_path) {
278 FilePath user_data_dir;
279 Profile* profile;
280
[email protected]09584972010-07-03 00:00:59281 // Check for the existence of a profile manager. When quitting early,
[email protected]ed0cf562010-02-05 22:50:41282 // e.g. because another chrome instance is running, or when invoked with
283 // options such as --uninstall or --try-chrome-again=0, the profile manager
284 // does not exist yet.
285 if (!profile_manager_.get())
286 return false;
287
[email protected]4ef795df2010-02-03 02:35:08288 PathService::Get(chrome::DIR_USER_DATA, &user_data_dir);
289 profile = profile_manager_->GetDefaultProfile(user_data_dir);
[email protected]7bfc674322010-03-05 00:20:57290 if (!profile)
291 return false;
[email protected]4ef795df2010-02-03 02:35:08292 *profile_path = profile->GetPath();
293 return profile->GetPrefs()->GetBoolean(prefs::kClearSiteDataOnExit);
294}
295
initial.commit09911bf2008-07-26 23:55:29296void BrowserProcessImpl::CreateResourceDispatcherHost() {
297 DCHECK(!created_resource_dispatcher_host_ &&
298 resource_dispatcher_host_.get() == NULL);
299 created_resource_dispatcher_host_ = true;
300
[email protected]79084c2d2009-11-03 23:12:42301 resource_dispatcher_host_.reset(new ResourceDispatcherHost());
initial.commit09911bf2008-07-26 23:55:29302 resource_dispatcher_host_->Initialize();
303}
304
305void BrowserProcessImpl::CreateMetricsService() {
306 DCHECK(!created_metrics_service_ && metrics_service_.get() == NULL);
307 created_metrics_service_ = true;
308
309 metrics_service_.reset(new MetricsService);
310}
311
312void BrowserProcessImpl::CreateIOThread() {
313 DCHECK(!created_io_thread_ && io_thread_.get() == NULL);
314 created_io_thread_ = true;
315
316 // Prior to starting the io thread, we create the plugin service as
317 // it is predominantly used from the io thread, but must be created
318 // on the main thread. The service ctor is inexpensive and does not
319 // invoke the io_thread() accessor.
320 PluginService::GetInstance();
321
[email protected]753efc42010-03-09 19:52:16322#if defined(USE_X11)
[email protected]4c3cd7412009-04-22 17:56:06323 // The lifetime of the BACKGROUND_X11 thread is a subset of the IO thread so
324 // we start it now.
325 scoped_ptr<base::Thread> background_x11_thread(
326 new BrowserProcessSubThread(ChromeThread::BACKGROUND_X11));
327 if (!background_x11_thread->Start())
328 return;
329 background_x11_thread_.swap(background_x11_thread);
330#endif
331
[email protected]0ac83682010-01-22 17:46:27332 scoped_ptr<IOThread> thread(new IOThread);
[email protected]ab820df2008-08-26 05:55:10333 base::Thread::Options options;
334 options.message_loop_type = MessageLoop::TYPE_IO;
335 if (!thread->StartWithOptions(options))
initial.commit09911bf2008-07-26 23:55:29336 return;
337 io_thread_.swap(thread);
338}
339
340void BrowserProcessImpl::CreateFileThread() {
341 DCHECK(!created_file_thread_ && file_thread_.get() == NULL);
342 created_file_thread_ = true;
343
[email protected]ab820df2008-08-26 05:55:10344 scoped_ptr<base::Thread> thread(
345 new BrowserProcessSubThread(ChromeThread::FILE));
[email protected]a1db3842008-09-17 22:04:06346 base::Thread::Options options;
[email protected]9e549b582009-02-05 21:13:39347#if defined(OS_WIN)
348 // On Windows, the FILE thread needs to be have a UI message loop which pumps
349 // messages in such a way that Google Update can communicate back to us.
[email protected]a1db3842008-09-17 22:04:06350 options.message_loop_type = MessageLoop::TYPE_UI;
[email protected]9e549b582009-02-05 21:13:39351#else
352 options.message_loop_type = MessageLoop::TYPE_IO;
353#endif
[email protected]a1db3842008-09-17 22:04:06354 if (!thread->StartWithOptions(options))
initial.commit09911bf2008-07-26 23:55:29355 return;
356 file_thread_.swap(thread);
[email protected]27fbccc2010-03-25 03:00:49357
358 // ExtensionResource is in chrome/common, so it cannot depend on
359 // chrome/browser, which means it cannot lookup what the File thread is.
360 // We therefore store the thread ID from here so we can validate the proper
361 // thread usage in the ExtensionResource class.
362 ExtensionResource::set_file_thread_id(file_thread_->thread_id());
initial.commit09911bf2008-07-26 23:55:29363}
364
365void BrowserProcessImpl::CreateDBThread() {
366 DCHECK(!created_db_thread_ && db_thread_.get() == NULL);
367 created_db_thread_ = true;
368
[email protected]ab820df2008-08-26 05:55:10369 scoped_ptr<base::Thread> thread(
370 new BrowserProcessSubThread(ChromeThread::DB));
initial.commit09911bf2008-07-26 23:55:29371 if (!thread->Start())
372 return;
373 db_thread_.swap(thread);
374}
375
[email protected]914511712009-11-23 19:42:33376void BrowserProcessImpl::CreateProcessLauncherThread() {
377 DCHECK(!created_process_launcher_thread_ && !process_launcher_thread_.get());
378 created_process_launcher_thread_ = true;
379
380 scoped_ptr<base::Thread> thread(
381 new BrowserProcessSubThread(ChromeThread::PROCESS_LAUNCHER));
382 if (!thread->Start())
383 return;
384 process_launcher_thread_.swap(thread);
385}
386
[email protected]875ee822010-05-18 20:58:01387void BrowserProcessImpl::CreateCacheThread() {
388 DCHECK(!created_cache_thread_ && !cache_thread_.get());
389 created_cache_thread_ = true;
390
391 scoped_ptr<base::Thread> thread(
392 new BrowserProcessSubThread(ChromeThread::CACHE));
393 base::Thread::Options options;
394 options.message_loop_type = MessageLoop::TYPE_IO;
395 if (!thread->StartWithOptions(options))
396 return;
397 cache_thread_.swap(thread);
398}
399
initial.commit09911bf2008-07-26 23:55:29400void BrowserProcessImpl::CreateProfileManager() {
401 DCHECK(!created_profile_manager_ && profile_manager_.get() == NULL);
402 created_profile_manager_ = true;
403
404 profile_manager_.reset(new ProfileManager());
405}
406
407void BrowserProcessImpl::CreateLocalState() {
408 DCHECK(!created_local_state_ && local_state_.get() == NULL);
409 created_local_state_ = true;
410
[email protected]b9636002009-03-04 00:05:25411 FilePath local_state_path;
initial.commit09911bf2008-07-26 23:55:29412 PathService::Get(chrome::FILE_LOCAL_STATE, &local_state_path);
[email protected]d8b08c92010-06-07 13:13:28413 local_state_.reset(PrefService::CreatePrefService(local_state_path));
414 }
initial.commit09911bf2008-07-26 23:55:29415
initial.commit09911bf2008-07-26 23:55:29416void BrowserProcessImpl::CreateIconManager() {
417 DCHECK(!created_icon_manager_ && icon_manager_.get() == NULL);
418 created_icon_manager_ = true;
419 icon_manager_.reset(new IconManager);
420}
421
422void BrowserProcessImpl::CreateDebuggerWrapper(int port) {
423 DCHECK(debugger_wrapper_.get() == NULL);
424 created_debugger_wrapper_ = true;
425
426 debugger_wrapper_ = new DebuggerWrapper(port);
427}
428
[email protected]40ecc902009-03-16 13:42:47429void BrowserProcessImpl::CreateDevToolsManager() {
[email protected]73ee01522009-06-05 10:13:44430 DCHECK(devtools_manager_.get() == NULL);
[email protected]40ecc902009-03-16 13:42:47431 created_devtools_manager_ = true;
[email protected]73ee01522009-06-05 10:13:44432 devtools_manager_ = new DevToolsManager();
[email protected]40ecc902009-03-16 13:42:47433}
434
initial.commit09911bf2008-07-26 23:55:29435void BrowserProcessImpl::CreateGoogleURLTracker() {
436 DCHECK(google_url_tracker_.get() == NULL);
437 scoped_ptr<GoogleURLTracker> google_url_tracker(new GoogleURLTracker);
438 google_url_tracker_.swap(google_url_tracker);
439}
[email protected]6641bf662009-08-21 00:34:09440
[email protected]c4ff4952010-01-08 19:12:47441void BrowserProcessImpl::CreateIntranetRedirectDetector() {
442 DCHECK(intranet_redirect_detector_.get() == NULL);
443 scoped_ptr<IntranetRedirectDetector> intranet_redirect_detector(
444 new IntranetRedirectDetector);
445 intranet_redirect_detector_.swap(intranet_redirect_detector);
446}
447
[email protected]29672ab2009-10-30 03:44:03448void BrowserProcessImpl::CreateNotificationUIManager() {
449 DCHECK(notification_ui_manager_.get() == NULL);
450 notification_ui_manager_.reset(NotificationUIManager::Create());
451 created_notification_ui_manager_ = true;
452}
453
[email protected]f1b6de22010-03-06 12:13:47454void BrowserProcessImpl::SetApplicationLocale(const std::string& locale) {
455 locale_ = locale;
456 extension_l10n_util::SetProcessLocale(locale);
457}
458
[email protected]ccb55cf52010-03-06 22:02:04459void BrowserProcessImpl::CreateStatusTrayManager() {
460 DCHECK(status_tray_manager_.get() == NULL);
461 status_tray_manager_.reset(new StatusTrayManager());
462}
463
[email protected]6641bf662009-08-21 00:34:09464// The BrowserProcess object must outlive the file thread so we use traits
465// which don't do any management.
[email protected]c56428f22010-06-16 02:17:23466DISABLE_RUNNABLE_METHOD_REFCOUNT(BrowserProcessImpl);
[email protected]6641bf662009-08-21 00:34:09467
468void BrowserProcessImpl::CheckForInspectorFiles() {
469 file_thread()->message_loop()->PostTask
470 (FROM_HERE,
471 NewRunnableMethod(this, &BrowserProcessImpl::DoInspectorFilesCheck));
472}
473
[email protected]3cdacd42010-04-30 18:55:53474#if (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)
[email protected]bd48c2b02010-04-09 20:32:42475void BrowserProcessImpl::StartAutoupdateTimer() {
476 autoupdate_timer_.Start(
[email protected]760d970a2010-05-18 00:39:18477 base::TimeDelta::FromHours(kUpdateCheckIntervalHours),
[email protected]bd48c2b02010-04-09 20:32:42478 this,
479 &BrowserProcessImpl::OnAutoupdateTimer);
480}
[email protected]3cdacd42010-04-30 18:55:53481#endif
[email protected]bd48c2b02010-04-09 20:32:42482
[email protected]d55aaa132009-09-28 21:08:04483#if defined(IPC_MESSAGE_LOG_ENABLED)
484
485void BrowserProcessImpl::SetIPCLoggingEnabled(bool enable) {
486 // First enable myself.
487 if (enable)
488 IPC::Logging::current()->Enable();
489 else
490 IPC::Logging::current()->Disable();
491
492 // Now tell subprocesses. Messages to ChildProcess-derived
493 // processes must be done on the IO thread.
494 io_thread()->message_loop()->PostTask
495 (FROM_HERE,
496 NewRunnableMethod(
497 this,
498 &BrowserProcessImpl::SetIPCLoggingEnabledForChildProcesses,
499 enable));
500
501 // Finally, tell the renderers which don't derive from ChildProcess.
502 // Messages to the renderers must be done on the UI (main) thread.
[email protected]019191a2009-10-02 20:37:27503 for (RenderProcessHost::iterator i(RenderProcessHost::AllHostsIterator());
504 !i.IsAtEnd(); i.Advance())
505 i.GetCurrentValue()->Send(new ViewMsg_SetIPCLoggingEnabled(enable));
[email protected]d55aaa132009-09-28 21:08:04506}
507
508// Helper for SetIPCLoggingEnabled.
509void BrowserProcessImpl::SetIPCLoggingEnabledForChildProcesses(bool enabled) {
[email protected]d85cf072009-10-27 03:59:31510 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::IO));
[email protected]d55aaa132009-09-28 21:08:04511
512 ChildProcessHost::Iterator i; // default constr references a singleton
[email protected]34cf97d2009-09-29 22:46:11513 while (!i.Done()) {
514 i->Send(new PluginProcessMsg_SetIPCLoggingEnabled(enabled));
515 ++i;
[email protected]d55aaa132009-09-28 21:08:04516 }
517}
518
519#endif // IPC_MESSAGE_LOG_ENABLED
520
[email protected]6641bf662009-08-21 00:34:09521void BrowserProcessImpl::DoInspectorFilesCheck() {
522 // Runs on FILE thread.
523 DCHECK(file_thread_->message_loop() == MessageLoop::current());
524 bool result = false;
525
526 FilePath inspector_dir;
527 if (PathService::Get(chrome::DIR_INSPECTOR, &inspector_dir)) {
528 result = file_util::PathExists(inspector_dir);
529 }
530
[email protected]308080d2009-11-11 19:19:02531 have_inspector_files_ = result;
[email protected]6641bf662009-08-21 00:34:09532}
[email protected]bd48c2b02010-04-09 20:32:42533
[email protected]3cdacd42010-04-30 18:55:53534// Mac is currently not supported.
535#if (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)
[email protected]bd48c2b02010-04-09 20:32:42536
537bool BrowserProcessImpl::CanAutorestartForUpdate() const {
538 // Check if browser is in the background and if it needs to be restarted to
539 // apply a pending update.
540 return BrowserList::IsInPersistentMode() && Upgrade::IsUpdatePendingRestart();
541}
542
543// Switches enumerated here will be removed when a background instance of
544// Chrome restarts itself. If your key is designed to only be used once,
545// or if it does not make sense when restarting a background instance to
546// pick up an automatic update, be sure to add it to this list.
547const char* const kSwitchesToRemoveOnAutorestart[] = {
548 switches::kApp,
549 switches::kFirstRun,
550 switches::kImport,
551 switches::kImportFromFile,
552 switches::kMakeDefaultBrowser
553};
554
555void BrowserProcessImpl::RestartPersistentInstance() {
556 CommandLine* old_cl = CommandLine::ForCurrentProcess();
[email protected]3cdacd42010-04-30 18:55:53557 scoped_ptr<CommandLine> new_cl(new CommandLine(old_cl->GetProgram()));
[email protected]bd48c2b02010-04-09 20:32:42558
559 std::map<std::string, CommandLine::StringType> switches =
560 old_cl->GetSwitches();
561
562 // Remove the keys that we shouldn't pass through during restart.
[email protected]3cdacd42010-04-30 18:55:53563 for (size_t i = 0; i < arraysize(kSwitchesToRemoveOnAutorestart); i++) {
[email protected]bd48c2b02010-04-09 20:32:42564 switches.erase(kSwitchesToRemoveOnAutorestart[i]);
565 }
566
567 // Append the rest of the switches (along with their values, if any)
568 // to the new command line
569 for (std::map<std::string, CommandLine::StringType>::const_iterator i =
570 switches.begin(); i != switches.end(); ++i) {
571 CommandLine::StringType switch_value = i->second;
572 if (switch_value.length() > 0) {
[email protected]3cdacd42010-04-30 18:55:53573 new_cl->AppendSwitchWithValue(i->first, i->second);
[email protected]bd48c2b02010-04-09 20:32:42574 } else {
[email protected]3cdacd42010-04-30 18:55:53575 new_cl->AppendSwitch(i->first);
[email protected]bd48c2b02010-04-09 20:32:42576 }
577 }
578
[email protected]398206c2010-06-21 01:46:08579 if (!new_cl->HasSwitch(switches::kRestoreBackgroundContents))
580 new_cl->AppendSwitch(switches::kRestoreBackgroundContents);
[email protected]bd48c2b02010-04-09 20:32:42581
[email protected]3cdacd42010-04-30 18:55:53582 DLOG(WARNING) << "Shutting down current instance of the browser.";
583 BrowserList::CloseAllBrowsersAndExit();
584
585 // Transfer ownership to Upgrade.
586 Upgrade::SetNewCommandLine(new_cl.release());
[email protected]bd48c2b02010-04-09 20:32:42587}
588
589void BrowserProcessImpl::OnAutoupdateTimer() {
590 if (CanAutorestartForUpdate()) {
[email protected]3cdacd42010-04-30 18:55:53591 DLOG(WARNING) << "Detected update. Restarting browser.";
[email protected]bd48c2b02010-04-09 20:32:42592 RestartPersistentInstance();
593 }
594}
595
[email protected]3cdacd42010-04-30 18:55:53596#endif // (defined(OS_WIN) || defined(OS_LINUX)) && !defined(OS_CHROMEOS)