1 // Copyright 2014 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 "extensions/shell/browser/shell_browser_main_parts.h" 6 7 #include "base/command_line.h" 8 #include "base/run_loop.h" 9 #include "components/keyed_service/content/browser_context_dependency_manager.h" 10 #include "components/omaha_query_params/omaha_query_params.h" 11 #include "content/public/browser/child_process_security_policy.h" 12 #include "content/public/browser/context_factory.h" 13 #include "content/public/common/result_codes.h" 14 #include "content/shell/browser/shell_devtools_delegate.h" 15 #include "content/shell/browser/shell_net_log.h" 16 #include "extensions/browser/app_window/app_window_client.h" 17 #include "extensions/browser/browser_context_keyed_service_factories.h" 18 #include "extensions/browser/extension_system.h" 19 #include "extensions/common/constants.cc" 20 #include "extensions/shell/browser/shell_browser_context.h" 21 #include "extensions/shell/browser/shell_browser_main_delegate.h" 22 #include "extensions/shell/browser/shell_desktop_controller.h" 23 #include "extensions/shell/browser/shell_device_client.h" 24 #include "extensions/shell/browser/shell_extension_system.h" 25 #include "extensions/shell/browser/shell_extension_system_factory.h" 26 #include "extensions/shell/browser/shell_extensions_browser_client.h" 27 #include "extensions/shell/browser/shell_omaha_query_params_delegate.h" 28 #include "extensions/shell/common/shell_extensions_client.h" 29 #include "extensions/shell/common/switches.h" 30 #include "ui/aura/env.h" 31 #include "ui/aura/window_tree_host.h" 32 #include "ui/base/ime/input_method_initializer.h" 33 #include "ui/base/resource/resource_bundle.h" 34 35 #if !defined(OS_ANDROID) && !defined(OS_IOS) 36 #include "components/storage_monitor/storage_monitor.h" 37 #endif 38 39 #if defined(OS_CHROMEOS) 40 #include "chromeos/audio/cras_audio_handler.h" 41 #include "chromeos/dbus/dbus_thread_manager.h" 42 #include "chromeos/network/network_handler.h" 43 #include "extensions/shell/browser/shell_audio_controller_chromeos.h" 44 #include "extensions/shell/browser/shell_network_controller_chromeos.h" 45 #endif 46 47 #if !defined(DISABLE_NACL) 48 #include "components/nacl/browser/nacl_browser.h" 49 #include "components/nacl/browser/nacl_process_host.h" 50 #include "content/public/browser/browser_thread.h" 51 #include "extensions/shell/browser/shell_nacl_browser_delegate.h" 52 #endif 53 54 using content::BrowserContext; 55 56 namespace extensions { 57 58 ShellBrowserMainParts::ShellBrowserMainParts( 59 const content::MainFunctionParams& parameters, 60 ShellBrowserMainDelegate* browser_main_delegate) 61 : extension_system_(NULL), 62 parameters_(parameters), 63 run_message_loop_(true), 64 browser_main_delegate_(browser_main_delegate) { 65 } 66 67 ShellBrowserMainParts::~ShellBrowserMainParts() { 68 } 69 70 void ShellBrowserMainParts::PreMainMessageLoopStart() { 71 // TODO(jamescook): Initialize touch here? 72 } 73 74 void ShellBrowserMainParts::PostMainMessageLoopStart() { 75 #if defined(OS_CHROMEOS) 76 // Perform initialization of D-Bus objects here rather than in the below 77 // helper classes so those classes' tests can initialize stub versions of the 78 // D-Bus objects. 79 chromeos::DBusThreadManager::Initialize(); 80 81 chromeos::NetworkHandler::Initialize(); 82 network_controller_.reset(new ShellNetworkController( 83 base::CommandLine::ForCurrentProcess()->GetSwitchValueNative( 84 switches::kAppShellPreferredNetwork))); 85 86 chromeos::CrasAudioHandler::Initialize( 87 new ShellAudioController::PrefHandler()); 88 audio_controller_.reset(new ShellAudioController()); 89 #else 90 // Non-Chrome OS platforms are for developer convenience, so use a test IME. 91 ui::InitializeInputMethodForTesting(); 92 #endif 93 } 94 95 void ShellBrowserMainParts::PreEarlyInitialization() { 96 } 97 98 int ShellBrowserMainParts::PreCreateThreads() { 99 // TODO(jamescook): Initialize chromeos::CrosSettings here? 100 101 content::ChildProcessSecurityPolicy::GetInstance()->RegisterWebSafeScheme( 102 kExtensionScheme); 103 content::ChildProcessSecurityPolicy::GetInstance()->RegisterWebSafeScheme( 104 kExtensionResourceScheme); 105 106 // Return no error. 107 return 0; 108 } 109 110 void ShellBrowserMainParts::PreMainMessageLoopRun() { 111 // Initialize our "profile" equivalent. 112 browser_context_.reset(new ShellBrowserContext); 113 114 aura::Env::GetInstance()->set_context_factory(content::GetContextFactory()); 115 116 #if !defined(OS_ANDROID) && !defined(OS_IOS) 117 storage_monitor::StorageMonitor::Create(); 118 #endif 119 120 desktop_controller_.reset(browser_main_delegate_->CreateDesktopController()); 121 122 // NOTE: Much of this is culled from chrome/test/base/chrome_test_suite.cc 123 // TODO(jamescook): Initialize user_manager::UserManager. 124 net_log_.reset(new content::ShellNetLog("app_shell")); 125 126 device_client_.reset(new ShellDeviceClient); 127 128 extensions_client_.reset(new ShellExtensionsClient()); 129 ExtensionsClient::Set(extensions_client_.get()); 130 131 extensions_browser_client_.reset( 132 new ShellExtensionsBrowserClient(browser_context_.get())); 133 ExtensionsBrowserClient::Set(extensions_browser_client_.get()); 134 135 omaha_query_params_delegate_.reset(new ShellOmahaQueryParamsDelegate); 136 omaha_query_params::OmahaQueryParams::SetDelegate( 137 omaha_query_params_delegate_.get()); 138 139 // Create our custom ExtensionSystem first because other 140 // KeyedServices depend on it. 141 // TODO(yoz): Move this after EnsureBrowserContextKeyedServiceFactoriesBuilt. 142 CreateExtensionSystem(); 143 144 // Register additional KeyedService factories here. See 145 // ChromeBrowserMainExtraPartsProfiles for details. 146 EnsureBrowserContextKeyedServiceFactoriesBuilt(); 147 ShellExtensionSystemFactory::GetInstance(); 148 149 BrowserContextDependencyManager::GetInstance()->CreateBrowserContextServices( 150 browser_context_.get()); 151 152 #if !defined(DISABLE_NACL) 153 // Takes ownership. 154 nacl::NaClBrowser::SetDelegate( 155 new ShellNaClBrowserDelegate(browser_context_.get())); 156 content::BrowserThread::PostTask( 157 content::BrowserThread::IO, 158 FROM_HERE, 159 base::Bind(nacl::NaClProcessHost::EarlyStartup)); 160 #endif 161 162 devtools_delegate_.reset( 163 new content::ShellDevToolsDelegate(browser_context_.get())); 164 if (parameters_.ui_task) { 165 // For running browser tests. 166 parameters_.ui_task->Run(); 167 delete parameters_.ui_task; 168 run_message_loop_ = false; 169 } else { 170 browser_main_delegate_->Start(browser_context_.get()); 171 } 172 } 173 174 bool ShellBrowserMainParts::MainMessageLoopRun(int* result_code) { 175 if (!run_message_loop_) 176 return true; 177 // TODO(yoz): just return false here? 178 base::RunLoop run_loop; 179 run_loop.Run(); 180 *result_code = content::RESULT_CODE_NORMAL_EXIT; 181 return true; 182 } 183 184 void ShellBrowserMainParts::PostMainMessageLoopRun() { 185 browser_main_delegate_->Shutdown(); 186 187 BrowserContextDependencyManager::GetInstance()->DestroyBrowserContextServices( 188 browser_context_.get()); 189 extension_system_ = NULL; 190 ExtensionsBrowserClient::Set(NULL); 191 extensions_browser_client_.reset(); 192 browser_context_.reset(); 193 194 desktop_controller_.reset(); 195 196 #if !defined(OS_ANDROID) && !defined(OS_IOS) 197 storage_monitor::StorageMonitor::Destroy(); 198 #endif 199 } 200 201 void ShellBrowserMainParts::PostDestroyThreads() { 202 #if defined(OS_CHROMEOS) 203 audio_controller_.reset(); 204 chromeos::CrasAudioHandler::Shutdown(); 205 network_controller_.reset(); 206 chromeos::NetworkHandler::Shutdown(); 207 chromeos::DBusThreadManager::Shutdown(); 208 #endif 209 } 210 211 void ShellBrowserMainParts::CreateExtensionSystem() { 212 DCHECK(browser_context_); 213 extension_system_ = static_cast<ShellExtensionSystem*>( 214 ExtensionSystem::Get(browser_context_.get())); 215 extension_system_->InitForRegularProfile(true); 216 } 217 218 } // namespace extensions 219