OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/extensions/extension_process_manager.h" | 5 #include "extensions/browser/process_manager.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/command_line.h" | 8 #include "base/command_line.h" |
9 #include "base/lazy_instance.h" | 9 #include "base/lazy_instance.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
11 #include "base/message_loop/message_loop.h" | 11 #include "base/message_loop/message_loop.h" |
12 #include "base/metrics/histogram.h" | 12 #include "base/metrics/histogram.h" |
13 #include "base/stl_util.h" | 13 #include "base/stl_util.h" |
14 #include "base/strings/string_number_conversions.h" | 14 #include "base/strings/string_number_conversions.h" |
15 #include "base/time/time.h" | 15 #include "base/time/time.h" |
(...skipping 25 matching lines...) Expand all Loading... |
41 #include "extensions/common/switches.h" | 41 #include "extensions/common/switches.h" |
42 | 42 |
43 #if defined(OS_MACOSX) | 43 #if defined(OS_MACOSX) |
44 #include "chrome/browser/extensions/extension_host_mac.h" | 44 #include "chrome/browser/extensions/extension_host_mac.h" |
45 #endif | 45 #endif |
46 | 46 |
47 using content::BrowserContext; | 47 using content::BrowserContext; |
48 using content::RenderViewHost; | 48 using content::RenderViewHost; |
49 using content::SiteInstance; | 49 using content::SiteInstance; |
50 using content::WebContents; | 50 using content::WebContents; |
51 using extensions::BackgroundInfo; | |
52 using extensions::BackgroundManifestHandler; | |
53 using extensions::Extension; | |
54 using extensions::ExtensionHost; | |
55 using extensions::ExtensionsBrowserClient; | |
56 using extensions::ExtensionSystem; | |
57 | 51 |
| 52 namespace extensions { |
58 class RenderViewHostDestructionObserver; | 53 class RenderViewHostDestructionObserver; |
59 DEFINE_WEB_CONTENTS_USER_DATA_KEY(RenderViewHostDestructionObserver); | 54 } |
| 55 DEFINE_WEB_CONTENTS_USER_DATA_KEY( |
| 56 extensions::RenderViewHostDestructionObserver); |
| 57 |
| 58 namespace extensions { |
60 | 59 |
61 namespace { | 60 namespace { |
62 | 61 |
63 std::string GetExtensionID(RenderViewHost* render_view_host) { | 62 std::string GetExtensionID(RenderViewHost* render_view_host) { |
64 // This works for both apps and extensions because the site has been | 63 // This works for both apps and extensions because the site has been |
65 // normalized to the extension URL for apps. | 64 // normalized to the extension URL for apps. |
66 if (!render_view_host->GetSiteInstance()) | 65 if (!render_view_host->GetSiteInstance()) |
67 return std::string(); | 66 return std::string(); |
68 | 67 |
69 return render_view_host->GetSiteInstance()->GetSiteURL().host(); | 68 return render_view_host->GetSiteInstance()->GetSiteURL().host(); |
70 } | 69 } |
71 | 70 |
72 void OnRenderViewHostUnregistered(BrowserContext* context, | 71 void OnRenderViewHostUnregistered(BrowserContext* context, |
73 RenderViewHost* render_view_host) { | 72 RenderViewHost* render_view_host) { |
74 content::NotificationService::current()->Notify( | 73 content::NotificationService::current()->Notify( |
75 chrome::NOTIFICATION_EXTENSION_VIEW_UNREGISTERED, | 74 chrome::NOTIFICATION_EXTENSION_VIEW_UNREGISTERED, |
76 content::Source<BrowserContext>(context), | 75 content::Source<BrowserContext>(context), |
77 content::Details<RenderViewHost>(render_view_host)); | 76 content::Details<RenderViewHost>(render_view_host)); |
78 } | 77 } |
79 | 78 |
80 // Incognito profiles use this process manager. It is mostly a shim that decides | 79 // Incognito profiles use this process manager. It is mostly a shim that decides |
81 // whether to fall back on the original profile's ExtensionProcessManager based | 80 // whether to fall back on the original profile's ProcessManager based |
82 // on whether a given extension uses "split" or "spanning" incognito behavior. | 81 // on whether a given extension uses "split" or "spanning" incognito behavior. |
83 class IncognitoExtensionProcessManager : public ExtensionProcessManager { | 82 class IncognitoProcessManager : public ProcessManager { |
84 public: | 83 public: |
85 IncognitoExtensionProcessManager(BrowserContext* incognito_context, | 84 IncognitoProcessManager(BrowserContext* incognito_context, |
86 BrowserContext* original_context); | 85 BrowserContext* original_context); |
87 virtual ~IncognitoExtensionProcessManager(); | 86 virtual ~IncognitoProcessManager(); |
88 virtual ExtensionHost* CreateBackgroundHost(const Extension* extension, | 87 virtual ExtensionHost* CreateBackgroundHost(const Extension* extension, |
89 const GURL& url) OVERRIDE; | 88 const GURL& url) OVERRIDE; |
90 virtual SiteInstance* GetSiteInstanceForURL(const GURL& url) OVERRIDE; | 89 virtual SiteInstance* GetSiteInstanceForURL(const GURL& url) OVERRIDE; |
91 | 90 |
92 private: | 91 private: |
93 // Returns true if the extension is allowed to run in incognito mode. | 92 // Returns true if the extension is allowed to run in incognito mode. |
94 bool IsIncognitoEnabled(const Extension* extension); | 93 bool IsIncognitoEnabled(const Extension* extension); |
95 | 94 |
96 ExtensionProcessManager* original_manager_; | 95 ProcessManager* original_manager_; |
97 | 96 |
98 DISALLOW_COPY_AND_ASSIGN(IncognitoExtensionProcessManager); | 97 DISALLOW_COPY_AND_ASSIGN(IncognitoProcessManager); |
99 }; | 98 }; |
100 | 99 |
101 static void CreateBackgroundHostForExtensionLoad( | 100 static void CreateBackgroundHostForExtensionLoad( |
102 ExtensionProcessManager* manager, const Extension* extension) { | 101 ProcessManager* manager, const Extension* extension) { |
103 DVLOG(1) << "CreateBackgroundHostForExtensionLoad"; | 102 DVLOG(1) << "CreateBackgroundHostForExtensionLoad"; |
104 if (BackgroundInfo::HasPersistentBackgroundPage(extension)) | 103 if (BackgroundInfo::HasPersistentBackgroundPage(extension)) |
105 manager->CreateBackgroundHost(extension, | 104 manager->CreateBackgroundHost(extension, |
106 BackgroundInfo::GetBackgroundURL(extension)); | 105 BackgroundInfo::GetBackgroundURL(extension)); |
107 } | 106 } |
108 | 107 |
109 } // namespace | 108 } // namespace |
110 | 109 |
111 class RenderViewHostDestructionObserver | 110 class RenderViewHostDestructionObserver |
112 : public content::WebContentsObserver, | 111 : public content::WebContentsObserver, |
113 public content::WebContentsUserData<RenderViewHostDestructionObserver> { | 112 public content::WebContentsUserData<RenderViewHostDestructionObserver> { |
114 public: | 113 public: |
115 virtual ~RenderViewHostDestructionObserver() {} | 114 virtual ~RenderViewHostDestructionObserver() {} |
116 | 115 |
117 private: | 116 private: |
118 explicit RenderViewHostDestructionObserver(WebContents* web_contents) | 117 explicit RenderViewHostDestructionObserver(WebContents* web_contents) |
119 : WebContentsObserver(web_contents) { | 118 : WebContentsObserver(web_contents) { |
120 BrowserContext* context = web_contents->GetBrowserContext(); | 119 BrowserContext* context = web_contents->GetBrowserContext(); |
121 process_manager_ = | 120 process_manager_ = |
122 ExtensionSystem::GetForBrowserContext(context)->process_manager(); | 121 ExtensionSystem::GetForBrowserContext(context)->process_manager(); |
123 } | 122 } |
124 | 123 |
125 friend class content::WebContentsUserData<RenderViewHostDestructionObserver>; | 124 friend class content::WebContentsUserData<RenderViewHostDestructionObserver>; |
126 | 125 |
127 // content::WebContentsObserver overrides. | 126 // content::WebContentsObserver overrides. |
128 virtual void RenderViewDeleted(RenderViewHost* render_view_host) OVERRIDE { | 127 virtual void RenderViewDeleted(RenderViewHost* render_view_host) OVERRIDE { |
129 process_manager_->UnregisterRenderViewHost(render_view_host); | 128 process_manager_->UnregisterRenderViewHost(render_view_host); |
130 } | 129 } |
131 | 130 |
132 ExtensionProcessManager* process_manager_; | 131 ProcessManager* process_manager_; |
133 | 132 |
134 DISALLOW_COPY_AND_ASSIGN(RenderViewHostDestructionObserver); | 133 DISALLOW_COPY_AND_ASSIGN(RenderViewHostDestructionObserver); |
135 }; | 134 }; |
136 | 135 |
137 struct ExtensionProcessManager::BackgroundPageData { | 136 struct ProcessManager::BackgroundPageData { |
138 // The count of things keeping the lazy background page alive. | 137 // The count of things keeping the lazy background page alive. |
139 int lazy_keepalive_count; | 138 int lazy_keepalive_count; |
140 | 139 |
141 // This is used with the ShouldSuspend message, to ensure that the extension | 140 // This is used with the ShouldSuspend message, to ensure that the extension |
142 // remained idle between sending the message and receiving the ack. | 141 // remained idle between sending the message and receiving the ack. |
143 int close_sequence_id; | 142 int close_sequence_id; |
144 | 143 |
145 // True if the page responded to the ShouldSuspend message and is currently | 144 // True if the page responded to the ShouldSuspend message and is currently |
146 // dispatching the suspend event. During this time any events that arrive will | 145 // dispatching the suspend event. During this time any events that arrive will |
147 // cancel the suspend process and an onSuspendCanceled event will be | 146 // cancel the suspend process and an onSuspendCanceled event will be |
148 // dispatched to the page. | 147 // dispatched to the page. |
149 bool is_closing; | 148 bool is_closing; |
150 | 149 |
151 // Keeps track of when this page was last suspended. Used for perf metrics. | 150 // Keeps track of when this page was last suspended. Used for perf metrics. |
152 linked_ptr<base::ElapsedTimer> since_suspended; | 151 linked_ptr<base::ElapsedTimer> since_suspended; |
153 | 152 |
154 BackgroundPageData() | 153 BackgroundPageData() |
155 : lazy_keepalive_count(0), close_sequence_id(0), is_closing(false) {} | 154 : lazy_keepalive_count(0), close_sequence_id(0), is_closing(false) {} |
156 }; | 155 }; |
157 | 156 |
158 // | 157 // |
159 // ExtensionProcessManager | 158 // ProcessManager |
160 // | 159 // |
161 | 160 |
162 // static | 161 // static |
163 ExtensionProcessManager* ExtensionProcessManager::Create( | 162 ProcessManager* ProcessManager::Create(BrowserContext* context) { |
164 BrowserContext* context) { | |
165 if (context->IsOffTheRecord()) { | 163 if (context->IsOffTheRecord()) { |
166 BrowserContext* original_context = | 164 BrowserContext* original_context = |
167 ExtensionsBrowserClient::Get()->GetOriginalContext(context); | 165 ExtensionsBrowserClient::Get()->GetOriginalContext(context); |
168 return new IncognitoExtensionProcessManager(context, original_context); | 166 return new IncognitoProcessManager(context, original_context); |
169 } | 167 } |
170 return new ExtensionProcessManager(context, context); | 168 return new ProcessManager(context, context); |
171 } | 169 } |
172 | 170 |
173 ExtensionProcessManager::ExtensionProcessManager( | 171 ProcessManager::ProcessManager(BrowserContext* context, |
174 BrowserContext* context, | 172 BrowserContext* original_context) |
175 BrowserContext* original_context) | |
176 : site_instance_(SiteInstance::Create(context)), | 173 : site_instance_(SiteInstance::Create(context)), |
177 defer_background_host_creation_(false), | 174 defer_background_host_creation_(false), |
178 startup_background_hosts_created_(false), | 175 startup_background_hosts_created_(false), |
179 devtools_callback_(base::Bind( | 176 devtools_callback_(base::Bind( |
180 &ExtensionProcessManager::OnDevToolsStateChanged, | 177 &ProcessManager::OnDevToolsStateChanged, |
181 base::Unretained(this))), | 178 base::Unretained(this))), |
182 weak_ptr_factory_(this) { | 179 weak_ptr_factory_(this) { |
183 registrar_.Add(this, chrome::NOTIFICATION_EXTENSIONS_READY, | 180 registrar_.Add(this, chrome::NOTIFICATION_EXTENSIONS_READY, |
184 content::Source<BrowserContext>(original_context)); | 181 content::Source<BrowserContext>(original_context)); |
185 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LOADED, | 182 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LOADED, |
186 content::Source<BrowserContext>(original_context)); | 183 content::Source<BrowserContext>(original_context)); |
187 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED, | 184 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED, |
188 content::Source<BrowserContext>(original_context)); | 185 content::Source<BrowserContext>(original_context)); |
189 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED, | 186 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED, |
190 content::Source<BrowserContext>(context)); | 187 content::Source<BrowserContext>(context)); |
(...skipping 24 matching lines...) Expand all Loading... |
215 extensions::switches::kEventPageSuspendingTime), | 212 extensions::switches::kEventPageSuspendingTime), |
216 &suspending_time_sec)) { | 213 &suspending_time_sec)) { |
217 event_page_suspending_time_ = | 214 event_page_suspending_time_ = |
218 base::TimeDelta::FromSeconds(suspending_time_sec); | 215 base::TimeDelta::FromSeconds(suspending_time_sec); |
219 } | 216 } |
220 | 217 |
221 content::DevToolsManager::GetInstance()->AddAgentStateCallback( | 218 content::DevToolsManager::GetInstance()->AddAgentStateCallback( |
222 devtools_callback_); | 219 devtools_callback_); |
223 } | 220 } |
224 | 221 |
225 ExtensionProcessManager::~ExtensionProcessManager() { | 222 ProcessManager::~ProcessManager() { |
226 CloseBackgroundHosts(); | 223 CloseBackgroundHosts(); |
227 DCHECK(background_hosts_.empty()); | 224 DCHECK(background_hosts_.empty()); |
228 content::DevToolsManager::GetInstance()->RemoveAgentStateCallback( | 225 content::DevToolsManager::GetInstance()->RemoveAgentStateCallback( |
229 devtools_callback_); | 226 devtools_callback_); |
230 } | 227 } |
231 | 228 |
232 const ExtensionProcessManager::ViewSet | 229 const ProcessManager::ViewSet ProcessManager::GetAllViews() const { |
233 ExtensionProcessManager::GetAllViews() const { | |
234 ViewSet result; | 230 ViewSet result; |
235 for (ExtensionRenderViews::const_iterator iter = | 231 for (ExtensionRenderViews::const_iterator iter = |
236 all_extension_views_.begin(); | 232 all_extension_views_.begin(); |
237 iter != all_extension_views_.end(); ++iter) { | 233 iter != all_extension_views_.end(); ++iter) { |
238 result.insert(iter->first); | 234 result.insert(iter->first); |
239 } | 235 } |
240 return result; | 236 return result; |
241 } | 237 } |
242 | 238 |
243 ExtensionHost* ExtensionProcessManager::CreateBackgroundHost( | 239 ExtensionHost* ProcessManager::CreateBackgroundHost(const Extension* extension, |
244 const Extension* extension, const GURL& url) { | 240 const GURL& url) { |
245 DVLOG(1) << "CreateBackgroundHost " << url.spec(); | 241 DVLOG(1) << "CreateBackgroundHost " << url.spec(); |
246 // Hosted apps are taken care of from BackgroundContentsService. Ignore them | 242 // Hosted apps are taken care of from BackgroundContentsService. Ignore them |
247 // here. | 243 // here. |
248 if (extension->is_hosted_app()) | 244 if (extension->is_hosted_app()) |
249 return NULL; | 245 return NULL; |
250 | 246 |
251 // Don't create multiple background hosts for an extension. | 247 // Don't create multiple background hosts for an extension. |
252 if (ExtensionHost* host = GetBackgroundHostForExtension(extension->id())) | 248 if (ExtensionHost* host = GetBackgroundHostForExtension(extension->id())) |
253 return host; // TODO(kalman): return NULL here? It might break things... | 249 return host; // TODO(kalman): return NULL here? It might break things... |
254 | 250 |
255 ExtensionHost* host = | 251 ExtensionHost* host = |
256 #if defined(OS_MACOSX) | 252 #if defined(OS_MACOSX) |
257 new extensions::ExtensionHostMac( | 253 new ExtensionHostMac( |
258 extension, GetSiteInstanceForURL(url), url, | 254 extension, GetSiteInstanceForURL(url), url, |
259 extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); | 255 VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); |
260 #else | 256 #else |
261 new ExtensionHost(extension, GetSiteInstanceForURL(url), url, | 257 new ExtensionHost(extension, GetSiteInstanceForURL(url), url, |
262 extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); | 258 VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); |
263 #endif | 259 #endif |
264 | 260 |
265 host->CreateRenderViewSoon(); | 261 host->CreateRenderViewSoon(); |
266 OnBackgroundHostCreated(host); | 262 OnBackgroundHostCreated(host); |
267 return host; | 263 return host; |
268 } | 264 } |
269 | 265 |
270 ExtensionHost* ExtensionProcessManager::GetBackgroundHostForExtension( | 266 ExtensionHost* ProcessManager::GetBackgroundHostForExtension( |
271 const std::string& extension_id) { | 267 const std::string& extension_id) { |
272 for (ExtensionHostSet::iterator iter = background_hosts_.begin(); | 268 for (ExtensionHostSet::iterator iter = background_hosts_.begin(); |
273 iter != background_hosts_.end(); ++iter) { | 269 iter != background_hosts_.end(); ++iter) { |
274 ExtensionHost* host = *iter; | 270 ExtensionHost* host = *iter; |
275 if (host->extension_id() == extension_id) | 271 if (host->extension_id() == extension_id) |
276 return host; | 272 return host; |
277 } | 273 } |
278 return NULL; | 274 return NULL; |
279 } | 275 } |
280 | 276 |
281 std::set<RenderViewHost*> | 277 std::set<RenderViewHost*> ProcessManager::GetRenderViewHostsForExtension( |
282 ExtensionProcessManager::GetRenderViewHostsForExtension( | 278 const std::string& extension_id) { |
283 const std::string& extension_id) { | |
284 std::set<RenderViewHost*> result; | 279 std::set<RenderViewHost*> result; |
285 | 280 |
286 SiteInstance* site_instance = GetSiteInstanceForURL( | 281 SiteInstance* site_instance = GetSiteInstanceForURL( |
287 Extension::GetBaseURLFromExtensionId(extension_id)); | 282 Extension::GetBaseURLFromExtensionId(extension_id)); |
288 if (!site_instance) | 283 if (!site_instance) |
289 return result; | 284 return result; |
290 | 285 |
291 // Gather up all the views for that site. | 286 // Gather up all the views for that site. |
292 for (ExtensionRenderViews::iterator view = all_extension_views_.begin(); | 287 for (ExtensionRenderViews::iterator view = all_extension_views_.begin(); |
293 view != all_extension_views_.end(); ++view) { | 288 view != all_extension_views_.end(); ++view) { |
294 if (view->first->GetSiteInstance() == site_instance) | 289 if (view->first->GetSiteInstance() == site_instance) |
295 result.insert(view->first); | 290 result.insert(view->first); |
296 } | 291 } |
297 | 292 |
298 return result; | 293 return result; |
299 } | 294 } |
300 | 295 |
301 const Extension* ExtensionProcessManager::GetExtensionForRenderViewHost( | 296 const Extension* ProcessManager::GetExtensionForRenderViewHost( |
302 RenderViewHost* render_view_host) { | 297 RenderViewHost* render_view_host) { |
303 if (!render_view_host->GetSiteInstance()) | 298 if (!render_view_host->GetSiteInstance()) |
304 return NULL; | 299 return NULL; |
305 | 300 |
306 ExtensionService* service = ExtensionSystem::GetForBrowserContext( | 301 ExtensionService* service = ExtensionSystem::GetForBrowserContext( |
307 GetBrowserContext())->extension_service(); | 302 GetBrowserContext())->extension_service(); |
308 if (!service) | 303 if (!service) |
309 return NULL; | 304 return NULL; |
310 | 305 |
311 return service->extensions()->GetByID(GetExtensionID(render_view_host)); | 306 return service->extensions()->GetByID(GetExtensionID(render_view_host)); |
312 } | 307 } |
313 | 308 |
314 void ExtensionProcessManager::UnregisterRenderViewHost( | 309 void ProcessManager::UnregisterRenderViewHost( |
315 RenderViewHost* render_view_host) { | 310 RenderViewHost* render_view_host) { |
316 ExtensionRenderViews::iterator view = | 311 ExtensionRenderViews::iterator view = |
317 all_extension_views_.find(render_view_host); | 312 all_extension_views_.find(render_view_host); |
318 if (view == all_extension_views_.end()) | 313 if (view == all_extension_views_.end()) |
319 return; | 314 return; |
320 | 315 |
321 OnRenderViewHostUnregistered(GetBrowserContext(), render_view_host); | 316 OnRenderViewHostUnregistered(GetBrowserContext(), render_view_host); |
322 extensions::ViewType view_type = view->second; | 317 ViewType view_type = view->second; |
323 all_extension_views_.erase(view); | 318 all_extension_views_.erase(view); |
324 | 319 |
325 // Keepalive count, balanced in RegisterRenderViewHost. | 320 // Keepalive count, balanced in RegisterRenderViewHost. |
326 if (view_type != extensions::VIEW_TYPE_INVALID && | 321 if (view_type != VIEW_TYPE_INVALID && |
327 view_type != extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) { | 322 view_type != VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) { |
328 const Extension* extension = GetExtensionForRenderViewHost( | 323 const Extension* extension = GetExtensionForRenderViewHost( |
329 render_view_host); | 324 render_view_host); |
330 if (extension) | 325 if (extension) |
331 DecrementLazyKeepaliveCount(extension); | 326 DecrementLazyKeepaliveCount(extension); |
332 } | 327 } |
333 } | 328 } |
334 | 329 |
335 void ExtensionProcessManager::RegisterRenderViewHost( | 330 void ProcessManager::RegisterRenderViewHost(RenderViewHost* render_view_host) { |
336 RenderViewHost* render_view_host) { | |
337 const Extension* extension = GetExtensionForRenderViewHost( | 331 const Extension* extension = GetExtensionForRenderViewHost( |
338 render_view_host); | 332 render_view_host); |
339 if (!extension) | 333 if (!extension) |
340 return; | 334 return; |
341 | 335 |
342 WebContents* web_contents = WebContents::FromRenderViewHost(render_view_host); | 336 WebContents* web_contents = WebContents::FromRenderViewHost(render_view_host); |
343 all_extension_views_[render_view_host] = | 337 all_extension_views_[render_view_host] = GetViewType(web_contents); |
344 extensions::GetViewType(web_contents); | |
345 | 338 |
346 // Keep the lazy background page alive as long as any non-background-page | 339 // Keep the lazy background page alive as long as any non-background-page |
347 // extension views are visible. Keepalive count balanced in | 340 // extension views are visible. Keepalive count balanced in |
348 // UnregisterRenderViewHost. | 341 // UnregisterRenderViewHost. |
349 IncrementLazyKeepaliveCountForView(render_view_host); | 342 IncrementLazyKeepaliveCountForView(render_view_host); |
350 } | 343 } |
351 | 344 |
352 SiteInstance* ExtensionProcessManager::GetSiteInstanceForURL(const GURL& url) { | 345 SiteInstance* ProcessManager::GetSiteInstanceForURL(const GURL& url) { |
353 return site_instance_->GetRelatedSiteInstance(url); | 346 return site_instance_->GetRelatedSiteInstance(url); |
354 } | 347 } |
355 | 348 |
356 bool ExtensionProcessManager::IsBackgroundHostClosing( | 349 bool ProcessManager::IsBackgroundHostClosing(const std::string& extension_id) { |
357 const std::string& extension_id) { | |
358 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); | 350 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); |
359 return (host && background_page_data_[extension_id].is_closing); | 351 return (host && background_page_data_[extension_id].is_closing); |
360 } | 352 } |
361 | 353 |
362 int ExtensionProcessManager::GetLazyKeepaliveCount(const Extension* extension) { | 354 int ProcessManager::GetLazyKeepaliveCount(const Extension* extension) { |
363 if (!BackgroundInfo::HasLazyBackgroundPage(extension)) | 355 if (!BackgroundInfo::HasLazyBackgroundPage(extension)) |
364 return 0; | 356 return 0; |
365 | 357 |
366 return background_page_data_[extension->id()].lazy_keepalive_count; | 358 return background_page_data_[extension->id()].lazy_keepalive_count; |
367 } | 359 } |
368 | 360 |
369 int ExtensionProcessManager::IncrementLazyKeepaliveCount( | 361 int ProcessManager::IncrementLazyKeepaliveCount(const Extension* extension) { |
370 const Extension* extension) { | |
371 if (!BackgroundInfo::HasLazyBackgroundPage(extension)) | 362 if (!BackgroundInfo::HasLazyBackgroundPage(extension)) |
372 return 0; | 363 return 0; |
373 | 364 |
374 int& count = background_page_data_[extension->id()].lazy_keepalive_count; | 365 int& count = background_page_data_[extension->id()].lazy_keepalive_count; |
375 if (++count == 1) | 366 if (++count == 1) |
376 OnLazyBackgroundPageActive(extension->id()); | 367 OnLazyBackgroundPageActive(extension->id()); |
377 | 368 |
378 return count; | 369 return count; |
379 } | 370 } |
380 | 371 |
381 int ExtensionProcessManager::DecrementLazyKeepaliveCount( | 372 int ProcessManager::DecrementLazyKeepaliveCount(const Extension* extension) { |
382 const Extension* extension) { | |
383 if (!BackgroundInfo::HasLazyBackgroundPage(extension)) | 373 if (!BackgroundInfo::HasLazyBackgroundPage(extension)) |
384 return 0; | 374 return 0; |
385 | 375 |
386 int& count = background_page_data_[extension->id()].lazy_keepalive_count; | 376 int& count = background_page_data_[extension->id()].lazy_keepalive_count; |
387 DCHECK_GT(count, 0); | 377 DCHECK_GT(count, 0); |
388 | 378 |
389 // If we reach a zero keepalive count when the lazy background page is about | 379 // If we reach a zero keepalive count when the lazy background page is about |
390 // to be closed, incrementing close_sequence_id will cancel the close | 380 // to be closed, incrementing close_sequence_id will cancel the close |
391 // sequence and cause the background page to linger. So check is_closing | 381 // sequence and cause the background page to linger. So check is_closing |
392 // before initiating another close sequence. | 382 // before initiating another close sequence. |
393 if (--count == 0 && !background_page_data_[extension->id()].is_closing) { | 383 if (--count == 0 && !background_page_data_[extension->id()].is_closing) { |
394 base::MessageLoop::current()->PostDelayedTask( | 384 base::MessageLoop::current()->PostDelayedTask( |
395 FROM_HERE, | 385 FROM_HERE, |
396 base::Bind(&ExtensionProcessManager::OnLazyBackgroundPageIdle, | 386 base::Bind(&ProcessManager::OnLazyBackgroundPageIdle, |
397 weak_ptr_factory_.GetWeakPtr(), extension->id(), | 387 weak_ptr_factory_.GetWeakPtr(), extension->id(), |
398 ++background_page_data_[extension->id()].close_sequence_id), | 388 ++background_page_data_[extension->id()].close_sequence_id), |
399 event_page_idle_time_); | 389 event_page_idle_time_); |
400 } | 390 } |
401 | 391 |
402 return count; | 392 return count; |
403 } | 393 } |
404 | 394 |
405 void ExtensionProcessManager::IncrementLazyKeepaliveCountForView( | 395 void ProcessManager::IncrementLazyKeepaliveCountForView( |
406 RenderViewHost* render_view_host) { | 396 RenderViewHost* render_view_host) { |
407 WebContents* web_contents = | 397 WebContents* web_contents = |
408 WebContents::FromRenderViewHost(render_view_host); | 398 WebContents::FromRenderViewHost(render_view_host); |
409 extensions::ViewType view_type = extensions::GetViewType(web_contents); | 399 ViewType view_type = GetViewType(web_contents); |
410 if (view_type != extensions::VIEW_TYPE_INVALID && | 400 if (view_type != VIEW_TYPE_INVALID && |
411 view_type != extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) { | 401 view_type != VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) { |
412 const Extension* extension = GetExtensionForRenderViewHost( | 402 const Extension* extension = GetExtensionForRenderViewHost( |
413 render_view_host); | 403 render_view_host); |
414 if (extension) | 404 if (extension) |
415 IncrementLazyKeepaliveCount(extension); | 405 IncrementLazyKeepaliveCount(extension); |
416 } | 406 } |
417 } | 407 } |
418 | 408 |
419 void ExtensionProcessManager::OnLazyBackgroundPageIdle( | 409 void ProcessManager::OnLazyBackgroundPageIdle(const std::string& extension_id, |
420 const std::string& extension_id, int sequence_id) { | 410 int sequence_id) { |
421 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); | 411 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); |
422 if (host && !background_page_data_[extension_id].is_closing && | 412 if (host && !background_page_data_[extension_id].is_closing && |
423 sequence_id == background_page_data_[extension_id].close_sequence_id) { | 413 sequence_id == background_page_data_[extension_id].close_sequence_id) { |
424 // Tell the renderer we are about to close. This is a simple ping that the | 414 // Tell the renderer we are about to close. This is a simple ping that the |
425 // renderer will respond to. The purpose is to control sequencing: if the | 415 // renderer will respond to. The purpose is to control sequencing: if the |
426 // extension remains idle until the renderer responds with an ACK, then we | 416 // extension remains idle until the renderer responds with an ACK, then we |
427 // know that the extension process is ready to shut down. If our | 417 // know that the extension process is ready to shut down. If our |
428 // close_sequence_id has already changed, then we would ignore the | 418 // close_sequence_id has already changed, then we would ignore the |
429 // ShouldSuspendAck, so we don't send the ping. | 419 // ShouldSuspendAck, so we don't send the ping. |
430 host->render_view_host()->Send(new ExtensionMsg_ShouldSuspend( | 420 host->render_view_host()->Send(new ExtensionMsg_ShouldSuspend( |
431 extension_id, sequence_id)); | 421 extension_id, sequence_id)); |
432 } | 422 } |
433 } | 423 } |
434 | 424 |
435 void ExtensionProcessManager::OnLazyBackgroundPageActive( | 425 void ProcessManager::OnLazyBackgroundPageActive( |
436 const std::string& extension_id) { | 426 const std::string& extension_id) { |
437 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); | 427 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); |
438 if (host && !background_page_data_[extension_id].is_closing) { | 428 if (host && !background_page_data_[extension_id].is_closing) { |
439 // Cancel the current close sequence by changing the close_sequence_id, | 429 // Cancel the current close sequence by changing the close_sequence_id, |
440 // which causes us to ignore the next ShouldSuspendAck. | 430 // which causes us to ignore the next ShouldSuspendAck. |
441 ++background_page_data_[extension_id].close_sequence_id; | 431 ++background_page_data_[extension_id].close_sequence_id; |
442 } | 432 } |
443 } | 433 } |
444 | 434 |
445 void ExtensionProcessManager::OnShouldSuspendAck( | 435 void ProcessManager::OnShouldSuspendAck(const std::string& extension_id, |
446 const std::string& extension_id, int sequence_id) { | 436 int sequence_id) { |
447 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); | 437 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); |
448 if (host && | 438 if (host && |
449 sequence_id == background_page_data_[extension_id].close_sequence_id) { | 439 sequence_id == background_page_data_[extension_id].close_sequence_id) { |
450 host->render_view_host()->Send(new ExtensionMsg_Suspend(extension_id)); | 440 host->render_view_host()->Send(new ExtensionMsg_Suspend(extension_id)); |
451 } | 441 } |
452 } | 442 } |
453 | 443 |
454 void ExtensionProcessManager::OnSuspendAck(const std::string& extension_id) { | 444 void ProcessManager::OnSuspendAck(const std::string& extension_id) { |
455 background_page_data_[extension_id].is_closing = true; | 445 background_page_data_[extension_id].is_closing = true; |
456 int sequence_id = background_page_data_[extension_id].close_sequence_id; | 446 int sequence_id = background_page_data_[extension_id].close_sequence_id; |
457 base::MessageLoop::current()->PostDelayedTask( | 447 base::MessageLoop::current()->PostDelayedTask( |
458 FROM_HERE, | 448 FROM_HERE, |
459 base::Bind(&ExtensionProcessManager::CloseLazyBackgroundPageNow, | 449 base::Bind(&ProcessManager::CloseLazyBackgroundPageNow, |
460 weak_ptr_factory_.GetWeakPtr(), extension_id, sequence_id), | 450 weak_ptr_factory_.GetWeakPtr(), extension_id, sequence_id), |
461 event_page_suspending_time_); | 451 event_page_suspending_time_); |
462 } | 452 } |
463 | 453 |
464 void ExtensionProcessManager::CloseLazyBackgroundPageNow( | 454 void ProcessManager::CloseLazyBackgroundPageNow(const std::string& extension_id, |
465 const std::string& extension_id, int sequence_id) { | 455 int sequence_id) { |
466 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); | 456 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); |
467 if (host && | 457 if (host && |
468 sequence_id == background_page_data_[extension_id].close_sequence_id) { | 458 sequence_id == background_page_data_[extension_id].close_sequence_id) { |
469 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); | 459 ExtensionHost* host = GetBackgroundHostForExtension(extension_id); |
470 if (host) | 460 if (host) |
471 CloseBackgroundHost(host); | 461 CloseBackgroundHost(host); |
472 } | 462 } |
473 } | 463 } |
474 | 464 |
475 void ExtensionProcessManager::OnNetworkRequestStarted( | 465 void ProcessManager::OnNetworkRequestStarted(RenderViewHost* render_view_host) { |
476 RenderViewHost* render_view_host) { | |
477 ExtensionHost* host = GetBackgroundHostForExtension( | 466 ExtensionHost* host = GetBackgroundHostForExtension( |
478 GetExtensionID(render_view_host)); | 467 GetExtensionID(render_view_host)); |
479 if (host && host->render_view_host() == render_view_host) | 468 if (host && host->render_view_host() == render_view_host) |
480 IncrementLazyKeepaliveCount(host->extension()); | 469 IncrementLazyKeepaliveCount(host->extension()); |
481 } | 470 } |
482 | 471 |
483 void ExtensionProcessManager::OnNetworkRequestDone( | 472 void ProcessManager::OnNetworkRequestDone(RenderViewHost* render_view_host) { |
484 RenderViewHost* render_view_host) { | |
485 ExtensionHost* host = GetBackgroundHostForExtension( | 473 ExtensionHost* host = GetBackgroundHostForExtension( |
486 GetExtensionID(render_view_host)); | 474 GetExtensionID(render_view_host)); |
487 if (host && host->render_view_host() == render_view_host) | 475 if (host && host->render_view_host() == render_view_host) |
488 DecrementLazyKeepaliveCount(host->extension()); | 476 DecrementLazyKeepaliveCount(host->extension()); |
489 } | 477 } |
490 | 478 |
491 void ExtensionProcessManager::CancelSuspend(const Extension* extension) { | 479 void ProcessManager::CancelSuspend(const Extension* extension) { |
492 bool& is_closing = background_page_data_[extension->id()].is_closing; | 480 bool& is_closing = background_page_data_[extension->id()].is_closing; |
493 ExtensionHost* host = GetBackgroundHostForExtension(extension->id()); | 481 ExtensionHost* host = GetBackgroundHostForExtension(extension->id()); |
494 if (host && is_closing) { | 482 if (host && is_closing) { |
495 is_closing = false; | 483 is_closing = false; |
496 host->render_view_host()->Send( | 484 host->render_view_host()->Send( |
497 new ExtensionMsg_CancelSuspend(extension->id())); | 485 new ExtensionMsg_CancelSuspend(extension->id())); |
498 // This increment / decrement is to simulate an instantaneous event. This | 486 // This increment / decrement is to simulate an instantaneous event. This |
499 // has the effect of invalidating close_sequence_id, preventing any in | 487 // has the effect of invalidating close_sequence_id, preventing any in |
500 // progress closes from completing and starting a new close process if | 488 // progress closes from completing and starting a new close process if |
501 // necessary. | 489 // necessary. |
502 IncrementLazyKeepaliveCount(extension); | 490 IncrementLazyKeepaliveCount(extension); |
503 DecrementLazyKeepaliveCount(extension); | 491 DecrementLazyKeepaliveCount(extension); |
504 } | 492 } |
505 } | 493 } |
506 | 494 |
507 void ExtensionProcessManager::DeferBackgroundHostCreation(bool defer) { | 495 void ProcessManager::DeferBackgroundHostCreation(bool defer) { |
508 bool previous = defer_background_host_creation_; | 496 bool previous = defer_background_host_creation_; |
509 defer_background_host_creation_ = defer; | 497 defer_background_host_creation_ = defer; |
510 | 498 |
511 // If we were deferred, and we switch to non-deferred, then create the | 499 // If we were deferred, and we switch to non-deferred, then create the |
512 // background hosts. | 500 // background hosts. |
513 if (previous && !defer_background_host_creation_) | 501 if (previous && !defer_background_host_creation_) |
514 CreateBackgroundHostsForProfileStartup(); | 502 CreateBackgroundHostsForProfileStartup(); |
515 } | 503 } |
516 | 504 |
517 void ExtensionProcessManager::OnBrowserWindowReady() { | 505 void ProcessManager::OnBrowserWindowReady() { |
518 ExtensionService* service = ExtensionSystem::GetForBrowserContext( | 506 ExtensionService* service = ExtensionSystem::GetForBrowserContext( |
519 GetBrowserContext())->extension_service(); | 507 GetBrowserContext())->extension_service(); |
520 // On Chrome OS, a login screen is implemented as a browser. | 508 // On Chrome OS, a login screen is implemented as a browser. |
521 // This browser has no extension service. In this case, | 509 // This browser has no extension service. In this case, |
522 // service will be NULL. | 510 // service will be NULL. |
523 if (!service || !service->is_ready()) | 511 if (!service || !service->is_ready()) |
524 return; | 512 return; |
525 | 513 |
526 CreateBackgroundHostsForProfileStartup(); | 514 CreateBackgroundHostsForProfileStartup(); |
527 } | 515 } |
528 | 516 |
529 content::BrowserContext* ExtensionProcessManager::GetBrowserContext() const { | 517 content::BrowserContext* ProcessManager::GetBrowserContext() const { |
530 return site_instance_->GetBrowserContext(); | 518 return site_instance_->GetBrowserContext(); |
531 } | 519 } |
532 | 520 |
533 void ExtensionProcessManager::Observe( | 521 void ProcessManager::Observe(int type, |
534 int type, | 522 const content::NotificationSource& source, |
535 const content::NotificationSource& source, | 523 const content::NotificationDetails& details) { |
536 const content::NotificationDetails& details) { | |
537 switch (type) { | 524 switch (type) { |
538 case chrome::NOTIFICATION_EXTENSIONS_READY: | 525 case chrome::NOTIFICATION_EXTENSIONS_READY: |
539 case chrome::NOTIFICATION_PROFILE_CREATED: { | 526 case chrome::NOTIFICATION_PROFILE_CREATED: { |
540 CreateBackgroundHostsForProfileStartup(); | 527 CreateBackgroundHostsForProfileStartup(); |
541 break; | 528 break; |
542 } | 529 } |
543 | 530 |
544 case chrome::NOTIFICATION_EXTENSION_LOADED: { | 531 case chrome::NOTIFICATION_EXTENSION_LOADED: { |
545 BrowserContext* context = content::Source<BrowserContext>(source).ptr(); | 532 BrowserContext* context = content::Source<BrowserContext>(source).ptr(); |
546 ExtensionService* service = | 533 ExtensionService* service = |
547 ExtensionSystem::GetForBrowserContext(context)->extension_service(); | 534 ExtensionSystem::GetForBrowserContext(context)->extension_service(); |
548 if (service->is_ready()) { | 535 if (service->is_ready()) { |
549 const Extension* extension = | 536 const Extension* extension = |
550 content::Details<const Extension>(details).ptr(); | 537 content::Details<const Extension>(details).ptr(); |
551 CreateBackgroundHostForExtensionLoad(this, extension); | 538 CreateBackgroundHostForExtensionLoad(this, extension); |
552 } | 539 } |
553 break; | 540 break; |
554 } | 541 } |
555 | 542 |
556 case chrome::NOTIFICATION_EXTENSION_UNLOADED: { | 543 case chrome::NOTIFICATION_EXTENSION_UNLOADED: { |
557 const Extension* extension = | 544 const Extension* extension = |
558 content::Details<extensions::UnloadedExtensionInfo>( | 545 content::Details<UnloadedExtensionInfo>(details)->extension; |
559 details)->extension; | |
560 for (ExtensionHostSet::iterator iter = background_hosts_.begin(); | 546 for (ExtensionHostSet::iterator iter = background_hosts_.begin(); |
561 iter != background_hosts_.end(); ++iter) { | 547 iter != background_hosts_.end(); ++iter) { |
562 ExtensionHost* host = *iter; | 548 ExtensionHost* host = *iter; |
563 if (host->extension_id() == extension->id()) { | 549 if (host->extension_id() == extension->id()) { |
564 CloseBackgroundHost(host); | 550 CloseBackgroundHost(host); |
565 break; | 551 break; |
566 } | 552 } |
567 } | 553 } |
568 UnregisterExtension(extension->id()); | 554 UnregisterExtension(extension->id()); |
569 break; | 555 break; |
570 } | 556 } |
571 | 557 |
572 case chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED: { | 558 case chrome::NOTIFICATION_EXTENSION_HOST_DESTROYED: { |
573 ExtensionHost* host = content::Details<ExtensionHost>(details).ptr(); | 559 ExtensionHost* host = content::Details<ExtensionHost>(details).ptr(); |
574 if (background_hosts_.erase(host)) { | 560 if (background_hosts_.erase(host)) { |
575 ClearBackgroundPageData(host->extension()->id()); | 561 ClearBackgroundPageData(host->extension()->id()); |
576 background_page_data_[host->extension()->id()].since_suspended.reset( | 562 background_page_data_[host->extension()->id()].since_suspended.reset( |
577 new base::ElapsedTimer()); | 563 new base::ElapsedTimer()); |
578 } | 564 } |
579 break; | 565 break; |
580 } | 566 } |
581 | 567 |
582 case chrome::NOTIFICATION_EXTENSION_HOST_VIEW_SHOULD_CLOSE: { | 568 case chrome::NOTIFICATION_EXTENSION_HOST_VIEW_SHOULD_CLOSE: { |
583 ExtensionHost* host = content::Details<ExtensionHost>(details).ptr(); | 569 ExtensionHost* host = content::Details<ExtensionHost>(details).ptr(); |
584 if (host->extension_host_type() == | 570 if (host->extension_host_type() == VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) { |
585 extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) { | |
586 CloseBackgroundHost(host); | 571 CloseBackgroundHost(host); |
587 } | 572 } |
588 break; | 573 break; |
589 } | 574 } |
590 | 575 |
591 case content::NOTIFICATION_RENDER_VIEW_HOST_CHANGED: { | 576 case content::NOTIFICATION_RENDER_VIEW_HOST_CHANGED: { |
592 // We get this notification both for new WebContents and when one | 577 // We get this notification both for new WebContents and when one |
593 // has its RenderViewHost replaced (e.g. when a user does a cross-site | 578 // has its RenderViewHost replaced (e.g. when a user does a cross-site |
594 // navigation away from an extension URL). For the replaced case, we must | 579 // navigation away from an extension URL). For the replaced case, we must |
595 // unregister the old RVH so it doesn't count as an active view that would | 580 // unregister the old RVH so it doesn't count as an active view that would |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
635 // destructor is called too late in the shutdown sequence. | 620 // destructor is called too late in the shutdown sequence. |
636 CloseBackgroundHosts(); | 621 CloseBackgroundHosts(); |
637 break; | 622 break; |
638 } | 623 } |
639 | 624 |
640 default: | 625 default: |
641 NOTREACHED(); | 626 NOTREACHED(); |
642 } | 627 } |
643 } | 628 } |
644 | 629 |
645 void ExtensionProcessManager::OnDevToolsStateChanged( | 630 void ProcessManager::OnDevToolsStateChanged( |
646 content::DevToolsAgentHost* agent_host, bool attached) { | 631 content::DevToolsAgentHost* agent_host, |
| 632 bool attached) { |
647 RenderViewHost* rvh = agent_host->GetRenderViewHost(); | 633 RenderViewHost* rvh = agent_host->GetRenderViewHost(); |
648 // Ignore unrelated notifications. | 634 // Ignore unrelated notifications. |
649 if (!rvh || | 635 if (!rvh || |
650 rvh->GetSiteInstance()->GetProcess()->GetBrowserContext() != | 636 rvh->GetSiteInstance()->GetProcess()->GetBrowserContext() != |
651 GetBrowserContext()) | 637 GetBrowserContext()) |
652 return; | 638 return; |
653 if (extensions::GetViewType(WebContents::FromRenderViewHost(rvh)) != | 639 if (GetViewType(WebContents::FromRenderViewHost(rvh)) != |
654 extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) | 640 VIEW_TYPE_EXTENSION_BACKGROUND_PAGE) |
655 return; | 641 return; |
656 const Extension* extension = GetExtensionForRenderViewHost(rvh); | 642 const Extension* extension = GetExtensionForRenderViewHost(rvh); |
657 if (!extension) | 643 if (!extension) |
658 return; | 644 return; |
659 if (attached) { | 645 if (attached) { |
660 // Keep the lazy background page alive while it's being inspected. | 646 // Keep the lazy background page alive while it's being inspected. |
661 CancelSuspend(extension); | 647 CancelSuspend(extension); |
662 IncrementLazyKeepaliveCount(extension); | 648 IncrementLazyKeepaliveCount(extension); |
663 } else { | 649 } else { |
664 DecrementLazyKeepaliveCount(extension); | 650 DecrementLazyKeepaliveCount(extension); |
665 } | 651 } |
666 } | 652 } |
667 | 653 |
668 void ExtensionProcessManager::CreateBackgroundHostsForProfileStartup() { | 654 void ProcessManager::CreateBackgroundHostsForProfileStartup() { |
669 if (startup_background_hosts_created_) | 655 if (startup_background_hosts_created_) |
670 return; | 656 return; |
671 | 657 |
672 // Don't load background hosts now if the loading should be deferred. | 658 // Don't load background hosts now if the loading should be deferred. |
673 // Instead they will be loaded when a browser window for this profile | 659 // Instead they will be loaded when a browser window for this profile |
674 // (or an incognito profile from this profile) is ready, or when | 660 // (or an incognito profile from this profile) is ready, or when |
675 // DeferBackgroundHostCreation is called with false. | 661 // DeferBackgroundHostCreation is called with false. |
676 if (DeferLoadingBackgroundHosts()) | 662 if (DeferLoadingBackgroundHosts()) |
677 return; | 663 return; |
678 | 664 |
679 ExtensionService* service = ExtensionSystem::GetForBrowserContext( | 665 ExtensionService* service = ExtensionSystem::GetForBrowserContext( |
680 GetBrowserContext())->extension_service(); | 666 GetBrowserContext())->extension_service(); |
681 DCHECK(service); | 667 DCHECK(service); |
682 for (ExtensionSet::const_iterator extension = service->extensions()->begin(); | 668 for (ExtensionSet::const_iterator extension = service->extensions()->begin(); |
683 extension != service->extensions()->end(); ++extension) { | 669 extension != service->extensions()->end(); ++extension) { |
684 CreateBackgroundHostForExtensionLoad(this, extension->get()); | 670 CreateBackgroundHostForExtensionLoad(this, extension->get()); |
685 | 671 |
686 extensions::RuntimeEventRouter::DispatchOnStartupEvent( | 672 RuntimeEventRouter::DispatchOnStartupEvent(GetBrowserContext(), |
687 GetBrowserContext(), (*extension)->id()); | 673 (*extension)->id()); |
688 } | 674 } |
689 startup_background_hosts_created_ = true; | 675 startup_background_hosts_created_ = true; |
690 | 676 |
691 // Background pages should only be loaded once. To prevent any further loads | 677 // Background pages should only be loaded once. To prevent any further loads |
692 // occurring, we remove the notification listeners. | 678 // occurring, we remove the notification listeners. |
693 BrowserContext* original_context = | 679 BrowserContext* original_context = |
694 ExtensionsBrowserClient::Get()->GetOriginalContext(GetBrowserContext()); | 680 ExtensionsBrowserClient::Get()->GetOriginalContext(GetBrowserContext()); |
695 if (registrar_.IsRegistered( | 681 if (registrar_.IsRegistered( |
696 this, | 682 this, |
697 chrome::NOTIFICATION_PROFILE_CREATED, | 683 chrome::NOTIFICATION_PROFILE_CREATED, |
698 content::Source<BrowserContext>(original_context))) { | 684 content::Source<BrowserContext>(original_context))) { |
699 registrar_.Remove(this, | 685 registrar_.Remove(this, |
700 chrome::NOTIFICATION_PROFILE_CREATED, | 686 chrome::NOTIFICATION_PROFILE_CREATED, |
701 content::Source<BrowserContext>(original_context)); | 687 content::Source<BrowserContext>(original_context)); |
702 } | 688 } |
703 if (registrar_.IsRegistered( | 689 if (registrar_.IsRegistered( |
704 this, | 690 this, |
705 chrome::NOTIFICATION_EXTENSIONS_READY, | 691 chrome::NOTIFICATION_EXTENSIONS_READY, |
706 content::Source<BrowserContext>(original_context))) { | 692 content::Source<BrowserContext>(original_context))) { |
707 registrar_.Remove(this, | 693 registrar_.Remove(this, |
708 chrome::NOTIFICATION_EXTENSIONS_READY, | 694 chrome::NOTIFICATION_EXTENSIONS_READY, |
709 content::Source<BrowserContext>(original_context)); | 695 content::Source<BrowserContext>(original_context)); |
710 } | 696 } |
711 } | 697 } |
712 | 698 |
713 void ExtensionProcessManager::OnBackgroundHostCreated(ExtensionHost* host) { | 699 void ProcessManager::OnBackgroundHostCreated(ExtensionHost* host) { |
714 DCHECK_EQ(GetBrowserContext(), host->browser_context()); | 700 DCHECK_EQ(GetBrowserContext(), host->browser_context()); |
715 background_hosts_.insert(host); | 701 background_hosts_.insert(host); |
716 | 702 |
717 if (BackgroundInfo::HasLazyBackgroundPage(host->extension())) { | 703 if (BackgroundInfo::HasLazyBackgroundPage(host->extension())) { |
718 linked_ptr<base::ElapsedTimer> since_suspended( | 704 linked_ptr<base::ElapsedTimer> since_suspended( |
719 background_page_data_[host->extension()->id()]. | 705 background_page_data_[host->extension()->id()]. |
720 since_suspended.release()); | 706 since_suspended.release()); |
721 if (since_suspended.get()) { | 707 if (since_suspended.get()) { |
722 UMA_HISTOGRAM_LONG_TIMES("Extensions.EventPageIdleTime", | 708 UMA_HISTOGRAM_LONG_TIMES("Extensions.EventPageIdleTime", |
723 since_suspended->Elapsed()); | 709 since_suspended->Elapsed()); |
724 } | 710 } |
725 } | 711 } |
726 } | 712 } |
727 | 713 |
728 void ExtensionProcessManager::CloseBackgroundHost(ExtensionHost* host) { | 714 void ProcessManager::CloseBackgroundHost(ExtensionHost* host) { |
729 CHECK(host->extension_host_type() == | 715 CHECK(host->extension_host_type() == |
730 extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); | 716 VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); |
731 delete host; | 717 delete host; |
732 // |host| should deregister itself from our structures. | 718 // |host| should deregister itself from our structures. |
733 CHECK(background_hosts_.find(host) == background_hosts_.end()); | 719 CHECK(background_hosts_.find(host) == background_hosts_.end()); |
734 } | 720 } |
735 | 721 |
736 void ExtensionProcessManager::CloseBackgroundHosts() { | 722 void ProcessManager::CloseBackgroundHosts() { |
737 for (ExtensionHostSet::iterator iter = background_hosts_.begin(); | 723 for (ExtensionHostSet::iterator iter = background_hosts_.begin(); |
738 iter != background_hosts_.end(); ) { | 724 iter != background_hosts_.end(); ) { |
739 ExtensionHostSet::iterator current = iter++; | 725 ExtensionHostSet::iterator current = iter++; |
740 delete *current; | 726 delete *current; |
741 } | 727 } |
742 } | 728 } |
743 | 729 |
744 void ExtensionProcessManager::UnregisterExtension( | 730 void ProcessManager::UnregisterExtension(const std::string& extension_id) { |
745 const std::string& extension_id) { | |
746 // The lazy_keepalive_count may be greater than zero at this point because | 731 // The lazy_keepalive_count may be greater than zero at this point because |
747 // RenderViewHosts are still alive. During extension reloading, they will | 732 // RenderViewHosts are still alive. During extension reloading, they will |
748 // decrement the lazy_keepalive_count to negative for the new extension | 733 // decrement the lazy_keepalive_count to negative for the new extension |
749 // instance when they are destroyed. Since we are erasing the background page | 734 // instance when they are destroyed. Since we are erasing the background page |
750 // data for the unloaded extension, unregister the RenderViewHosts too. | 735 // data for the unloaded extension, unregister the RenderViewHosts too. |
751 BrowserContext* context = GetBrowserContext(); | 736 BrowserContext* context = GetBrowserContext(); |
752 for (ExtensionRenderViews::iterator it = all_extension_views_.begin(); | 737 for (ExtensionRenderViews::iterator it = all_extension_views_.begin(); |
753 it != all_extension_views_.end(); ) { | 738 it != all_extension_views_.end(); ) { |
754 if (GetExtensionID(it->first) == extension_id) { | 739 if (GetExtensionID(it->first) == extension_id) { |
755 OnRenderViewHostUnregistered(context, it->first); | 740 OnRenderViewHostUnregistered(context, it->first); |
756 all_extension_views_.erase(it++); | 741 all_extension_views_.erase(it++); |
757 } else { | 742 } else { |
758 ++it; | 743 ++it; |
759 } | 744 } |
760 } | 745 } |
761 | 746 |
762 background_page_data_.erase(extension_id); | 747 background_page_data_.erase(extension_id); |
763 } | 748 } |
764 | 749 |
765 void ExtensionProcessManager::ClearBackgroundPageData( | 750 void ProcessManager::ClearBackgroundPageData(const std::string& extension_id) { |
766 const std::string& extension_id) { | |
767 background_page_data_.erase(extension_id); | 751 background_page_data_.erase(extension_id); |
768 | 752 |
769 // Re-register all RenderViews for this extension. We do this to restore | 753 // Re-register all RenderViews for this extension. We do this to restore |
770 // the lazy_keepalive_count (if any) to properly reflect the number of open | 754 // the lazy_keepalive_count (if any) to properly reflect the number of open |
771 // views. | 755 // views. |
772 for (ExtensionRenderViews::const_iterator it = all_extension_views_.begin(); | 756 for (ExtensionRenderViews::const_iterator it = all_extension_views_.begin(); |
773 it != all_extension_views_.end(); ++it) { | 757 it != all_extension_views_.end(); ++it) { |
774 if (GetExtensionID(it->first) == extension_id) | 758 if (GetExtensionID(it->first) == extension_id) |
775 IncrementLazyKeepaliveCountForView(it->first); | 759 IncrementLazyKeepaliveCountForView(it->first); |
776 } | 760 } |
777 } | 761 } |
778 | 762 |
779 bool ExtensionProcessManager::DeferLoadingBackgroundHosts() const { | 763 bool ProcessManager::DeferLoadingBackgroundHosts() const { |
780 // Don't load background hosts now if the loading should be deferred. | 764 // Don't load background hosts now if the loading should be deferred. |
781 if (defer_background_host_creation_) | 765 if (defer_background_host_creation_) |
782 return true; | 766 return true; |
783 | 767 |
784 // The extensions embedder may have special rules about background hosts. | 768 // The extensions embedder may have special rules about background hosts. |
785 return ExtensionsBrowserClient::Get()->DeferLoadingBackgroundHosts( | 769 return ExtensionsBrowserClient::Get()->DeferLoadingBackgroundHosts( |
786 GetBrowserContext()); | 770 GetBrowserContext()); |
787 } | 771 } |
788 | 772 |
789 // | 773 // |
790 // IncognitoExtensionProcessManager | 774 // IncognitoProcessManager |
791 // | 775 // |
792 | 776 |
793 IncognitoExtensionProcessManager::IncognitoExtensionProcessManager( | 777 IncognitoProcessManager::IncognitoProcessManager( |
794 BrowserContext* incognito_context, | 778 BrowserContext* incognito_context, |
795 BrowserContext* original_context) | 779 BrowserContext* original_context) |
796 : ExtensionProcessManager(incognito_context, original_context), | 780 : ProcessManager(incognito_context, original_context), |
797 original_manager_(extensions::ExtensionSystem::GetForBrowserContext( | 781 original_manager_(ExtensionSystem::GetForBrowserContext( |
798 original_context)->process_manager()) { | 782 original_context)->process_manager()) { |
799 DCHECK(incognito_context->IsOffTheRecord()); | 783 DCHECK(incognito_context->IsOffTheRecord()); |
800 | 784 |
801 // The original profile will have its own ExtensionProcessManager to | 785 // The original profile will have its own ProcessManager to |
802 // load the background pages of the spanning extensions. This process | 786 // load the background pages of the spanning extensions. This process |
803 // manager need only worry about the split mode extensions, which is handled | 787 // manager need only worry about the split mode extensions, which is handled |
804 // in the NOTIFICATION_BROWSER_WINDOW_READY notification handler. | 788 // in the NOTIFICATION_BROWSER_WINDOW_READY notification handler. |
805 registrar_.Remove(this, chrome::NOTIFICATION_EXTENSIONS_READY, | 789 registrar_.Remove(this, chrome::NOTIFICATION_EXTENSIONS_READY, |
806 content::Source<BrowserContext>(original_context)); | 790 content::Source<BrowserContext>(original_context)); |
807 registrar_.Remove(this, chrome::NOTIFICATION_PROFILE_CREATED, | 791 registrar_.Remove(this, chrome::NOTIFICATION_PROFILE_CREATED, |
808 content::Source<BrowserContext>(original_context)); | 792 content::Source<BrowserContext>(original_context)); |
809 } | 793 } |
810 | 794 |
811 IncognitoExtensionProcessManager::~IncognitoExtensionProcessManager() { | 795 IncognitoProcessManager::~IncognitoProcessManager() { |
812 // TODO(yoz): This cleanup code belongs in the MenuManager. | 796 // TODO(yoz): This cleanup code belongs in the MenuManager. |
813 // Remove "incognito" "split" mode context menu items. | 797 // Remove "incognito" "split" mode context menu items. |
814 ExtensionService* service = ExtensionSystem::GetForBrowserContext( | 798 ExtensionService* service = ExtensionSystem::GetForBrowserContext( |
815 GetBrowserContext())->extension_service(); | 799 GetBrowserContext())->extension_service(); |
816 if (service) | 800 if (service) |
817 service->menu_manager()->RemoveAllIncognitoContextItems(); | 801 service->menu_manager()->RemoveAllIncognitoContextItems(); |
818 } | 802 } |
819 | 803 |
820 ExtensionHost* IncognitoExtensionProcessManager::CreateBackgroundHost( | 804 ExtensionHost* IncognitoProcessManager::CreateBackgroundHost( |
821 const Extension* extension, const GURL& url) { | 805 const Extension* extension, const GURL& url) { |
822 if (extensions::IncognitoInfo::IsSplitMode(extension)) { | 806 if (IncognitoInfo::IsSplitMode(extension)) { |
823 if (IsIncognitoEnabled(extension)) | 807 if (IsIncognitoEnabled(extension)) |
824 return ExtensionProcessManager::CreateBackgroundHost(extension, url); | 808 return ProcessManager::CreateBackgroundHost(extension, url); |
825 } else { | 809 } else { |
826 // Do nothing. If an extension is spanning, then its original-profile | 810 // Do nothing. If an extension is spanning, then its original-profile |
827 // background page is shared with incognito, so we don't create another. | 811 // background page is shared with incognito, so we don't create another. |
828 } | 812 } |
829 return NULL; | 813 return NULL; |
830 } | 814 } |
831 | 815 |
832 SiteInstance* IncognitoExtensionProcessManager::GetSiteInstanceForURL( | 816 SiteInstance* IncognitoProcessManager::GetSiteInstanceForURL(const GURL& url) { |
833 const GURL& url) { | |
834 ExtensionService* service = ExtensionSystem::GetForBrowserContext( | 817 ExtensionService* service = ExtensionSystem::GetForBrowserContext( |
835 GetBrowserContext())->extension_service(); | 818 GetBrowserContext())->extension_service(); |
836 if (service) { | 819 if (service) { |
837 const Extension* extension = | 820 const Extension* extension = |
838 service->extensions()->GetExtensionOrAppByURL(url); | 821 service->extensions()->GetExtensionOrAppByURL(url); |
839 if (extension && | 822 if (extension && !IncognitoInfo::IsSplitMode(extension)) { |
840 !extensions::IncognitoInfo::IsSplitMode(extension)) { | |
841 return original_manager_->GetSiteInstanceForURL(url); | 823 return original_manager_->GetSiteInstanceForURL(url); |
842 } | 824 } |
843 } | 825 } |
844 return ExtensionProcessManager::GetSiteInstanceForURL(url); | 826 return ProcessManager::GetSiteInstanceForURL(url); |
845 } | 827 } |
846 | 828 |
847 bool IncognitoExtensionProcessManager::IsIncognitoEnabled( | 829 bool IncognitoProcessManager::IsIncognitoEnabled(const Extension* extension) { |
848 const Extension* extension) { | |
849 // Keep in sync with duplicate in extension_info_map.cc. | 830 // Keep in sync with duplicate in extension_info_map.cc. |
850 ExtensionService* service = ExtensionSystem::GetForBrowserContext( | 831 ExtensionService* service = ExtensionSystem::GetForBrowserContext( |
851 GetBrowserContext())->extension_service(); | 832 GetBrowserContext())->extension_service(); |
852 return extension_util::IsIncognitoEnabled(extension->id(), service); | 833 return extension_util::IsIncognitoEnabled(extension->id(), service); |
853 } | 834 } |
| 835 |
| 836 } // namespace extensions |
OLD | NEW |