Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(206)

Side by Side Diff: third_party/WebKit/Source/core/frame/FrameView.cpp

Issue 2516473002: Cross-origin iframes: collect data under hypothetical loading strategies (Closed)
Patch Set: fix histograms.xml Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (C) 1998, 1999 Torben Weis <weis@kde.org> 2 * Copyright (C) 1998, 1999 Torben Weis <weis@kde.org>
3 * 1999 Lars Knoll <knoll@kde.org> 3 * 1999 Lars Knoll <knoll@kde.org>
4 * 1999 Antti Koivisto <koivisto@kde.org> 4 * 1999 Antti Koivisto <koivisto@kde.org>
5 * 2000 Dirk Mueller <mueller@kde.org> 5 * 2000 Dirk Mueller <mueller@kde.org>
6 * Copyright (C) 2004, 2005, 2006, 2007, 2008 Apple Inc. All rights reserved. 6 * Copyright (C) 2004, 2005, 2006, 2007, 2008 Apple Inc. All rights reserved.
7 * (C) 2006 Graham Dennis (graham.dennis@gmail.com) 7 * (C) 2006 Graham Dennis (graham.dennis@gmail.com)
8 * (C) 2006 Alexey Proskuryakov (ap@nypop.com) 8 * (C) 2006 Alexey Proskuryakov (ap@nypop.com)
9 * Copyright (C) 2009 Google Inc. All rights reserved. 9 * Copyright (C) 2009 Google Inc. All rights reserved.
10 * 10 *
11 * This library is free software; you can redistribute it and/or 11 * This library is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU Library General Public 12 * modify it under the terms of the GNU Library General Public
13 * License as published by the Free Software Foundation; either 13 * License as published by the Free Software Foundation; either
14 * version 2 of the License, or (at your option) any later version. 14 * version 2 of the License, or (at your option) any later version.
15 * 15 *
16 * This library is distributed in the hope that it will be useful, 16 * This library is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 * Library General Public License for more details. 19 * Library General Public License for more details.
20 * 20 *
21 * You should have received a copy of the GNU Library General Public License 21 * You should have received a copy of the GNU Library General Public License
22 * along with this library; see the file COPYING.LIB. If not, write to 22 * along with this library; see the file COPYING.LIB. If not, write to
23 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 23 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
24 * Boston, MA 02110-1301, USA. 24 * Boston, MA 02110-1301, USA.
25 */ 25 */
26 26
27 #include "core/frame/FrameView.h" 27 #include "core/frame/FrameView.h"
28 28
29 #include <algorithm>
29 #include <memory> 30 #include <memory>
30 #include "core/HTMLNames.h" 31 #include "core/HTMLNames.h"
31 #include "core/MediaTypeNames.h" 32 #include "core/MediaTypeNames.h"
32 #include "core/animation/DocumentAnimations.h" 33 #include "core/animation/DocumentAnimations.h"
33 #include "core/css/FontFaceSet.h" 34 #include "core/css/FontFaceSet.h"
34 #include "core/dom/AXObjectCache.h" 35 #include "core/dom/AXObjectCache.h"
35 #include "core/dom/DOMNodeIds.h" 36 #include "core/dom/DOMNodeIds.h"
36 #include "core/dom/ElementVisibilityObserver.h" 37 #include "core/dom/ElementVisibilityObserver.h"
37 #include "core/dom/Fullscreen.h" 38 #include "core/dom/Fullscreen.h"
38 #include "core/dom/IntersectionObserverCallback.h" 39 #include "core/dom/IntersectionObserverCallback.h"
(...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after
321 if (!targetElement) 322 if (!targetElement)
322 return; 323 return;
323 324
324 m_visibilityObserver = new ElementVisibilityObserver( 325 m_visibilityObserver = new ElementVisibilityObserver(
325 targetElement, WTF::bind( 326 targetElement, WTF::bind(
326 [](FrameView* frameView, bool isVisible) { 327 [](FrameView* frameView, bool isVisible) {
327 if (!frameView) 328 if (!frameView)
328 return; 329 return;
329 frameView->updateRenderThrottlingStatus( 330 frameView->updateRenderThrottlingStatus(
330 !isVisible, frameView->m_subtreeThrottled); 331 !isVisible, frameView->m_subtreeThrottled);
331 frameView->maybeRecordLoadReason();
332 }, 332 },
333 wrapWeakPersistent(this))); 333 wrapWeakPersistent(this)));
334 m_visibilityObserver->start(); 334 m_visibilityObserver->start();
335 } 335 }
336 336
337 void FrameView::dispose() { 337 void FrameView::dispose() {
338 RELEASE_ASSERT(!isInPerformLayout()); 338 RELEASE_ASSERT(!isInPerformLayout());
339 339
340 if (ScrollAnimatorBase* scrollAnimator = existingScrollAnimator()) 340 if (ScrollAnimatorBase* scrollAnimator = existingScrollAnimator())
341 scrollAnimator->cancelAnimation(); 341 scrollAnimator->cancelAnimation();
(...skipping 4404 matching lines...) Expand 10 before | Expand all | Expand 10 after
4746 void FrameView::updateViewportIntersectionsForSubtree( 4746 void FrameView::updateViewportIntersectionsForSubtree(
4747 DocumentLifecycle::LifecycleState targetState) { 4747 DocumentLifecycle::LifecycleState targetState) {
4748 // TODO(dcheng): Since widget tree updates are deferred, FrameViews might 4748 // TODO(dcheng): Since widget tree updates are deferred, FrameViews might
4749 // still be in the widget hierarchy even though the associated Document is 4749 // still be in the widget hierarchy even though the associated Document is
4750 // already detached. Investigate if this check and a similar check in 4750 // already detached. Investigate if this check and a similar check in
4751 // lifecycle updates are still needed when there are no more deferred widget 4751 // lifecycle updates are still needed when there are no more deferred widget
4752 // updates: https://crbug.com/561683 4752 // updates: https://crbug.com/561683
4753 if (!frame().document()->isActive()) 4753 if (!frame().document()->isActive())
4754 return; 4754 return;
4755 4755
4756 // Notify javascript IntersectionObservers 4756 if (targetState == DocumentLifecycle::PaintClean) {
4757 if (targetState == DocumentLifecycle::PaintClean && 4757 recordDeferredLoadingStats();
4758 frame().document()->intersectionObserverController()) 4758 // Notify javascript IntersectionObservers
4759 frame() 4759 if (frame().document()->intersectionObserverController()) {
4760 .document() 4760 frame()
4761 ->intersectionObserverController() 4761 .document()
4762 ->computeTrackedIntersectionObservations(); 4762 ->intersectionObserverController()
4763 ->computeTrackedIntersectionObservations();
4764 }
4765 }
4763 4766
4764 // Don't throttle display:none frames (see updateRenderThrottlingStatus). 4767 // Don't throttle display:none frames (see updateRenderThrottlingStatus).
4765 HTMLFrameOwnerElement* ownerElement = m_frame->deprecatedLocalOwner(); 4768 HTMLFrameOwnerElement* ownerElement = m_frame->deprecatedLocalOwner();
4766 if (m_hiddenForThrottling && ownerElement && !ownerElement->layoutObject()) { 4769 if (m_hiddenForThrottling && ownerElement && !ownerElement->layoutObject()) {
4767 // No need to notify children because descendants of display:none frames 4770 // No need to notify children because descendants of display:none frames
4768 // should remain throttled. 4771 // should remain throttled.
4769 updateRenderThrottlingStatus(m_hiddenForThrottling, m_subtreeThrottled, 4772 updateRenderThrottlingStatus(m_hiddenForThrottling, m_subtreeThrottled,
4770 DontForceThrottlingInvalidation, 4773 DontForceThrottlingInvalidation,
4771 DontNotifyChildren); 4774 DontNotifyChildren);
4772 DCHECK(!canThrottleRendering()); 4775 DCHECK(!canThrottleRendering());
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
4866 #if DCHECK_IS_ON() 4869 #if DCHECK_IS_ON()
4867 // Make sure we never have an unthrottled frame inside a throttled one. 4870 // Make sure we never have an unthrottled frame inside a throttled one.
4868 FrameView* parent = parentFrameView(); 4871 FrameView* parent = parentFrameView();
4869 while (parent) { 4872 while (parent) {
4870 DCHECK(canThrottleRendering() || !parent->canThrottleRendering()); 4873 DCHECK(canThrottleRendering() || !parent->canThrottleRendering());
4871 parent = parent->parentFrameView(); 4874 parent = parent->parentFrameView();
4872 } 4875 }
4873 #endif 4876 #endif
4874 } 4877 }
4875 4878
4876 // TODO(esprehn): Rename this and the method on Document to 4879 void FrameView::recordDeferredLoadingStats() {
4877 // recordDeferredLoadReason(). 4880 if (!frame().document()->frame() || !frame().isCrossOriginSubframe())
4878 void FrameView::maybeRecordLoadReason() { 4881 return;
4882
4879 FrameView* parent = parentFrameView(); 4883 FrameView* parent = parentFrameView();
4880 if (frame().document()->frame()) { 4884 if (!parent) {
4881 if (!parent) { 4885 HTMLFrameOwnerElement* element = frame().deprecatedLocalOwner();
4882 HTMLFrameOwnerElement* element = frame().deprecatedLocalOwner(); 4886 // We would fall into an else block on some teardowns and other weird cases.
4883 if (!element) 4887 if (!element || !element->layoutObject())
4884 frame().document()->maybeRecordLoadReason(WouldLoadOutOfProcess); 4888 frame().document()->recordDeferredLoadReason(WouldLoadNoParent);
4885 // Having no layout object means the frame is not drawn. 4889 return;
4886 else if (!element->layoutObject())
4887 frame().document()->maybeRecordLoadReason(WouldLoadDisplayNone);
4888 } else {
4889 // Assume the main frame has always loaded since we don't track its
4890 // visibility.
4891 bool parentLoaded =
4892 !parent->parentFrameView() ||
4893 parent->frame().document()->wouldLoadReason() > Created;
4894 // If the parent wasn't loaded, the children won't be either.
4895 if (parentLoaded) {
4896 if (frameRect().isEmpty())
4897 frame().document()->maybeRecordLoadReason(WouldLoadZeroByZero);
4898 else if (frameRect().maxY() < 0 && frameRect().maxX() < 0)
4899 frame().document()->maybeRecordLoadReason(WouldLoadAboveAndLeft);
4900 else if (frameRect().maxY() < 0)
4901 frame().document()->maybeRecordLoadReason(WouldLoadAbove);
4902 else if (frameRect().maxX() < 0)
4903 frame().document()->maybeRecordLoadReason(WouldLoadLeft);
4904 else if (!m_hiddenForThrottling)
4905 frame().document()->maybeRecordLoadReason(WouldLoadVisible);
4906 }
4907 }
4908 } 4890 }
4891 // Small inaccuracy: frames with origins that match the top level might be
4892 // nested in a cross-origin frame. To keep code simpler, count such frames as
4893 // WouldLoadVisible, even when their parent is offscreen.
4894 WouldLoadReason whyParentLoaded = WouldLoadVisible;
4895 if (parent->parentFrameView() && parent->frame().isCrossOriginSubframe())
4896 whyParentLoaded = parent->frame().document()->deferredLoadReason();
4897
4898 // If the parent wasn't loaded, the children won't be either.
4899 if (whyParentLoaded == Created)
4900 return;
4901 // These frames are never meant to be seen so we will need to load them.
4902 if (frameRect().isEmpty() || frameRect().maxY() < 0 ||
4903 frameRect().maxX() < 0) {
4904 frame().document()->recordDeferredLoadReason(whyParentLoaded);
4905 return;
4906 }
4907
4908 IntRect parentRect = parent->frameRect();
4909 // First clause: for this rough data collection we assume the user never
4910 // scrolls right.
4911 if (frameRect().x() >= parentRect.width() || parentRect.height() <= 0)
4912 return;
4913
4914 int thisFrameScreensAway = 0;
4915 // If an frame is created above the current scoll position, this logic counts
4916 // it as visible.
4917 if (frameRect().y() > parent->getScrollOffset().height()) {
4918 thisFrameScreensAway =
4919 (frameRect().y() - parent->getScrollOffset().height()) /
4920 parentRect.height();
4921 }
4922 DCHECK_GE(thisFrameScreensAway, 0);
4923
4924 int parentScreensAway = 0;
4925 if (whyParentLoaded <= WouldLoadVisible)
4926 parentScreensAway = WouldLoadVisible - whyParentLoaded;
4927
4928 int totalScreensAway = thisFrameScreensAway + parentScreensAway;
4929
4930 // We're collecting data for frames that are at most 3 screens away.
4931 if (totalScreensAway > 3)
4932 return;
4933
4934 frame().document()->recordDeferredLoadReason(
4935 static_cast<WouldLoadReason>(WouldLoadVisible - totalScreensAway));
4909 } 4936 }
4910 4937
4911 bool FrameView::shouldThrottleRendering() const { 4938 bool FrameView::shouldThrottleRendering() const {
4912 return canThrottleRendering() && m_frame->document() && 4939 return canThrottleRendering() && m_frame->document() &&
4913 lifecycle().throttlingAllowed(); 4940 lifecycle().throttlingAllowed();
4914 } 4941 }
4915 4942
4916 bool FrameView::canThrottleRendering() const { 4943 bool FrameView::canThrottleRendering() const {
4917 if (m_lifecycleUpdatesThrottled) 4944 if (m_lifecycleUpdatesThrottled)
4918 return true; 4945 return true;
(...skipping 300 matching lines...) Expand 10 before | Expand all | Expand 10 after
5219 void FrameView::setAnimationHost( 5246 void FrameView::setAnimationHost(
5220 std::unique_ptr<CompositorAnimationHost> host) { 5247 std::unique_ptr<CompositorAnimationHost> host) {
5221 m_animationHost = std::move(host); 5248 m_animationHost = std::move(host);
5222 } 5249 }
5223 5250
5224 LayoutUnit FrameView::caretWidth() const { 5251 LayoutUnit FrameView::caretWidth() const {
5225 return LayoutUnit(getHostWindow()->windowToViewportScalar(1)); 5252 return LayoutUnit(getHostWindow()->windowToViewportScalar(1));
5226 } 5253 }
5227 5254
5228 } // namespace blink 5255 } // namespace blink
OLDNEW
« no previous file with comments | « third_party/WebKit/Source/core/frame/FrameView.h ('k') | third_party/WebKit/Source/core/frame/LocalDOMWindow.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698