OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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 "content/renderer/render_frame_impl.h" | 5 #include "content/renderer/render_frame_impl.h" |
6 | 6 |
7 #include <map> | 7 #include <map> |
8 #include <string> | 8 #include <string> |
9 #include <utility> | 9 #include <utility> |
10 #include <vector> | 10 #include <vector> |
(...skipping 547 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
558 // Sanitizes the navigation_start timestamp for browser-initiated navigations, | 558 // Sanitizes the navigation_start timestamp for browser-initiated navigations, |
559 // where the browser possibly has a better notion of start time than the | 559 // where the browser possibly has a better notion of start time than the |
560 // renderer. In the case of cross-process navigations, this carries over the | 560 // renderer. In the case of cross-process navigations, this carries over the |
561 // time of finishing the onbeforeunload handler of the previous page. | 561 // time of finishing the onbeforeunload handler of the previous page. |
562 // TimeTicks is sometimes not monotonic across processes, and because | 562 // TimeTicks is sometimes not monotonic across processes, and because |
563 // |browser_navigation_start| is likely before this process existed, | 563 // |browser_navigation_start| is likely before this process existed, |
564 // InterProcessTimeTicksConverter won't help. The timestamp is sanitized by | 564 // InterProcessTimeTicksConverter won't help. The timestamp is sanitized by |
565 // clamping it to renderer_navigation_start, initialized earlier in the call | 565 // clamping it to renderer_navigation_start, initialized earlier in the call |
566 // stack. | 566 // stack. |
567 base::TimeTicks SanitizeNavigationTiming( | 567 base::TimeTicks SanitizeNavigationTiming( |
568 blink::WebFrameLoadType load_type, | |
569 const base::TimeTicks& browser_navigation_start, | 568 const base::TimeTicks& browser_navigation_start, |
570 const base::TimeTicks& renderer_navigation_start) { | 569 const base::TimeTicks& renderer_navigation_start) { |
571 if (load_type != blink::WebFrameLoadType::Standard) | |
572 return base::TimeTicks(); | |
573 DCHECK(!browser_navigation_start.is_null()); | 570 DCHECK(!browser_navigation_start.is_null()); |
574 base::TimeTicks navigation_start = | 571 base::TimeTicks navigation_start = |
575 std::min(browser_navigation_start, renderer_navigation_start); | 572 std::min(browser_navigation_start, renderer_navigation_start); |
576 base::TimeDelta difference = | 573 base::TimeDelta difference = |
577 renderer_navigation_start - browser_navigation_start; | 574 renderer_navigation_start - browser_navigation_start; |
578 if (difference > base::TimeDelta()) { | 575 if (difference > base::TimeDelta()) { |
579 UMA_HISTOGRAM_TIMES("Navigation.Start.RendererBrowserDifference.Positive", | 576 UMA_HISTOGRAM_TIMES("Navigation.Start.RendererBrowserDifference.Positive", |
580 difference); | 577 difference); |
581 } else { | 578 } else { |
582 UMA_HISTOGRAM_TIMES("Navigation.Start.RendererBrowserDifference.Negative", | 579 UMA_HISTOGRAM_TIMES("Navigation.Start.RendererBrowserDifference.Negative", |
(...skipping 473 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1056 | 1053 |
1057 // RenderFrameImpl ---------------------------------------------------------- | 1054 // RenderFrameImpl ---------------------------------------------------------- |
1058 RenderFrameImpl::RenderFrameImpl(const CreateParams& params) | 1055 RenderFrameImpl::RenderFrameImpl(const CreateParams& params) |
1059 : frame_(NULL), | 1056 : frame_(NULL), |
1060 is_main_frame_(true), | 1057 is_main_frame_(true), |
1061 in_browser_initiated_detach_(false), | 1058 in_browser_initiated_detach_(false), |
1062 in_frame_tree_(false), | 1059 in_frame_tree_(false), |
1063 render_view_(params.render_view->AsWeakPtr()), | 1060 render_view_(params.render_view->AsWeakPtr()), |
1064 routing_id_(params.routing_id), | 1061 routing_id_(params.routing_id), |
1065 proxy_routing_id_(MSG_ROUTING_NONE), | 1062 proxy_routing_id_(MSG_ROUTING_NONE), |
| 1063 did_access_initial_document_(false), |
1066 #if defined(ENABLE_PLUGINS) | 1064 #if defined(ENABLE_PLUGINS) |
1067 plugin_power_saver_helper_(nullptr), | 1065 plugin_power_saver_helper_(nullptr), |
1068 plugin_find_handler_(nullptr), | 1066 plugin_find_handler_(nullptr), |
1069 #endif | 1067 #endif |
1070 cookie_jar_(this), | 1068 cookie_jar_(this), |
1071 selection_text_offset_(0), | 1069 selection_text_offset_(0), |
1072 selection_range_(gfx::Range::InvalidRange()), | 1070 selection_range_(gfx::Range::InvalidRange()), |
1073 handling_select_range_(false), | 1071 handling_select_range_(false), |
1074 notification_permission_dispatcher_(NULL), | 1072 notification_permission_dispatcher_(NULL), |
1075 web_user_media_client_(NULL), | 1073 web_user_media_client_(NULL), |
(...skipping 1673 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2749 if (!provider->context()) { | 2747 if (!provider->context()) { |
2750 // The context can be null when the frame is sandboxed. | 2748 // The context can be null when the frame is sandboxed. |
2751 return nullptr; | 2749 return nullptr; |
2752 } | 2750 } |
2753 return new WebServiceWorkerProviderImpl( | 2751 return new WebServiceWorkerProviderImpl( |
2754 ChildThreadImpl::current()->thread_safe_sender(), | 2752 ChildThreadImpl::current()->thread_safe_sender(), |
2755 provider->context()); | 2753 provider->context()); |
2756 } | 2754 } |
2757 | 2755 |
2758 void RenderFrameImpl::didAccessInitialDocument() { | 2756 void RenderFrameImpl::didAccessInitialDocument() { |
| 2757 did_access_initial_document_ = true; |
| 2758 |
2759 // If the request hasn't yet committed, notify the browser process that it is | 2759 // If the request hasn't yet committed, notify the browser process that it is |
2760 // no longer safe to show the pending URL of the main frame, since a URL spoof | 2760 // no longer safe to show the pending URL of the main frame, since a URL spoof |
2761 // is now possible. (If the request has committed, the browser already knows.) | 2761 // is now possible. (If the request has committed, the browser already knows.) |
2762 if (!frame_->parent()) { | 2762 if (!frame_->parent()) { |
2763 DocumentState* document_state = | 2763 DocumentState* document_state = |
2764 DocumentState::FromDataSource(frame_->dataSource()); | 2764 DocumentState::FromDataSource(frame_->dataSource()); |
2765 NavigationStateImpl* navigation_state = | 2765 NavigationStateImpl* navigation_state = |
2766 static_cast<NavigationStateImpl*>(document_state->navigation_state()); | 2766 static_cast<NavigationStateImpl*>(document_state->navigation_state()); |
2767 | 2767 |
2768 if (!navigation_state->request_committed()) { | 2768 if (!navigation_state->request_committed()) { |
(...skipping 600 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3369 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | 3369 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { |
3370 SendUpdateState(); | 3370 SendUpdateState(); |
3371 } else { | 3371 } else { |
3372 render_view_->SendUpdateState(); | 3372 render_view_->SendUpdateState(); |
3373 render_view_->history_controller()->UpdateForCommit( | 3373 render_view_->history_controller()->UpdateForCommit( |
3374 this, item, commit_type, navigation_state->WasWithinSamePage()); | 3374 this, item, commit_type, navigation_state->WasWithinSamePage()); |
3375 } | 3375 } |
3376 // Update the current history item for this frame (both in default Chrome and | 3376 // Update the current history item for this frame (both in default Chrome and |
3377 // subframe FrameNavigationEntry modes). | 3377 // subframe FrameNavigationEntry modes). |
3378 current_history_item_ = item; | 3378 current_history_item_ = item; |
| 3379 did_access_initial_document_ = false; |
3379 | 3380 |
3380 InternalDocumentStateData* internal_data = | 3381 InternalDocumentStateData* internal_data = |
3381 InternalDocumentStateData::FromDocumentState(document_state); | 3382 InternalDocumentStateData::FromDocumentState(document_state); |
3382 | 3383 |
3383 if (document_state->commit_load_time().is_null()) | 3384 if (document_state->commit_load_time().is_null()) |
3384 document_state->set_commit_load_time(Time::Now()); | 3385 document_state->set_commit_load_time(Time::Now()); |
3385 | 3386 |
3386 if (internal_data->must_reset_scroll_and_scale_state()) { | 3387 if (internal_data->must_reset_scroll_and_scale_state()) { |
3387 render_view_->webview()->resetScrollAndScaleState(); | 3388 render_view_->webview()->resetScrollAndScaleState(); |
3388 internal_data->set_must_reset_scroll_and_scale_state(false); | 3389 internal_data->set_must_reset_scroll_and_scale_state(false); |
(...skipping 1644 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5033 info.navigationType == blink::WebNavigationTypeOther; | 5034 info.navigationType == blink::WebNavigationTypeOther; |
5034 | 5035 |
5035 if (is_fork) { | 5036 if (is_fork) { |
5036 // Open the URL via the browser, not via WebKit. | 5037 // Open the URL via the browser, not via WebKit. |
5037 OpenURL(url, IsHttpPost(info.urlRequest), | 5038 OpenURL(url, IsHttpPost(info.urlRequest), |
5038 GetRequestBodyForWebURLRequest(info.urlRequest), Referrer(), | 5039 GetRequestBodyForWebURLRequest(info.urlRequest), Referrer(), |
5039 info.defaultPolicy, info.replacesCurrentHistoryItem, false); | 5040 info.defaultPolicy, info.replacesCurrentHistoryItem, false); |
5040 return blink::WebNavigationPolicyIgnore; | 5041 return blink::WebNavigationPolicyIgnore; |
5041 } | 5042 } |
5042 | 5043 |
5043 // Execute the BeforeUnload event. If asked not to proceed or the frame is | 5044 bool should_dispatch_before_unload = |
5044 // destroyed, ignore the navigation. There is no need to execute the | 5045 info.defaultPolicy == blink::WebNavigationPolicyCurrentTab && |
5045 // BeforeUnload event during a redirect, since it was already executed at the | 5046 // There is no need to execute the BeforeUnload event during a redirect, |
5046 // start of the navigation. | 5047 // since it was already executed at the start of the navigation. |
5047 // PlzNavigate: this is not executed when commiting the navigation. | 5048 !is_redirect && |
5048 if (info.defaultPolicy == blink::WebNavigationPolicyCurrentTab && | 5049 // PlzNavigate: this should not be executed when commiting the navigation. |
5049 !is_redirect && (!IsBrowserSideNavigationEnabled() || | 5050 (!IsBrowserSideNavigationEnabled() || |
5050 info.urlRequest.checkForBrowserSideNavigation())) { | 5051 info.urlRequest.checkForBrowserSideNavigation()) && |
| 5052 // No need to dispatch beforeunload if the frame has not committed a |
| 5053 // navigation and contains an empty initial document. |
| 5054 (did_access_initial_document_ || !current_history_item_.isNull()); |
| 5055 |
| 5056 if (should_dispatch_before_unload) { |
| 5057 // Execute the BeforeUnload event. If asked not to proceed or the frame is |
| 5058 // destroyed, ignore the navigation. |
5051 // Keep a WeakPtr to this RenderFrameHost to detect if executing the | 5059 // Keep a WeakPtr to this RenderFrameHost to detect if executing the |
5052 // BeforeUnload event destriyed this frame. | 5060 // BeforeUnload event destriyed this frame. |
5053 base::WeakPtr<RenderFrameImpl> weak_self = weak_factory_.GetWeakPtr(); | 5061 base::WeakPtr<RenderFrameImpl> weak_self = weak_factory_.GetWeakPtr(); |
5054 | 5062 |
5055 if (!frame_->dispatchBeforeUnloadEvent(info.navigationType == | 5063 if (!frame_->dispatchBeforeUnloadEvent(info.navigationType == |
5056 blink::WebNavigationTypeReload) || | 5064 blink::WebNavigationTypeReload) || |
5057 !weak_self) { | 5065 !weak_self) { |
5058 return blink::WebNavigationPolicyIgnore; | 5066 return blink::WebNavigationPolicyIgnore; |
5059 } | 5067 } |
| 5068 // navigation_start must be recorded immediately after dispatching the |
| 5069 // beforeunload event. |
| 5070 if (pending_navigation_params_) { |
| 5071 pending_navigation_params_->common_params.navigation_start = |
| 5072 base::TimeTicks::Now(); |
| 5073 } |
5060 } | 5074 } |
5061 | 5075 |
5062 // PlzNavigate: if the navigation is not synchronous, send it to the browser. | 5076 // PlzNavigate: if the navigation is not synchronous, send it to the browser. |
5063 // This includes navigations with no request being sent to the network stack. | 5077 // This includes navigations with no request being sent to the network stack. |
5064 if (IsBrowserSideNavigationEnabled() && | 5078 if (IsBrowserSideNavigationEnabled() && |
5065 info.urlRequest.checkForBrowserSideNavigation() && | 5079 info.urlRequest.checkForBrowserSideNavigation() && |
5066 ShouldMakeNetworkRequestForURL(url)) { | 5080 ShouldMakeNetworkRequestForURL(url)) { |
5067 BeginNavigation(&info.urlRequest, info.replacesCurrentHistoryItem, | 5081 BeginNavigation(&info.urlRequest, info.replacesCurrentHistoryItem, |
5068 info.isClientRedirect); | 5082 info.isClientRedirect); |
5069 return blink::WebNavigationPolicyHandledByClient; | 5083 return blink::WebNavigationPolicyHandledByClient; |
(...skipping 377 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5447 } | 5461 } |
5448 | 5462 |
5449 // If the navigation is for "view source", the WebLocalFrame needs to be put | 5463 // If the navigation is for "view source", the WebLocalFrame needs to be put |
5450 // in a special mode. | 5464 // in a special mode. |
5451 if (request_params.is_view_source) | 5465 if (request_params.is_view_source) |
5452 frame_->enableViewSourceMode(true); | 5466 frame_->enableViewSourceMode(true); |
5453 | 5467 |
5454 pending_navigation_params_.reset( | 5468 pending_navigation_params_.reset( |
5455 new NavigationParams(common_params, start_params, request_params)); | 5469 new NavigationParams(common_params, start_params, request_params)); |
5456 | 5470 |
5457 // Unless the load is a WebFrameLoadType::Standard, this should remain | 5471 // Sanitize navigation start and store in |pending_navigation_params_|. |
5458 // uninitialized. It will be updated when the load type is determined to be | 5472 // It will be picked up in UpdateNavigationState. |
5459 // Standard, or after the previous document's unload handler has been | |
5460 // triggered. This occurs in UpdateNavigationState. | |
5461 // TODO(csharrison) See if we can always use the browser timestamp. | |
5462 pending_navigation_params_->common_params.navigation_start = | 5473 pending_navigation_params_->common_params.navigation_start = |
5463 base::TimeTicks(); | 5474 SanitizeNavigationTiming(common_params.navigation_start, |
| 5475 renderer_navigation_start); |
5464 | 5476 |
5465 // Create parameters for a standard navigation, indicating whether it should | 5477 // Create parameters for a standard navigation, indicating whether it should |
5466 // replace the current NavigationEntry. | 5478 // replace the current NavigationEntry. |
5467 blink::WebFrameLoadType load_type = | 5479 blink::WebFrameLoadType load_type = |
5468 common_params.should_replace_current_entry | 5480 common_params.should_replace_current_entry |
5469 ? blink::WebFrameLoadType::ReplaceCurrentItem | 5481 ? blink::WebFrameLoadType::ReplaceCurrentItem |
5470 : blink::WebFrameLoadType::Standard; | 5482 : blink::WebFrameLoadType::Standard; |
5471 blink::WebHistoryLoadType history_load_type = | 5483 blink::WebHistoryLoadType history_load_type = |
5472 blink::WebHistoryDifferentDocumentLoad; | 5484 blink::WebHistoryDifferentDocumentLoad; |
5473 bool should_load_request = false; | 5485 bool should_load_request = false; |
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5576 GetWebHTTPBodyForRequestBody(common_params.post_data)); | 5588 GetWebHTTPBodyForRequestBody(common_params.post_data)); |
5577 } | 5589 } |
5578 | 5590 |
5579 // A session history navigation should have been accompanied by state. | 5591 // A session history navigation should have been accompanied by state. |
5580 CHECK_EQ(request_params.page_id, -1); | 5592 CHECK_EQ(request_params.page_id, -1); |
5581 | 5593 |
5582 should_load_request = true; | 5594 should_load_request = true; |
5583 } | 5595 } |
5584 | 5596 |
5585 if (should_load_request) { | 5597 if (should_load_request) { |
5586 // Sanitize navigation start now that we know the load_type. | |
5587 pending_navigation_params_->common_params.navigation_start = | |
5588 SanitizeNavigationTiming(load_type, common_params.navigation_start, | |
5589 renderer_navigation_start); | |
5590 | |
5591 // PlzNavigate: check if the navigation being committed originated as a | 5598 // PlzNavigate: check if the navigation being committed originated as a |
5592 // client redirect. | 5599 // client redirect. |
5593 bool is_client_redirect = | 5600 bool is_client_redirect = |
5594 browser_side_navigation | 5601 browser_side_navigation |
5595 ? !!(common_params.transition & ui::PAGE_TRANSITION_CLIENT_REDIRECT) | 5602 ? !!(common_params.transition & ui::PAGE_TRANSITION_CLIENT_REDIRECT) |
5596 : false; | 5603 : false; |
5597 | 5604 |
5598 // Perform a navigation to a data url if needed. | 5605 // Perform a navigation to a data url if needed. |
5599 // Note: the base URL might be invalid, so also check the data URL string. | 5606 // Note: the base URL might be invalid, so also check the data URL string. |
5600 bool should_load_data_url = !common_params.base_url_for_data_url.is_empty(); | 5607 bool should_load_data_url = !common_params.base_url_for_data_url.is_empty(); |
(...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6020 // If this was a browser-initiated navigation, then there could be pending | 6027 // If this was a browser-initiated navigation, then there could be pending |
6021 // navigation params, so use them. Otherwise, just reset the document state | 6028 // navigation params, so use them. Otherwise, just reset the document state |
6022 // here, since if pending navigation params exist they are for some other | 6029 // here, since if pending navigation params exist they are for some other |
6023 // navigation <https://crbug.com/597239>. | 6030 // navigation <https://crbug.com/597239>. |
6024 if (!pending_navigation_params_ || content_initiated) { | 6031 if (!pending_navigation_params_ || content_initiated) { |
6025 document_state->set_navigation_state( | 6032 document_state->set_navigation_state( |
6026 NavigationStateImpl::CreateContentInitiated()); | 6033 NavigationStateImpl::CreateContentInitiated()); |
6027 return; | 6034 return; |
6028 } | 6035 } |
6029 | 6036 |
6030 // If this is a browser-initiated load that doesn't override | 6037 DCHECK(!pending_navigation_params_->common_params.navigation_start.is_null()); |
6031 // navigation_start, set it here. | |
6032 if (pending_navigation_params_->common_params.navigation_start.is_null()) { | |
6033 pending_navigation_params_->common_params.navigation_start = | |
6034 base::TimeTicks::Now(); | |
6035 } | |
6036 document_state->set_navigation_state(CreateNavigationStateFromPending()); | 6038 document_state->set_navigation_state(CreateNavigationStateFromPending()); |
6037 | 6039 |
6038 // The |set_was_load_data_with_base_url_request| state should not change for | 6040 // The |set_was_load_data_with_base_url_request| state should not change for |
6039 // an in-page navigation, so skip updating it from the in-page navigation | 6041 // an in-page navigation, so skip updating it from the in-page navigation |
6040 // params in this case. | 6042 // params in this case. |
6041 if (!was_within_same_page) { | 6043 if (!was_within_same_page) { |
6042 const CommonNavigationParams& common_params = | 6044 const CommonNavigationParams& common_params = |
6043 pending_navigation_params_->common_params; | 6045 pending_navigation_params_->common_params; |
6044 bool load_data = !common_params.base_url_for_data_url.is_empty() && | 6046 bool load_data = !common_params.base_url_for_data_url.is_empty() && |
6045 !common_params.history_url_for_data_url.is_empty() && | 6047 !common_params.history_url_for_data_url.is_empty() && |
(...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6328 // event target. Potentially a Pepper plugin will receive the event. | 6330 // event target. Potentially a Pepper plugin will receive the event. |
6329 // In order to tell whether a plugin gets the last mouse event and which it | 6331 // In order to tell whether a plugin gets the last mouse event and which it |
6330 // is, we set |pepper_last_mouse_event_target_| to null here. If a plugin gets | 6332 // is, we set |pepper_last_mouse_event_target_| to null here. If a plugin gets |
6331 // the event, it will notify us via DidReceiveMouseEvent() and set itself as | 6333 // the event, it will notify us via DidReceiveMouseEvent() and set itself as |
6332 // |pepper_last_mouse_event_target_|. | 6334 // |pepper_last_mouse_event_target_|. |
6333 pepper_last_mouse_event_target_ = nullptr; | 6335 pepper_last_mouse_event_target_ = nullptr; |
6334 #endif | 6336 #endif |
6335 } | 6337 } |
6336 | 6338 |
6337 } // namespace content | 6339 } // namespace content |
OLD | NEW |