| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 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 "extensions/browser/extension_host.h" | 5 #include "extensions/browser/extension_host.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "base/metrics/field_trial.h" | 8 #include "base/metrics/field_trial.h" |
| 9 #include "base/metrics/histogram_macros.h" | 9 #include "base/metrics/histogram_macros.h" |
| 10 #include "base/profiler/scoped_tracker.h" | 10 #include "base/profiler/scoped_tracker.h" |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 95 extension_ && BackgroundInfo::HasLazyBackgroundPage(extension_) && | 95 extension_ && BackgroundInfo::HasLazyBackgroundPage(extension_) && |
| 96 load_start_.get()) { | 96 load_start_.get()) { |
| 97 UMA_HISTOGRAM_LONG_TIMES("Extensions.EventPageActiveTime2", | 97 UMA_HISTOGRAM_LONG_TIMES("Extensions.EventPageActiveTime2", |
| 98 load_start_->Elapsed()); | 98 load_start_->Elapsed()); |
| 99 } | 99 } |
| 100 | 100 |
| 101 content::NotificationService::current()->Notify( | 101 content::NotificationService::current()->Notify( |
| 102 extensions::NOTIFICATION_EXTENSION_HOST_DESTROYED, | 102 extensions::NOTIFICATION_EXTENSION_HOST_DESTROYED, |
| 103 content::Source<BrowserContext>(browser_context_), | 103 content::Source<BrowserContext>(browser_context_), |
| 104 content::Details<ExtensionHost>(this)); | 104 content::Details<ExtensionHost>(this)); |
| 105 FOR_EACH_OBSERVER(ExtensionHostObserver, observer_list_, | 105 for (auto& observer : observer_list_) |
| 106 OnExtensionHostDestroyed(this)); | 106 observer.OnExtensionHostDestroyed(this); |
| 107 FOR_EACH_OBSERVER(DeferredStartRenderHostObserver, | 107 for (auto& observer : deferred_start_render_host_observer_list_) |
| 108 deferred_start_render_host_observer_list_, | 108 observer.OnDeferredStartRenderHostDestroyed(this); |
| 109 OnDeferredStartRenderHostDestroyed(this)); | |
| 110 | 109 |
| 111 // Remove ourselves from the queue as late as possible (before effectively | 110 // Remove ourselves from the queue as late as possible (before effectively |
| 112 // destroying self, but after everything else) so that queues that are | 111 // destroying self, but after everything else) so that queues that are |
| 113 // monitoring lifetime get a chance to see stop-loading events. | 112 // monitoring lifetime get a chance to see stop-loading events. |
| 114 delegate_->GetExtensionHostQueue()->Remove(this); | 113 delegate_->GetExtensionHostQueue()->Remove(this); |
| 115 | 114 |
| 116 // Deliberately stop observing |host_contents_| because its destruction | 115 // Deliberately stop observing |host_contents_| because its destruction |
| 117 // events (like DidStopLoading, it turns out) can call back into | 116 // events (like DidStopLoading, it turns out) can call back into |
| 118 // ExtensionHost re-entrantly, when anything declared after |host_contents_| | 117 // ExtensionHost re-entrantly, when anything declared after |host_contents_| |
| 119 // has already been destroyed. | 118 // has already been destroyed. |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 204 } | 203 } |
| 205 | 204 |
| 206 void ExtensionHost::RemoveObserver(ExtensionHostObserver* observer) { | 205 void ExtensionHost::RemoveObserver(ExtensionHostObserver* observer) { |
| 207 observer_list_.RemoveObserver(observer); | 206 observer_list_.RemoveObserver(observer); |
| 208 } | 207 } |
| 209 | 208 |
| 210 void ExtensionHost::OnBackgroundEventDispatched(const std::string& event_name, | 209 void ExtensionHost::OnBackgroundEventDispatched(const std::string& event_name, |
| 211 int event_id) { | 210 int event_id) { |
| 212 CHECK(IsBackgroundPage()); | 211 CHECK(IsBackgroundPage()); |
| 213 unacked_messages_.insert(event_id); | 212 unacked_messages_.insert(event_id); |
| 214 FOR_EACH_OBSERVER(ExtensionHostObserver, observer_list_, | 213 for (auto& observer : observer_list_) |
| 215 OnBackgroundEventDispatched(this, event_name, event_id)); | 214 observer.OnBackgroundEventDispatched(this, event_name, event_id); |
| 216 } | 215 } |
| 217 | 216 |
| 218 void ExtensionHost::OnNetworkRequestStarted(uint64_t request_id) { | 217 void ExtensionHost::OnNetworkRequestStarted(uint64_t request_id) { |
| 219 FOR_EACH_OBSERVER(ExtensionHostObserver, observer_list_, | 218 for (auto& observer : observer_list_) |
| 220 OnNetworkRequestStarted(this, request_id)); | 219 observer.OnNetworkRequestStarted(this, request_id); |
| 221 } | 220 } |
| 222 | 221 |
| 223 void ExtensionHost::OnNetworkRequestDone(uint64_t request_id) { | 222 void ExtensionHost::OnNetworkRequestDone(uint64_t request_id) { |
| 224 FOR_EACH_OBSERVER(ExtensionHostObserver, observer_list_, | 223 for (auto& observer : observer_list_) |
| 225 OnNetworkRequestDone(this, request_id)); | 224 observer.OnNetworkRequestDone(this, request_id); |
| 226 } | 225 } |
| 227 | 226 |
| 228 const GURL& ExtensionHost::GetURL() const { | 227 const GURL& ExtensionHost::GetURL() const { |
| 229 return host_contents()->GetURL(); | 228 return host_contents()->GetURL(); |
| 230 } | 229 } |
| 231 | 230 |
| 232 void ExtensionHost::LoadInitialURL() { | 231 void ExtensionHost::LoadInitialURL() { |
| 233 load_start_.reset(new base::ElapsedTimer()); | 232 load_start_.reset(new base::ElapsedTimer()); |
| 234 host_contents_->GetController().LoadURL( | 233 host_contents_->GetController().LoadURL( |
| 235 initial_url_, content::Referrer(), ui::PAGE_TRANSITION_LINK, | 234 initial_url_, content::Referrer(), ui::PAGE_TRANSITION_LINK, |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 280 // and they aren't all going to use ExtensionHost. This should be in someplace | 279 // and they aren't all going to use ExtensionHost. This should be in someplace |
| 281 // more central, like EPM maybe. | 280 // more central, like EPM maybe. |
| 282 content::NotificationService::current()->Notify( | 281 content::NotificationService::current()->Notify( |
| 283 extensions::NOTIFICATION_EXTENSION_PROCESS_TERMINATED, | 282 extensions::NOTIFICATION_EXTENSION_PROCESS_TERMINATED, |
| 284 content::Source<BrowserContext>(browser_context_), | 283 content::Source<BrowserContext>(browser_context_), |
| 285 content::Details<ExtensionHost>(this)); | 284 content::Details<ExtensionHost>(this)); |
| 286 } | 285 } |
| 287 | 286 |
| 288 void ExtensionHost::DidStartLoading() { | 287 void ExtensionHost::DidStartLoading() { |
| 289 if (!has_loaded_once_) { | 288 if (!has_loaded_once_) { |
| 290 FOR_EACH_OBSERVER(DeferredStartRenderHostObserver, | 289 for (auto& observer : deferred_start_render_host_observer_list_) |
| 291 deferred_start_render_host_observer_list_, | 290 observer.OnDeferredStartRenderHostDidStartFirstLoad(this); |
| 292 OnDeferredStartRenderHostDidStartFirstLoad(this)); | |
| 293 } | 291 } |
| 294 } | 292 } |
| 295 | 293 |
| 296 void ExtensionHost::DidStopLoading() { | 294 void ExtensionHost::DidStopLoading() { |
| 297 // Only record UMA for the first load. Subsequent loads will likely behave | 295 // Only record UMA for the first load. Subsequent loads will likely behave |
| 298 // quite different, and it's first load we're most interested in. | 296 // quite different, and it's first load we're most interested in. |
| 299 bool first_load = !has_loaded_once_; | 297 bool first_load = !has_loaded_once_; |
| 300 has_loaded_once_ = true; | 298 has_loaded_once_ = true; |
| 301 if (first_load) { | 299 if (first_load) { |
| 302 RecordStopLoadingUMA(); | 300 RecordStopLoadingUMA(); |
| 303 OnDidStopFirstLoad(); | 301 OnDidStopFirstLoad(); |
| 304 content::NotificationService::current()->Notify( | 302 content::NotificationService::current()->Notify( |
| 305 extensions::NOTIFICATION_EXTENSION_HOST_DID_STOP_FIRST_LOAD, | 303 extensions::NOTIFICATION_EXTENSION_HOST_DID_STOP_FIRST_LOAD, |
| 306 content::Source<BrowserContext>(browser_context_), | 304 content::Source<BrowserContext>(browser_context_), |
| 307 content::Details<ExtensionHost>(this)); | 305 content::Details<ExtensionHost>(this)); |
| 308 FOR_EACH_OBSERVER(DeferredStartRenderHostObserver, | 306 for (auto& observer : deferred_start_render_host_observer_list_) |
| 309 deferred_start_render_host_observer_list_, | 307 observer.OnDeferredStartRenderHostDidStopFirstLoad(this); |
| 310 OnDeferredStartRenderHostDidStopFirstLoad(this)); | |
| 311 } | 308 } |
| 312 } | 309 } |
| 313 | 310 |
| 314 void ExtensionHost::OnDidStopFirstLoad() { | 311 void ExtensionHost::OnDidStopFirstLoad() { |
| 315 DCHECK_EQ(extension_host_type_, VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); | 312 DCHECK_EQ(extension_host_type_, VIEW_TYPE_EXTENSION_BACKGROUND_PAGE); |
| 316 // Nothing to do for background pages. | 313 // Nothing to do for background pages. |
| 317 } | 314 } |
| 318 | 315 |
| 319 void ExtensionHost::DocumentAvailableInMainFrame() { | 316 void ExtensionHost::DocumentAvailableInMainFrame() { |
| 320 // If the document has already been marked as available for this host, then | 317 // If the document has already been marked as available for this host, then |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 364 << ", which does not have a lazy background page."; | 361 << ", which does not have a lazy background page."; |
| 365 return; | 362 return; |
| 366 } | 363 } |
| 367 | 364 |
| 368 // A compromised renderer could start sending out arbitrary event ids, which | 365 // A compromised renderer could start sending out arbitrary event ids, which |
| 369 // may affect other renderers by causing downstream methods to think that | 366 // may affect other renderers by causing downstream methods to think that |
| 370 // events for other extensions have been acked. Make sure that the event id | 367 // events for other extensions have been acked. Make sure that the event id |
| 371 // sent by the renderer is one that this ExtensionHost expects to receive. | 368 // sent by the renderer is one that this ExtensionHost expects to receive. |
| 372 // This way if a renderer _is_ compromised, it can really only affect itself. | 369 // This way if a renderer _is_ compromised, it can really only affect itself. |
| 373 if (unacked_messages_.erase(event_id) > 0) { | 370 if (unacked_messages_.erase(event_id) > 0) { |
| 374 FOR_EACH_OBSERVER(ExtensionHostObserver, observer_list_, | 371 for (auto& observer : observer_list_) |
| 375 OnBackgroundEventAcked(this, event_id)); | 372 observer.OnBackgroundEventAcked(this, event_id); |
| 376 } else { | 373 } else { |
| 377 // We have received an unexpected event id from the renderer. It might be | 374 // We have received an unexpected event id from the renderer. It might be |
| 378 // compromised or it might have some other issue. Kill it just to be safe. | 375 // compromised or it might have some other issue. Kill it just to be safe. |
| 379 DCHECK(render_process_host()); | 376 DCHECK(render_process_host()); |
| 380 LOG(ERROR) << "Killing renderer for extension " << extension_id() << " for " | 377 LOG(ERROR) << "Killing renderer for extension " << extension_id() << " for " |
| 381 << "sending an EventAck message with a bad event id."; | 378 << "sending an EventAck message with a bad event id."; |
| 382 bad_message::ReceivedBadMessage(render_process_host(), | 379 bad_message::ReceivedBadMessage(render_process_host(), |
| 383 bad_message::EH_BAD_EVENT_ID); | 380 bad_message::EH_BAD_EVENT_ID); |
| 384 } | 381 } |
| 385 } | 382 } |
| (...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 486 } | 483 } |
| 487 } else if (extension_host_type_ == VIEW_TYPE_EXTENSION_POPUP) { | 484 } else if (extension_host_type_ == VIEW_TYPE_EXTENSION_POPUP) { |
| 488 UMA_HISTOGRAM_MEDIUM_TIMES("Extensions.PopupLoadTime2", | 485 UMA_HISTOGRAM_MEDIUM_TIMES("Extensions.PopupLoadTime2", |
| 489 load_start_->Elapsed()); | 486 load_start_->Elapsed()); |
| 490 UMA_HISTOGRAM_MEDIUM_TIMES("Extensions.PopupCreateTime", | 487 UMA_HISTOGRAM_MEDIUM_TIMES("Extensions.PopupCreateTime", |
| 491 create_start_.Elapsed()); | 488 create_start_.Elapsed()); |
| 492 } | 489 } |
| 493 } | 490 } |
| 494 | 491 |
| 495 } // namespace extensions | 492 } // namespace extensions |
| OLD | NEW |