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 // See http://dev.chromium.org/developers/design-documents/multi-process-resourc e-loading | 5 // See http://dev.chromium.org/developers/design-documents/multi-process-resourc e-loading |
6 | 6 |
7 #include "content/browser/loader/resource_dispatcher_host_impl.h" | 7 #include "content/browser/loader/resource_dispatcher_host_impl.h" |
8 | 8 |
9 #include <stddef.h> | 9 #include <stddef.h> |
10 #include <algorithm> | 10 #include <algorithm> |
(...skipping 21 matching lines...) Expand all Loading... | |
32 #include "base/time/time.h" | 32 #include "base/time/time.h" |
33 #include "content/browser/appcache/appcache_interceptor.h" | 33 #include "content/browser/appcache/appcache_interceptor.h" |
34 #include "content/browser/appcache/chrome_appcache_service.h" | 34 #include "content/browser/appcache/chrome_appcache_service.h" |
35 #include "content/browser/bad_message.h" | 35 #include "content/browser/bad_message.h" |
36 #include "content/browser/cert_store_impl.h" | 36 #include "content/browser/cert_store_impl.h" |
37 #include "content/browser/child_process_security_policy_impl.h" | 37 #include "content/browser/child_process_security_policy_impl.h" |
38 #include "content/browser/download/download_resource_handler.h" | 38 #include "content/browser/download/download_resource_handler.h" |
39 #include "content/browser/download/save_file_manager.h" | 39 #include "content/browser/download/save_file_manager.h" |
40 #include "content/browser/download/save_file_resource_handler.h" | 40 #include "content/browser/download/save_file_resource_handler.h" |
41 #include "content/browser/fileapi/chrome_blob_storage_context.h" | 41 #include "content/browser/fileapi/chrome_blob_storage_context.h" |
42 #include "content/browser/frame_host/frame_tree.h" | |
42 #include "content/browser/frame_host/navigation_request_info.h" | 43 #include "content/browser/frame_host/navigation_request_info.h" |
43 #include "content/browser/frame_host/navigator.h" | 44 #include "content/browser/frame_host/navigator.h" |
44 #include "content/browser/loader/async_resource_handler.h" | 45 #include "content/browser/loader/async_resource_handler.h" |
45 #include "content/browser/loader/async_revalidation_manager.h" | 46 #include "content/browser/loader/async_revalidation_manager.h" |
46 #include "content/browser/loader/cross_site_resource_handler.h" | 47 #include "content/browser/loader/cross_site_resource_handler.h" |
47 #include "content/browser/loader/detachable_resource_handler.h" | 48 #include "content/browser/loader/detachable_resource_handler.h" |
48 #include "content/browser/loader/mime_type_resource_handler.h" | 49 #include "content/browser/loader/mime_type_resource_handler.h" |
49 #include "content/browser/loader/navigation_resource_handler.h" | 50 #include "content/browser/loader/navigation_resource_handler.h" |
50 #include "content/browser/loader/navigation_resource_throttle.h" | 51 #include "content/browser/loader/navigation_resource_throttle.h" |
51 #include "content/browser/loader/navigation_url_loader_impl_core.h" | 52 #include "content/browser/loader/navigation_url_loader_impl_core.h" |
(...skipping 407 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
459 // slow bucket because a shocking number of aborts happen under 100ms. | 460 // slow bucket because a shocking number of aborts happen under 100ms. |
460 void RecordAbortRapporOnUI(const GURL& url, | 461 void RecordAbortRapporOnUI(const GURL& url, |
461 base::TimeDelta request_loading_time) { | 462 base::TimeDelta request_loading_time) { |
462 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 463 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
463 if (request_loading_time.InMilliseconds() < 100) | 464 if (request_loading_time.InMilliseconds() < 100) |
464 GetContentClient()->browser()->RecordURLMetric("Net.ErrAborted.Fast", url); | 465 GetContentClient()->browser()->RecordURLMetric("Net.ErrAborted.Fast", url); |
465 else | 466 else |
466 GetContentClient()->browser()->RecordURLMetric("Net.ErrAborted.Slow", url); | 467 GetContentClient()->browser()->RecordURLMetric("Net.ErrAborted.Slow", url); |
467 } | 468 } |
468 | 469 |
470 // The following functions simplify code paths where the UI thread notifies the | |
471 // ResourceDispatcherHostImpl of information pertaining to loading behavior of | |
472 // frame hosts. | |
473 void NotifyForRouteOnIO( | |
474 base::Callback<void(ResourceDispatcherHostImpl*, | |
475 const GlobalFrameRoutingId&)> frame_callback, | |
476 const GlobalFrameRoutingId& global_routing_id) { | |
477 DCHECK_CURRENTLY_ON(BrowserThread::IO); | |
478 ResourceDispatcherHostImpl* rdh = ResourceDispatcherHostImpl::Get(); | |
479 if (rdh) | |
480 frame_callback.Run(rdh, global_routing_id); | |
481 } | |
482 | |
483 void NotifyForRoute( | |
484 const GlobalFrameRoutingId& global_routing_id, | |
485 base::Callback<void(ResourceDispatcherHostImpl*, | |
486 const GlobalFrameRoutingId&)> frame_callback) { | |
487 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
488 BrowserThread::PostTask( | |
489 BrowserThread::IO, FROM_HERE, | |
490 base::Bind(&NotifyForRouteOnIO, frame_callback, global_routing_id)); | |
491 } | |
492 | |
493 void NotifyForEachFrameOnIO( | |
Randy Smith (Not in Mondays)
2016/02/01 21:19:20
nitty nit, suggestion: The name of this function i
Charlie Harrison
2016/02/01 23:05:39
Changed it to "NotifyForRouteSetOnIO", to better p
| |
494 base::Callback<void(ResourceDispatcherHostImpl*, | |
495 const GlobalFrameRoutingId&)> frame_callback, | |
496 scoped_ptr<std::set<GlobalFrameRoutingId>> routing_ids) { | |
497 DCHECK_CURRENTLY_ON(BrowserThread::IO); | |
498 for (const auto& routing_id : *routing_ids) | |
499 NotifyForRouteOnIO(frame_callback, routing_id); | |
500 } | |
501 | |
502 void NotifyForEachFrame( | |
Randy Smith (Not in Mondays)
2016/02/01 21:19:20
Same as above.
Charlie Harrison
2016/02/01 23:05:39
I prefer to leave this one as is. I can't really t
Randy Smith (Not in Mondays)
2016/02/02 20:47:06
Yeah, looking at it more closely, this is fine. O
| |
503 RenderFrameHost* root_frame_host, | |
504 base::Callback<void(ResourceDispatcherHostImpl*, | |
505 const GlobalFrameRoutingId&)> frame_callback) { | |
506 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
507 FrameTree* frame_tree = static_cast<RenderFrameHostImpl*>(root_frame_host) | |
508 ->frame_tree_node() | |
509 ->frame_tree(); | |
510 DCHECK_EQ(root_frame_host, frame_tree->GetMainFrame()); | |
511 scoped_ptr<std::set<GlobalFrameRoutingId>> routing_ids( | |
512 new std::set<GlobalFrameRoutingId>()); | |
513 for (FrameTreeNode* node : frame_tree->Nodes()) { | |
514 RenderFrameHostImpl* frame_host = node->current_frame_host(); | |
515 RenderFrameHostImpl* pending_frame_host = | |
516 IsBrowserSideNavigationEnabled() | |
517 ? node->render_manager()->speculative_frame_host() | |
518 : node->render_manager()->pending_frame_host(); | |
519 if (frame_host) | |
520 routing_ids->insert(frame_host->GetGlobalFrameRoutingId()); | |
521 if (pending_frame_host) | |
522 routing_ids->insert(pending_frame_host->GetGlobalFrameRoutingId()); | |
523 } | |
524 BrowserThread::PostTask(BrowserThread::IO, FROM_HERE, | |
525 base::Bind(&NotifyForEachFrameOnIO, frame_callback, | |
526 base::Passed(std::move(routing_ids)))); | |
527 } | |
528 | |
469 } // namespace | 529 } // namespace |
470 | 530 |
531 LoaderIOThreadNotifier::LoaderIOThreadNotifier(WebContents* web_contents) | |
532 : WebContentsObserver(web_contents) {} | |
533 | |
534 LoaderIOThreadNotifier::~LoaderIOThreadNotifier() {} | |
535 | |
536 void LoaderIOThreadNotifier::RenderFrameDeleted( | |
537 RenderFrameHost* render_frame_host) { | |
538 NotifyForRoute(static_cast<RenderFrameHostImpl*>(render_frame_host) | |
539 ->GetGlobalFrameRoutingId(), | |
540 base::Bind(&ResourceDispatcherHostImpl::OnRenderFrameDeleted)); | |
Randy Smith (Not in Mondays)
2016/02/01 21:19:20
nit, suggestion: I'm inclined to think it's a clea
Charlie Harrison
2016/02/01 23:05:39
I implemented this suggestion.
| |
541 } | |
542 | |
471 // static | 543 // static |
472 ResourceDispatcherHost* ResourceDispatcherHost::Get() { | 544 ResourceDispatcherHost* ResourceDispatcherHost::Get() { |
473 return g_resource_dispatcher_host; | 545 return g_resource_dispatcher_host; |
474 } | 546 } |
475 | 547 |
476 ResourceDispatcherHostImpl::ResourceDispatcherHostImpl() | 548 ResourceDispatcherHostImpl::ResourceDispatcherHostImpl() |
477 : save_file_manager_(new SaveFileManager()), | 549 : save_file_manager_(new SaveFileManager()), |
478 request_id_(-1), | 550 request_id_(-1), |
479 is_shutdown_(false), | 551 is_shutdown_(false), |
480 num_in_flight_requests_(0), | 552 num_in_flight_requests_(0), |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
527 DCHECK(outstanding_requests_stats_map_.empty()); | 599 DCHECK(outstanding_requests_stats_map_.empty()); |
528 DCHECK(g_resource_dispatcher_host); | 600 DCHECK(g_resource_dispatcher_host); |
529 g_resource_dispatcher_host = NULL; | 601 g_resource_dispatcher_host = NULL; |
530 } | 602 } |
531 | 603 |
532 // static | 604 // static |
533 ResourceDispatcherHostImpl* ResourceDispatcherHostImpl::Get() { | 605 ResourceDispatcherHostImpl* ResourceDispatcherHostImpl::Get() { |
534 return g_resource_dispatcher_host; | 606 return g_resource_dispatcher_host; |
535 } | 607 } |
536 | 608 |
609 // static | |
610 void ResourceDispatcherHostImpl::ResumeBlockedRequestsForRouteOnUI( | |
611 const GlobalFrameRoutingId& global_routing_id) { | |
612 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
613 NotifyForRoute( | |
614 global_routing_id, | |
615 base::Bind(&ResourceDispatcherHostImpl::ResumeBlockedRequestsForRoute)); | |
616 } | |
617 | |
618 // static | |
619 void ResourceDispatcherHostImpl::BlockRequestsForFrames( | |
620 RenderFrameHost* root_frame_host) { | |
621 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
622 NotifyForEachFrame( | |
623 root_frame_host, | |
624 base::Bind(&ResourceDispatcherHostImpl::BlockRequestsForRoute)); | |
625 } | |
626 | |
627 // static | |
628 void ResourceDispatcherHostImpl::ResumeBlockedRequestsForFrames( | |
629 RenderFrameHost* root_frame_host) { | |
630 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
631 NotifyForEachFrame( | |
632 root_frame_host, | |
633 base::Bind(&ResourceDispatcherHostImpl::ResumeBlockedRequestsForRoute)); | |
634 } | |
635 | |
636 // static | |
637 void ResourceDispatcherHostImpl::CancelBlockedRequestsForFrames( | |
638 RenderFrameHostImpl* root_frame_host) { | |
639 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
640 NotifyForEachFrame( | |
641 root_frame_host, | |
642 base::Bind(&ResourceDispatcherHostImpl::CancelBlockedRequestsForRoute)); | |
643 } | |
644 | |
537 void ResourceDispatcherHostImpl::SetDelegate( | 645 void ResourceDispatcherHostImpl::SetDelegate( |
538 ResourceDispatcherHostDelegate* delegate) { | 646 ResourceDispatcherHostDelegate* delegate) { |
539 delegate_ = delegate; | 647 delegate_ = delegate; |
540 } | 648 } |
541 | 649 |
542 void ResourceDispatcherHostImpl::SetAllowCrossOriginAuthPrompt(bool value) { | 650 void ResourceDispatcherHostImpl::SetAllowCrossOriginAuthPrompt(bool value) { |
543 allow_cross_origin_auth_prompt_ = value; | 651 allow_cross_origin_auth_prompt_ = value; |
544 } | 652 } |
545 | 653 |
546 void ResourceDispatcherHostImpl::AddResourceContext(ResourceContext* context) { | 654 void ResourceDispatcherHostImpl::AddResourceContext(ResourceContext* context) { |
(...skipping 536 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1083 | 1191 |
1084 // Make sure we shutdown the timer now, otherwise by the time our destructor | 1192 // Make sure we shutdown the timer now, otherwise by the time our destructor |
1085 // runs if the timer is still running the Task is deleted twice (once by | 1193 // runs if the timer is still running the Task is deleted twice (once by |
1086 // the MessageLoop and the second time by RepeatingTimer). | 1194 // the MessageLoop and the second time by RepeatingTimer). |
1087 update_load_states_timer_.reset(); | 1195 update_load_states_timer_.reset(); |
1088 | 1196 |
1089 // Clear blocked requests if any left. | 1197 // Clear blocked requests if any left. |
1090 // Note that we have to do this in 2 passes as we cannot call | 1198 // Note that we have to do this in 2 passes as we cannot call |
1091 // CancelBlockedRequestsForRoute while iterating over | 1199 // CancelBlockedRequestsForRoute while iterating over |
1092 // blocked_loaders_map_, as it modifies it. | 1200 // blocked_loaders_map_, as it modifies it. |
1093 std::set<GlobalRoutingID> ids; | 1201 std::set<GlobalFrameRoutingId> ids; |
1094 for (const auto& blocked_loaders : blocked_loaders_map_) { | 1202 for (const auto& blocked_loaders : blocked_loaders_map_) { |
1095 std::pair<std::set<GlobalRoutingID>::iterator, bool> result = | 1203 std::pair<std::set<GlobalFrameRoutingId>::iterator, bool> result = |
1096 ids.insert(blocked_loaders.first); | 1204 ids.insert(blocked_loaders.first); |
1097 // We should not have duplicates. | 1205 // We should not have duplicates. |
1098 DCHECK(result.second); | 1206 DCHECK(result.second); |
1099 } | 1207 } |
1100 for (const auto& routing_id : ids) { | 1208 for (const auto& routing_id : ids) { |
1101 CancelBlockedRequestsForRoute(routing_id.child_id, routing_id.route_id); | 1209 CancelBlockedRequestsForRoute(routing_id); |
1102 } | 1210 } |
1103 | 1211 |
1104 scheduler_.reset(); | 1212 scheduler_.reset(); |
1105 } | 1213 } |
1106 | 1214 |
1107 bool ResourceDispatcherHostImpl::OnMessageReceived( | 1215 bool ResourceDispatcherHostImpl::OnMessageReceived( |
1108 const IPC::Message& message, | 1216 const IPC::Message& message, |
1109 ResourceMessageFilter* filter) { | 1217 ResourceMessageFilter* filter) { |
1110 filter_ = filter; | 1218 filter_ = filter; |
1111 bool handled = true; | 1219 bool handled = true; |
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1187 sync_result->routing_id()); | 1295 sync_result->routing_id()); |
1188 } | 1296 } |
1189 | 1297 |
1190 void ResourceDispatcherHostImpl::UpdateRequestForTransfer( | 1298 void ResourceDispatcherHostImpl::UpdateRequestForTransfer( |
1191 int child_id, | 1299 int child_id, |
1192 int route_id, | 1300 int route_id, |
1193 int request_id, | 1301 int request_id, |
1194 const ResourceHostMsg_Request& request_data, | 1302 const ResourceHostMsg_Request& request_data, |
1195 LoaderMap::iterator iter) { | 1303 LoaderMap::iterator iter) { |
1196 ResourceRequestInfoImpl* info = iter->second->GetRequestInfo(); | 1304 ResourceRequestInfoImpl* info = iter->second->GetRequestInfo(); |
1197 GlobalRoutingID old_routing_id( | 1305 GlobalFrameRoutingId old_routing_id(request_data.transferred_request_child_id, |
1198 request_data.transferred_request_child_id, info->GetRouteID()); | 1306 info->GetRenderFrameID()); |
1199 GlobalRequestID old_request_id(request_data.transferred_request_child_id, | 1307 GlobalRequestID old_request_id(request_data.transferred_request_child_id, |
1200 request_data.transferred_request_request_id); | 1308 request_data.transferred_request_request_id); |
1201 GlobalRoutingID new_routing_id(child_id, route_id); | 1309 GlobalFrameRoutingId new_routing_id(child_id, request_data.render_frame_id); |
1202 GlobalRequestID new_request_id(child_id, request_id); | 1310 GlobalRequestID new_request_id(child_id, request_id); |
1203 | 1311 |
1204 // Clear out data that depends on |info| before updating it. | 1312 // Clear out data that depends on |info| before updating it. |
1205 // We always need to move the memory stats to the new process. In contrast, | 1313 // We always need to move the memory stats to the new process. In contrast, |
1206 // stats.num_requests is only tracked for some requests (those that require | 1314 // stats.num_requests is only tracked for some requests (those that require |
1207 // file descriptors for their shared memory buffer). | 1315 // file descriptors for their shared memory buffer). |
1208 IncrementOutstandingRequestsMemory(-1, *info); | 1316 IncrementOutstandingRequestsMemory(-1, *info); |
1209 bool should_update_count = info->counted_as_in_flight_request(); | 1317 bool should_update_count = info->counted_as_in_flight_request(); |
1210 if (should_update_count) | 1318 if (should_update_count) |
1211 IncrementOutstandingRequestsCount(-1, info); | 1319 IncrementOutstandingRequestsCount(-1, info); |
(...skipping 542 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1754 blink::WebReferrerPolicyDefault, | 1862 blink::WebReferrerPolicyDefault, |
1755 blink::WebPageVisibilityStateVisible, | 1863 blink::WebPageVisibilityStateVisible, |
1756 context, | 1864 context, |
1757 base::WeakPtr<ResourceMessageFilter>(), // filter | 1865 base::WeakPtr<ResourceMessageFilter>(), // filter |
1758 false, // report_raw_headers | 1866 false, // report_raw_headers |
1759 true, // is_async | 1867 true, // is_async |
1760 false, // is_using_lofi | 1868 false, // is_using_lofi |
1761 std::string()); // original_headers | 1869 std::string()); // original_headers |
1762 } | 1870 } |
1763 | 1871 |
1872 void ResourceDispatcherHostImpl::OnRenderFrameDeleted( | |
1873 const GlobalFrameRoutingId& global_routing_id) { | |
1874 CancelRequestsForRoute(global_routing_id); | |
Randy Smith (Not in Mondays)
2016/02/01 21:19:20
Alternatively to my other suggestion, just make Lo
Charlie Harrison
2016/02/01 23:05:39
I implemented your previous suggestion.
| |
1875 } | |
1876 | |
1764 void ResourceDispatcherHostImpl::OnRenderViewHostCreated(int child_id, | 1877 void ResourceDispatcherHostImpl::OnRenderViewHostCreated(int child_id, |
1765 int route_id, | 1878 int route_id, |
1766 bool is_visible, | 1879 bool is_visible, |
1767 bool is_audible) { | 1880 bool is_audible) { |
1768 scheduler_->OnClientCreated(child_id, route_id, is_visible, is_audible); | 1881 scheduler_->OnClientCreated(child_id, route_id, is_visible, is_audible); |
1769 } | 1882 } |
1770 | 1883 |
1771 void ResourceDispatcherHostImpl::OnRenderViewHostDeleted( | 1884 void ResourceDispatcherHostImpl::OnRenderViewHostDeleted(int child_id, |
1772 int child_id, | 1885 int route_id) { |
1773 int route_id) { | |
1774 scheduler_->OnClientDeleted(child_id, route_id); | 1886 scheduler_->OnClientDeleted(child_id, route_id); |
1775 CancelRequestsForRoute(child_id, route_id); | |
1776 } | 1887 } |
1777 | 1888 |
1778 void ResourceDispatcherHostImpl::OnRenderViewHostSetIsLoading(int child_id, | 1889 void ResourceDispatcherHostImpl::OnRenderViewHostSetIsLoading(int child_id, |
1779 int route_id, | 1890 int route_id, |
1780 bool is_loading) { | 1891 bool is_loading) { |
1781 scheduler_->OnLoadingStateChanged(child_id, route_id, !is_loading); | 1892 scheduler_->OnLoadingStateChanged(child_id, route_id, !is_loading); |
1782 } | 1893 } |
1783 | 1894 |
1784 void ResourceDispatcherHostImpl::OnRenderViewHostWasHidden( | 1895 void ResourceDispatcherHostImpl::OnRenderViewHostWasHidden( |
1785 int child_id, | 1896 int child_id, |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1874 ResourceLoader* loader = GetLoader(id); | 1985 ResourceLoader* loader = GetLoader(id); |
1875 // The response we were meant to resume could have already been canceled. | 1986 // The response we were meant to resume could have already been canceled. |
1876 if (loader) | 1987 if (loader) |
1877 loader->CompleteTransfer(); | 1988 loader->CompleteTransfer(); |
1878 } | 1989 } |
1879 | 1990 |
1880 // The object died, so cancel and detach all requests associated with it except | 1991 // The object died, so cancel and detach all requests associated with it except |
1881 // for downloads and detachable resources, which belong to the browser process | 1992 // for downloads and detachable resources, which belong to the browser process |
1882 // even if initiated via a renderer. | 1993 // even if initiated via a renderer. |
1883 void ResourceDispatcherHostImpl::CancelRequestsForProcess(int child_id) { | 1994 void ResourceDispatcherHostImpl::CancelRequestsForProcess(int child_id) { |
1884 CancelRequestsForRoute(child_id, -1 /* cancel all */); | 1995 CancelRequestsForRoute( |
1996 GlobalFrameRoutingId(child_id, MSG_ROUTING_NONE /* cancel all */)); | |
1885 registered_temp_files_.erase(child_id); | 1997 registered_temp_files_.erase(child_id); |
1886 } | 1998 } |
1887 | 1999 |
1888 void ResourceDispatcherHostImpl::CancelRequestsForRoute(int child_id, | 2000 void ResourceDispatcherHostImpl::CancelRequestsForRoute( |
1889 int route_id) { | 2001 const GlobalFrameRoutingId& global_routing_id) { |
1890 // Since pending_requests_ is a map, we first build up a list of all of the | 2002 // Since pending_requests_ is a map, we first build up a list of all of the |
1891 // matching requests to be cancelled, and then we cancel them. Since there | 2003 // matching requests to be cancelled, and then we cancel them. Since there |
1892 // may be more than one request to cancel, we cannot simply hold onto the map | 2004 // may be more than one request to cancel, we cannot simply hold onto the map |
1893 // iterators found in the first loop. | 2005 // iterators found in the first loop. |
1894 | 2006 |
1895 // Find the global ID of all matching elements. | 2007 // Find the global ID of all matching elements. |
2008 int child_id = global_routing_id.child_id; | |
2009 int route_id = global_routing_id.frame_routing_id; | |
2010 bool cancel_all_routes = (route_id == MSG_ROUTING_NONE); | |
2011 | |
1896 bool any_requests_transferring = false; | 2012 bool any_requests_transferring = false; |
1897 std::vector<GlobalRequestID> matching_requests; | 2013 std::vector<GlobalRequestID> matching_requests; |
1898 for (const auto& loader : pending_loaders_) { | 2014 for (const auto& loader : pending_loaders_) { |
1899 if (loader.first.child_id != child_id) | 2015 if (loader.first.child_id != child_id) |
1900 continue; | 2016 continue; |
1901 | 2017 |
1902 ResourceRequestInfoImpl* info = loader.second->GetRequestInfo(); | 2018 ResourceRequestInfoImpl* info = loader.second->GetRequestInfo(); |
1903 | 2019 |
1904 GlobalRequestID id(child_id, loader.first.request_id); | 2020 GlobalRequestID id(child_id, loader.first.request_id); |
1905 DCHECK(id == loader.first); | 2021 DCHECK(id == loader.first); |
1906 // Don't cancel navigations that are expected to live beyond this process. | 2022 // Don't cancel navigations that are expected to live beyond this process. |
1907 if (IsTransferredNavigation(id)) | 2023 if (IsTransferredNavigation(id)) |
1908 any_requests_transferring = true; | 2024 any_requests_transferring = true; |
1909 if (info->detachable_handler()) { | 2025 if (info->detachable_handler()) { |
1910 info->detachable_handler()->Detach(); | 2026 info->detachable_handler()->Detach(); |
1911 } else if (!info->IsDownload() && !info->is_stream() && | 2027 } else if (!info->IsDownload() && !info->is_stream() && |
1912 !IsTransferredNavigation(id) && | 2028 !IsTransferredNavigation(id) && |
1913 (route_id == -1 || route_id == info->GetRouteID())) { | 2029 (cancel_all_routes || route_id == info->GetRenderFrameID())) { |
1914 matching_requests.push_back(id); | 2030 matching_requests.push_back(id); |
1915 } | 2031 } |
1916 } | 2032 } |
1917 | 2033 |
1918 // Remove matches. | 2034 // Remove matches. |
1919 for (size_t i = 0; i < matching_requests.size(); ++i) { | 2035 for (size_t i = 0; i < matching_requests.size(); ++i) { |
1920 LoaderMap::iterator iter = pending_loaders_.find(matching_requests[i]); | 2036 LoaderMap::iterator iter = pending_loaders_.find(matching_requests[i]); |
1921 // Although every matching request was in pending_requests_ when we built | 2037 // Although every matching request was in pending_requests_ when we built |
1922 // matching_requests, it is normal for a matching request to be not found | 2038 // matching_requests, it is normal for a matching request to be not found |
1923 // in pending_requests_ after we have removed some matching requests from | 2039 // in pending_requests_ after we have removed some matching requests from |
1924 // pending_requests_. For example, deleting a net::URLRequest that has | 2040 // pending_requests_. For example, deleting a net::URLRequest that has |
1925 // exclusive (write) access to an HTTP cache entry may unblock another | 2041 // exclusive (write) access to an HTTP cache entry may unblock another |
1926 // net::URLRequest that needs exclusive access to the same cache entry, and | 2042 // net::URLRequest that needs exclusive access to the same cache entry, and |
1927 // that net::URLRequest may complete and remove itself from | 2043 // that net::URLRequest may complete and remove itself from |
1928 // pending_requests_. So we need to check that iter is not equal to | 2044 // pending_requests_. So we need to check that iter is not equal to |
1929 // pending_requests_.end(). | 2045 // pending_requests_.end(). |
1930 if (iter != pending_loaders_.end()) | 2046 if (iter != pending_loaders_.end()) |
1931 RemovePendingLoader(iter); | 2047 RemovePendingLoader(iter); |
1932 } | 2048 } |
1933 | 2049 |
1934 // Don't clear the blocked loaders or offline policy maps if any of the | 2050 // Don't clear the blocked loaders or offline policy maps if any of the |
1935 // requests in route_id are being transferred to a new process, since those | 2051 // requests in route_id are being transferred to a new process, since those |
1936 // maps will be updated with the new route_id after the transfer. Otherwise | 2052 // maps will be updated with the new route_id after the transfer. Otherwise |
1937 // we will lose track of this info when the old route goes away, before the | 2053 // we will lose track of this info when the old route goes away, before the |
1938 // new one is created. | 2054 // new one is created. |
1939 if (any_requests_transferring) | 2055 if (any_requests_transferring) |
1940 return; | 2056 return; |
1941 | 2057 |
1942 // Now deal with blocked requests if any. | 2058 // Now deal with blocked requests if any. |
1943 if (route_id != -1) { | 2059 if (!cancel_all_routes) { |
1944 if (blocked_loaders_map_.find(GlobalRoutingID(child_id, route_id)) != | 2060 if (blocked_loaders_map_.find(global_routing_id) != |
1945 blocked_loaders_map_.end()) { | 2061 blocked_loaders_map_.end()) { |
1946 CancelBlockedRequestsForRoute(child_id, route_id); | 2062 CancelBlockedRequestsForRoute(global_routing_id); |
1947 } | 2063 } |
1948 } else { | 2064 } else { |
1949 // We have to do all render views for the process |child_id|. | 2065 // We have to do all render frames for the process |child_id|. |
1950 // Note that we have to do this in 2 passes as we cannot call | 2066 // Note that we have to do this in 2 passes as we cannot call |
1951 // CancelBlockedRequestsForRoute while iterating over | 2067 // CancelBlockedRequestsForRoute while iterating over |
1952 // blocked_loaders_map_, as it modifies it. | 2068 // blocked_loaders_map_, as blocking requests modifies the map. |
1953 std::set<int> route_ids; | 2069 std::set<GlobalFrameRoutingId> routing_ids; |
1954 for (const auto& blocked_loaders : blocked_loaders_map_) { | 2070 for (const auto& blocked_loaders : blocked_loaders_map_) { |
1955 if (blocked_loaders.first.child_id == child_id) | 2071 if (blocked_loaders.first.child_id == child_id) |
1956 route_ids.insert(blocked_loaders.first.route_id); | 2072 routing_ids.insert(blocked_loaders.first); |
1957 } | 2073 } |
1958 for (int route_id : route_ids) { | 2074 for (const GlobalFrameRoutingId& route_id : routing_ids) { |
1959 CancelBlockedRequestsForRoute(child_id, route_id); | 2075 CancelBlockedRequestsForRoute(route_id); |
1960 } | 2076 } |
1961 } | 2077 } |
1962 } | 2078 } |
1963 | 2079 |
1964 // Cancels the request and removes it from the list. | 2080 // Cancels the request and removes it from the list. |
1965 void ResourceDispatcherHostImpl::RemovePendingRequest(int child_id, | 2081 void ResourceDispatcherHostImpl::RemovePendingRequest(int child_id, |
1966 int request_id) { | 2082 int request_id) { |
1967 LoaderMap::iterator i = pending_loaders_.find( | 2083 LoaderMap::iterator i = pending_loaders_.find( |
1968 GlobalRequestID(child_id, request_id)); | 2084 GlobalRequestID(child_id, request_id)); |
1969 if (i == pending_loaders_.end()) { | 2085 if (i == pending_loaders_.end()) { |
(...skipping 326 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2296 IncrementOutstandingRequestsMemory(-1, *info); | 2412 IncrementOutstandingRequestsMemory(-1, *info); |
2297 | 2413 |
2298 // A ResourceHandler must not outlive its associated URLRequest. | 2414 // A ResourceHandler must not outlive its associated URLRequest. |
2299 handler.reset(); | 2415 handler.reset(); |
2300 return; | 2416 return; |
2301 } | 2417 } |
2302 | 2418 |
2303 scoped_ptr<ResourceLoader> loader( | 2419 scoped_ptr<ResourceLoader> loader( |
2304 new ResourceLoader(std::move(request), std::move(handler), this)); | 2420 new ResourceLoader(std::move(request), std::move(handler), this)); |
2305 | 2421 |
2306 GlobalRoutingID id(info->GetGlobalRoutingID()); | 2422 GlobalFrameRoutingId id(info->GetChildID(), info->GetRenderFrameID()); |
2307 BlockedLoadersMap::const_iterator iter = blocked_loaders_map_.find(id); | 2423 BlockedLoadersMap::const_iterator iter = blocked_loaders_map_.find(id); |
2308 if (iter != blocked_loaders_map_.end()) { | 2424 if (iter != blocked_loaders_map_.end()) { |
2309 // The request should be blocked. | 2425 // The request should be blocked. |
2310 iter->second->push_back(std::move(loader)); | 2426 iter->second->push_back(std::move(loader)); |
2311 return; | 2427 return; |
2312 } | 2428 } |
2313 | 2429 |
2314 StartLoading(info, std::move(loader)); | 2430 StartLoading(info, std::move(loader)); |
2315 } | 2431 } |
2316 | 2432 |
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2420 update_load_states_timer_->Stop(); | 2536 update_load_states_timer_->Stop(); |
2421 return; | 2537 return; |
2422 } | 2538 } |
2423 | 2539 |
2424 BrowserThread::PostTask( | 2540 BrowserThread::PostTask( |
2425 BrowserThread::UI, FROM_HERE, | 2541 BrowserThread::UI, FROM_HERE, |
2426 base::Bind(&ResourceDispatcherHostImpl::UpdateLoadInfoOnUIThread, | 2542 base::Bind(&ResourceDispatcherHostImpl::UpdateLoadInfoOnUIThread, |
2427 base::Passed(&info_map))); | 2543 base::Passed(&info_map))); |
2428 } | 2544 } |
2429 | 2545 |
2430 void ResourceDispatcherHostImpl::BlockRequestsForRoute(int child_id, | 2546 void ResourceDispatcherHostImpl::BlockRequestsForRoute( |
2431 int route_id) { | 2547 const GlobalFrameRoutingId& global_routing_id) { |
2432 DCHECK_CURRENTLY_ON(BrowserThread::IO); | 2548 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
2433 GlobalRoutingID key(child_id, route_id); | 2549 DCHECK(blocked_loaders_map_.find(global_routing_id) == |
2434 DCHECK(blocked_loaders_map_.find(key) == blocked_loaders_map_.end()) << | 2550 blocked_loaders_map_.end()) |
2435 "BlockRequestsForRoute called multiple time for the same RVH"; | 2551 << "BlockRequestsForRoute called multiple time for the same RFH"; |
2436 blocked_loaders_map_[key] = make_scoped_ptr(new BlockedLoadersList()); | 2552 blocked_loaders_map_[global_routing_id] = |
2553 make_scoped_ptr(new BlockedLoadersList()); | |
2437 } | 2554 } |
2438 | 2555 |
2439 void ResourceDispatcherHostImpl::ResumeBlockedRequestsForRoute(int child_id, | 2556 void ResourceDispatcherHostImpl::ResumeBlockedRequestsForRoute( |
2440 int route_id) { | 2557 const GlobalFrameRoutingId& global_routing_id) { |
2441 ProcessBlockedRequestsForRoute(child_id, route_id, false); | 2558 ProcessBlockedRequestsForRoute(global_routing_id, false); |
2442 } | 2559 } |
2443 | 2560 |
2444 void ResourceDispatcherHostImpl::CancelBlockedRequestsForRoute(int child_id, | 2561 void ResourceDispatcherHostImpl::CancelBlockedRequestsForRoute( |
2445 int route_id) { | 2562 const GlobalFrameRoutingId& global_routing_id) { |
2446 ProcessBlockedRequestsForRoute(child_id, route_id, true); | 2563 ProcessBlockedRequestsForRoute(global_routing_id, true); |
2447 } | 2564 } |
2448 | 2565 |
2449 void ResourceDispatcherHostImpl::ProcessBlockedRequestsForRoute( | 2566 void ResourceDispatcherHostImpl::ProcessBlockedRequestsForRoute( |
2450 int child_id, | 2567 const GlobalFrameRoutingId& global_routing_id, |
2451 int route_id, | |
2452 bool cancel_requests) { | 2568 bool cancel_requests) { |
2453 BlockedLoadersMap::iterator iter = blocked_loaders_map_.find( | 2569 BlockedLoadersMap::iterator iter = |
2454 GlobalRoutingID(child_id, route_id)); | 2570 blocked_loaders_map_.find(global_routing_id); |
2455 if (iter == blocked_loaders_map_.end()) { | 2571 if (iter == blocked_loaders_map_.end()) { |
2456 // It's possible to reach here if the renderer crashed while an interstitial | 2572 // It's possible to reach here if the renderer crashed while an interstitial |
2457 // page was showing. | 2573 // page was showing. |
2458 return; | 2574 return; |
2459 } | 2575 } |
2460 | 2576 |
2461 BlockedLoadersList* loaders = iter->second.get(); | 2577 BlockedLoadersList* loaders = iter->second.get(); |
2462 scoped_ptr<BlockedLoadersList> deleter(std::move(iter->second)); | 2578 scoped_ptr<BlockedLoadersList> deleter(std::move(iter->second)); |
2463 | 2579 |
2464 // Removing the vector from the map unblocks any subsequent requests. | 2580 // Removing the vector from the map unblocks any subsequent requests. |
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2560 load_flags |= net::LOAD_PREFETCH; | 2676 load_flags |= net::LOAD_PREFETCH; |
2561 } | 2677 } |
2562 | 2678 |
2563 if (is_sync_load) | 2679 if (is_sync_load) |
2564 load_flags |= net::LOAD_IGNORE_LIMITS; | 2680 load_flags |= net::LOAD_IGNORE_LIMITS; |
2565 | 2681 |
2566 return load_flags; | 2682 return load_flags; |
2567 } | 2683 } |
2568 | 2684 |
2569 } // namespace content | 2685 } // namespace content |
OLD | NEW |