Commit 6d308af2 authored by Dave Tapuska's avatar Dave Tapuska Committed by Commit Bot

Remove redundant checks in freezing/pausing context.

Check IsAttached() in places where JS events fire.
Some GetDocument() checks become redundant since we can't have a null
document on an attached frame.

BUG=907125

Change-Id: Ia34a65fb71cbd7da16664880998f9054e7fbc726
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1801735
Commit-Queue: Dave Tapuska <dtapuska@chromium.org>
Reviewed-by: default avatarDaniel Cheng <dcheng@chromium.org>
Cr-Commit-Position: refs/heads/master@{#697223}
parent ea14fcc5
...@@ -497,55 +497,57 @@ void LocalFrame::DidChangeVisibilityState() { ...@@ -497,55 +497,57 @@ void LocalFrame::DidChangeVisibilityState() {
} }
void LocalFrame::DidFreeze() { void LocalFrame::DidFreeze() {
if (GetDocument()) { DCHECK(IsAttached());
if (GetDocument()->GetResourceCoordinator() && auto* document_resource_coordinator = GetDocument()->GetResourceCoordinator();
!RuntimeEnabledFeatures::BackForwardCacheEnabled()) { if (document_resource_coordinator &&
// TODO(yuzus): Skip this block if DidFreeze is triggered by bfcache. !RuntimeEnabledFeatures::BackForwardCacheEnabled()) {
// TODO(yuzus): Skip this block if DidFreeze is triggered by bfcache.
// Determine if there is a beforeunload handler by dispatching a
// beforeunload that will *not* launch a user dialog. If // Determine if there is a beforeunload handler by dispatching a
// |proceed| is false then there is a non-empty beforeunload // beforeunload that will *not* launch a user dialog. If
// handler indicating potentially unsaved user state. // |proceed| is false then there is a non-empty beforeunload
bool unused_did_allow_navigation = false; // handler indicating potentially unsaved user state.
bool proceed = GetDocument()->DispatchBeforeUnloadEvent( bool unused_did_allow_navigation = false;
nullptr, false /* is_reload */, unused_did_allow_navigation); bool proceed = GetDocument()->DispatchBeforeUnloadEvent(
// Running the beforeunload event may invalidate the nullptr, false /* is_reload */, unused_did_allow_navigation);
// DocumentResourceCoordinator. Because of that, it can't be stored in a
// local variable that is reused throughout the method. // DispatchBeforeUnloadEvent dispatches JS events, which may detatch |this|.
// https://crbug.com/991380. if (!IsAttached())
auto* document_resource_coordinator = return;
GetDocument()->GetResourceCoordinator(); document_resource_coordinator->SetHasNonEmptyBeforeUnload(!proceed);
if (document_resource_coordinator) }
document_resource_coordinator->SetHasNonEmptyBeforeUnload(!proceed);
}
GetDocument()->DispatchFreezeEvent(); GetDocument()->DispatchFreezeEvent();
// TODO(fmeawad): Move the following logic to the page once we have a // DispatchFreezeEvent dispatches JS events, which may detatch |this|.
// PageResourceCoordinator in Blink. http://crbug.com/838415 if (!IsAttached())
if (auto* document_resource_coordinator = return;
GetDocument()->GetResourceCoordinator()) { // TODO(fmeawad): Move the following logic to the page once we have a
document_resource_coordinator->SetLifecycleState( // PageResourceCoordinator in Blink. http://crbug.com/838415
resource_coordinator::mojom::LifecycleState::kFrozen); if (document_resource_coordinator) {
} document_resource_coordinator->SetLifecycleState(
resource_coordinator::mojom::LifecycleState::kFrozen);
} }
} }
void LocalFrame::DidResume() { void LocalFrame::DidResume() {
if (GetDocument()) { DCHECK(IsAttached());
const base::TimeTicks resume_event_start = base::TimeTicks::Now(); const base::TimeTicks resume_event_start = base::TimeTicks::Now();
GetDocument()->DispatchEvent(*Event::Create(event_type_names::kResume)); GetDocument()->DispatchEvent(*Event::Create(event_type_names::kResume));
const base::TimeTicks resume_event_end = base::TimeTicks::Now(); const base::TimeTicks resume_event_end = base::TimeTicks::Now();
DEFINE_STATIC_LOCAL( DEFINE_STATIC_LOCAL(CustomCountHistogram, resume_histogram,
CustomCountHistogram, resume_histogram, ("DocumentEventTiming.ResumeDuration", 0, 10000000, 50));
("DocumentEventTiming.ResumeDuration", 0, 10000000, 50)); resume_histogram.CountMicroseconds(resume_event_end - resume_event_start);
resume_histogram.CountMicroseconds(resume_event_end - resume_event_start);
// TODO(fmeawad): Move the following logic to the page once we have a // DispatchEvent dispatchs JS events, which may detatch |this|.
// PageResourceCoordinator in Blink if (!IsAttached())
if (auto* document_resource_coordinator = return;
GetDocument()->GetResourceCoordinator()) {
document_resource_coordinator->SetLifecycleState( // TODO(fmeawad): Move the following logic to the page once we have a
resource_coordinator::mojom::LifecycleState::kRunning); // PageResourceCoordinator in Blink
} if (auto* document_resource_coordinator =
GetDocument()->GetResourceCoordinator()) {
document_resource_coordinator->SetLifecycleState(
resource_coordinator::mojom::LifecycleState::kRunning);
} }
} }
...@@ -1700,19 +1702,15 @@ void LocalFrame::ForciblyPurgeV8Memory() { ...@@ -1700,19 +1702,15 @@ void LocalFrame::ForciblyPurgeV8Memory() {
} }
void LocalFrame::PauseContext() { void LocalFrame::PauseContext() {
if (Document* document = GetDocument()) { GetDocument()->Fetcher()->SetDefersLoading(true);
document->Fetcher()->SetDefersLoading(true); GetDocument()->SetLifecycleState(lifecycle_state_);
document->SetLifecycleState(lifecycle_state_);
}
Loader().SetDefersLoading(true); Loader().SetDefersLoading(true);
GetFrameScheduler()->SetPaused(true); GetFrameScheduler()->SetPaused(true);
} }
void LocalFrame::UnpauseContext() { void LocalFrame::UnpauseContext() {
if (Document* document = GetDocument()) { GetDocument()->Fetcher()->SetDefersLoading(false);
document->Fetcher()->SetDefersLoading(false); GetDocument()->SetLifecycleState(mojom::FrameLifecycleState::kRunning);
document->SetLifecycleState(mojom::FrameLifecycleState::kRunning);
}
Loader().SetDefersLoading(false); Loader().SetDefersLoading(false);
GetFrameScheduler()->SetPaused(false); GetFrameScheduler()->SetPaused(false);
} }
...@@ -1750,7 +1748,7 @@ void LocalFrame::SetLifecycleState(mojom::FrameLifecycleState state) { ...@@ -1750,7 +1748,7 @@ void LocalFrame::SetLifecycleState(mojom::FrameLifecycleState state) {
if (freeze) { if (freeze) {
if (lifecycle_state_ != mojom::FrameLifecycleState::kPaused) { if (lifecycle_state_ != mojom::FrameLifecycleState::kPaused) {
DidFreeze(); DidFreeze();
// DidFreeze can dispatch JS events, causing |this| to be detached. // DidFreeze can dispatch JS events, which may detatch |this|.
if (!IsAttached()) if (!IsAttached())
return; return;
} }
...@@ -1759,13 +1757,12 @@ void LocalFrame::SetLifecycleState(mojom::FrameLifecycleState state) { ...@@ -1759,13 +1757,12 @@ void LocalFrame::SetLifecycleState(mojom::FrameLifecycleState state) {
UnpauseContext(); UnpauseContext();
if (old_state != mojom::FrameLifecycleState::kPaused) { if (old_state != mojom::FrameLifecycleState::kPaused) {
DidResume(); DidResume();
// DidResume can dispatch JS events, causing |this| to be detached. // DidResume can dispatch JS events, which may detatch |this|.
if (!IsAttached()) if (!IsAttached())
return; return;
} }
} }
if (Client()) Client()->LifecycleStateChanged(state);
Client()->LifecycleStateChanged(state);
} }
void LocalFrame::MaybeLogAdClickNavigation() { void LocalFrame::MaybeLogAdClickNavigation() {
......
<!doctype html>
<html>
<head><title>Frozen Child iframe</title></head>
<body>
<script>
// This child removes itself from the parent on dispatch of the freeze event.
// Regression test of https://crbug.com/994442
window.document.addEventListener("freeze", () => {
window.frameElement.remove();
});
</script>
</body>
</html>
...@@ -6,6 +6,7 @@ ...@@ -6,6 +6,7 @@
<script src="/common/utils.js"></script> <script src="/common/utils.js"></script>
<body> <body>
<h1>This window will be frozen</h1> <h1>This window will be frozen</h1>
<iframe id="child_frame" src="child.html"></iframe>
<script> <script>
const freezingStepName = 'testOnFreeze'; const freezingStepName = 'testOnFreeze';
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment