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

Side by Side Diff: third_party/WebKit/Source/platform/scheduler/renderer/renderer_scheduler_impl.cc

Issue 2397753006: scheduler: Detect load RAIL mode (Closed)
Patch Set: Add fallback for missing FMP Created 4 years 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 // 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 "platform/scheduler/renderer/renderer_scheduler_impl.h" 5 #include "platform/scheduler/renderer/renderer_scheduler_impl.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/debug/stack_trace.h" 8 #include "base/debug/stack_trace.h"
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/memory/ptr_util.h" 10 #include "base/memory/ptr_util.h"
(...skipping 185 matching lines...) Expand 10 before | Expand all | Expand 10 after
196 rail_mode_observer(nullptr) {} 196 rail_mode_observer(nullptr) {}
197 197
198 RendererSchedulerImpl::MainThreadOnly::~MainThreadOnly() {} 198 RendererSchedulerImpl::MainThreadOnly::~MainThreadOnly() {}
199 199
200 RendererSchedulerImpl::AnyThread::AnyThread() 200 RendererSchedulerImpl::AnyThread::AnyThread()
201 : awaiting_touch_start_response(false), 201 : awaiting_touch_start_response(false),
202 in_idle_period(false), 202 in_idle_period(false),
203 begin_main_frame_on_critical_path(false), 203 begin_main_frame_on_critical_path(false),
204 last_gesture_was_compositor_driven(false), 204 last_gesture_was_compositor_driven(false),
205 default_gesture_prevented(true), 205 default_gesture_prevented(true),
206 have_seen_touchstart(false) {} 206 have_seen_touchstart(false),
207 waiting_for_meaningful_paint(false),
208 have_seen_input_since_navigation(false) {}
207 209
208 RendererSchedulerImpl::AnyThread::~AnyThread() {} 210 RendererSchedulerImpl::AnyThread::~AnyThread() {}
209 211
210 RendererSchedulerImpl::CompositorThreadOnly::CompositorThreadOnly() 212 RendererSchedulerImpl::CompositorThreadOnly::CompositorThreadOnly()
211 : last_input_type(blink::WebInputEvent::Undefined) {} 213 : last_input_type(blink::WebInputEvent::Undefined) {}
212 214
213 RendererSchedulerImpl::CompositorThreadOnly::~CompositorThreadOnly() {} 215 RendererSchedulerImpl::CompositorThreadOnly::~CompositorThreadOnly() {}
214 216
215 void RendererSchedulerImpl::Shutdown() { 217 void RendererSchedulerImpl::Shutdown() {
216 base::TimeTicks now = tick_clock()->NowTicks(); 218 base::TimeTicks now = tick_clock()->NowTicks();
(...skipping 399 matching lines...) Expand 10 before | Expand all | Expand 10 after
616 "type", static_cast<int>(type), "input_event_state", 618 "type", static_cast<int>(type), "input_event_state",
617 InputEventStateToString(input_event_state)); 619 InputEventStateToString(input_event_state));
618 620
619 base::TimeDelta unused_policy_duration; 621 base::TimeDelta unused_policy_duration;
620 UseCase previous_use_case = 622 UseCase previous_use_case =
621 ComputeCurrentUseCase(now, &unused_policy_duration); 623 ComputeCurrentUseCase(now, &unused_policy_duration);
622 bool was_awaiting_touch_start_response = 624 bool was_awaiting_touch_start_response =
623 AnyThread().awaiting_touch_start_response; 625 AnyThread().awaiting_touch_start_response;
624 626
625 AnyThread().user_model.DidStartProcessingInputEvent(type, now); 627 AnyThread().user_model.DidStartProcessingInputEvent(type, now);
628 AnyThread().have_seen_input_since_navigation = true;
626 629
627 if (input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR) 630 if (input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR)
628 AnyThread().user_model.DidFinishProcessingInputEvent(now); 631 AnyThread().user_model.DidFinishProcessingInputEvent(now);
629 632
630 switch (type) { 633 switch (type) {
631 case blink::WebInputEvent::TouchStart: 634 case blink::WebInputEvent::TouchStart:
632 AnyThread().awaiting_touch_start_response = true; 635 AnyThread().awaiting_touch_start_response = true;
633 // This is just a fail-safe to reset the state of 636 // This is just a fail-safe to reset the state of
634 // |last_gesture_was_compositor_driven| to the default. We don't know 637 // |last_gesture_was_compositor_driven| to the default. We don't know
635 // yet where the gesture will run. 638 // yet where the gesture will run.
(...skipping 339 matching lines...) Expand 10 before | Expand all | Expand 10 after
975 // driven gesture. 978 // driven gesture.
976 if (touchstart_expected_soon && 979 if (touchstart_expected_soon &&
977 AnyThread().last_gesture_was_compositor_driven) { 980 AnyThread().last_gesture_was_compositor_driven) {
978 new_policy.rail_mode = v8::PERFORMANCE_RESPONSE; 981 new_policy.rail_mode = v8::PERFORMANCE_RESPONSE;
979 expensive_task_policy = ExpensiveTaskPolicy::BLOCK; 982 expensive_task_policy = ExpensiveTaskPolicy::BLOCK;
980 } 983 }
981 break; 984 break;
982 985
983 case UseCase::LOADING: 986 case UseCase::LOADING:
984 new_policy.rail_mode = v8::PERFORMANCE_LOAD; 987 new_policy.rail_mode = v8::PERFORMANCE_LOAD;
985 new_policy.loading_queue_policy.priority = TaskQueue::HIGH_PRIORITY; 988 // TODO(skyostil): Experiment with increasing loading and default queue
986 new_policy.default_queue_policy.priority = TaskQueue::HIGH_PRIORITY; 989 // priorities and throttling rendering frame rate.
987 break; 990 break;
988 991
989 default: 992 default:
990 NOTREACHED(); 993 NOTREACHED();
991 } 994 }
992 995
993 // TODO(skyostil): Add an idle state for foreground tabs too. 996 // TODO(skyostil): Add an idle state for foreground tabs too.
994 if (MainThreadOnly().renderer_hidden) 997 if (MainThreadOnly().renderer_hidden)
995 new_policy.rail_mode = v8::PERFORMANCE_IDLE; 998 new_policy.rail_mode = v8::PERFORMANCE_IDLE;
996 999
(...skipping 185 matching lines...) Expand 10 before | Expand all | Expand 10 after
1182 return UseCase::COMPOSITOR_GESTURE; 1185 return UseCase::COMPOSITOR_GESTURE;
1183 } 1186 }
1184 } 1187 }
1185 if (AnyThread().default_gesture_prevented) { 1188 if (AnyThread().default_gesture_prevented) {
1186 return UseCase::MAIN_THREAD_CUSTOM_INPUT_HANDLING; 1189 return UseCase::MAIN_THREAD_CUSTOM_INPUT_HANDLING;
1187 } else { 1190 } else {
1188 return UseCase::MAIN_THREAD_GESTURE; 1191 return UseCase::MAIN_THREAD_GESTURE;
1189 } 1192 }
1190 } 1193 }
1191 1194
1192 // TODO(alexclarke): return UseCase::LOADING if signals suggest the system is 1195 // Occasionally the meaningful paint fails to be detected, so as a fallback we
1193 // in the initial 1s of RAIL loading. 1196 // treat the presence of input as an indirect signal that there is meaningful
1197 // content on the page.
1198 if (AnyThread().waiting_for_meaningful_paint &&
1199 !AnyThread().have_seen_input_since_navigation) {
1200 return UseCase::LOADING;
1201 }
1194 return UseCase::NONE; 1202 return UseCase::NONE;
1195 } 1203 }
1196 1204
1197 base::TimeDelta RendererSchedulerImpl::EstimateLongestJankFreeTaskDuration() 1205 base::TimeDelta RendererSchedulerImpl::EstimateLongestJankFreeTaskDuration()
1198 const { 1206 const {
1199 switch (MainThreadOnly().current_use_case) { 1207 switch (MainThreadOnly().current_use_case) {
1200 case UseCase::TOUCHSTART: 1208 case UseCase::TOUCHSTART:
1201 case UseCase::COMPOSITOR_GESTURE: 1209 case UseCase::COMPOSITOR_GESTURE:
1202 case UseCase::LOADING: 1210 case UseCase::LOADING:
1203 case UseCase::NONE: 1211 case UseCase::NONE:
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after
1328 state->SetBoolean("begin_frame_not_expected_soon", 1336 state->SetBoolean("begin_frame_not_expected_soon",
1329 MainThreadOnly().begin_frame_not_expected_soon); 1337 MainThreadOnly().begin_frame_not_expected_soon);
1330 state->SetBoolean("touchstart_expected_soon", 1338 state->SetBoolean("touchstart_expected_soon",
1331 MainThreadOnly().touchstart_expected_soon); 1339 MainThreadOnly().touchstart_expected_soon);
1332 state->SetString("idle_period_state", 1340 state->SetString("idle_period_state",
1333 IdleHelper::IdlePeriodStateToString( 1341 IdleHelper::IdlePeriodStateToString(
1334 idle_helper_.SchedulerIdlePeriodState())); 1342 idle_helper_.SchedulerIdlePeriodState()));
1335 state->SetBoolean("renderer_hidden", MainThreadOnly().renderer_hidden); 1343 state->SetBoolean("renderer_hidden", MainThreadOnly().renderer_hidden);
1336 state->SetBoolean("have_seen_a_begin_main_frame", 1344 state->SetBoolean("have_seen_a_begin_main_frame",
1337 MainThreadOnly().have_seen_a_begin_main_frame); 1345 MainThreadOnly().have_seen_a_begin_main_frame);
1346 state->SetBoolean("waiting_for_meaningful_paint",
1347 AnyThread().waiting_for_meaningful_paint);
1348 state->SetBoolean("have_seen_input_since_navigation",
1349 AnyThread().have_seen_input_since_navigation);
1338 state->SetBoolean( 1350 state->SetBoolean(
1339 "have_reported_blocking_intervention_in_current_policy", 1351 "have_reported_blocking_intervention_in_current_policy",
1340 MainThreadOnly().have_reported_blocking_intervention_in_current_policy); 1352 MainThreadOnly().have_reported_blocking_intervention_in_current_policy);
1341 state->SetBoolean( 1353 state->SetBoolean(
1342 "have_reported_blocking_intervention_since_navigation", 1354 "have_reported_blocking_intervention_since_navigation",
1343 MainThreadOnly().have_reported_blocking_intervention_since_navigation); 1355 MainThreadOnly().have_reported_blocking_intervention_since_navigation);
1344 state->SetBoolean("renderer_backgrounded", 1356 state->SetBoolean("renderer_backgrounded",
1345 MainThreadOnly().renderer_backgrounded); 1357 MainThreadOnly().renderer_backgrounded);
1346 state->SetBoolean("timer_queue_suspended_when_backgrounded", 1358 state->SetBoolean("timer_queue_suspended_when_backgrounded",
1347 MainThreadOnly().timer_queue_suspended_when_backgrounded); 1359 MainThreadOnly().timer_queue_suspended_when_backgrounded);
1348 state->SetInteger("timer_queue_suspend_count", 1360 state->SetInteger("timer_queue_suspend_count",
1349 MainThreadOnly().timer_queue_suspend_count); 1361 MainThreadOnly().timer_queue_suspend_count);
1350 state->SetDouble("now", (optional_now - base::TimeTicks()).InMillisecondsF()); 1362 state->SetDouble("now", (optional_now - base::TimeTicks()).InMillisecondsF());
1351 state->SetDouble( 1363 state->SetDouble(
1352 "rails_loading_priority_deadline",
1353 (AnyThread().rails_loading_priority_deadline - base::TimeTicks())
1354 .InMillisecondsF());
1355 state->SetDouble(
1356 "fling_compositor_escalation_deadline", 1364 "fling_compositor_escalation_deadline",
1357 (AnyThread().fling_compositor_escalation_deadline - base::TimeTicks()) 1365 (AnyThread().fling_compositor_escalation_deadline - base::TimeTicks())
1358 .InMillisecondsF()); 1366 .InMillisecondsF());
1359 state->SetInteger("navigation_task_expected_count", 1367 state->SetInteger("navigation_task_expected_count",
1360 MainThreadOnly().navigation_task_expected_count); 1368 MainThreadOnly().navigation_task_expected_count);
1361 state->SetDouble("last_idle_period_end_time", 1369 state->SetDouble("last_idle_period_end_time",
1362 (AnyThread().last_idle_period_end_time - base::TimeTicks()) 1370 (AnyThread().last_idle_period_end_time - base::TimeTicks())
1363 .InMillisecondsF()); 1371 .InMillisecondsF());
1364 state->SetBoolean("awaiting_touch_start_response", 1372 state->SetBoolean("awaiting_touch_start_response",
1365 AnyThread().awaiting_touch_start_response); 1373 AnyThread().awaiting_touch_start_response);
(...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after
1471 MainThreadOnly().navigation_task_expected_count > 0) { 1479 MainThreadOnly().navigation_task_expected_count > 0) {
1472 MainThreadOnly().navigation_task_expected_count--; 1480 MainThreadOnly().navigation_task_expected_count--;
1473 UpdatePolicy(); 1481 UpdatePolicy();
1474 } 1482 }
1475 } 1483 }
1476 1484
1477 void RendererSchedulerImpl::OnNavigationStarted() { 1485 void RendererSchedulerImpl::OnNavigationStarted() {
1478 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("renderer.scheduler"), 1486 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("renderer.scheduler"),
1479 "RendererSchedulerImpl::OnNavigationStarted"); 1487 "RendererSchedulerImpl::OnNavigationStarted");
1480 base::AutoLock lock(any_thread_lock_); 1488 base::AutoLock lock(any_thread_lock_);
1481 AnyThread().rails_loading_priority_deadline =
1482 helper_.scheduler_tqm_delegate()->NowTicks() +
1483 base::TimeDelta::FromMilliseconds(
1484 kRailsInitialLoadingPrioritizationMillis);
1485 ResetForNavigationLocked(); 1489 ResetForNavigationLocked();
1486 } 1490 }
1487 1491
1492 void RendererSchedulerImpl::OnFirstMeaningfulPaint() {
1493 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("renderer.scheduler"),
1494 "RendererSchedulerImpl::OnFirstMeaningfulPaint");
1495 {
1496 base::AutoLock lock(any_thread_lock_);
1497 AnyThread().waiting_for_meaningful_paint = false;
1498 }
1499 UpdatePolicy();
alex clarke (OOO till 29th) 2016/11/24 17:54:23 Can we call UpdatePolicyLocked(UpdateType::MAY_
Sami 2016/11/24 18:41:37 Oh, well spotted, thanks!
1500 }
1501
1488 void RendererSchedulerImpl::SuspendTimerQueueWhenBackgrounded() { 1502 void RendererSchedulerImpl::SuspendTimerQueueWhenBackgrounded() {
1489 DCHECK(MainThreadOnly().renderer_backgrounded); 1503 DCHECK(MainThreadOnly().renderer_backgrounded);
1490 if (MainThreadOnly().timer_queue_suspended_when_backgrounded) 1504 if (MainThreadOnly().timer_queue_suspended_when_backgrounded)
1491 return; 1505 return;
1492 1506
1493 MainThreadOnly().timer_queue_suspended_when_backgrounded = true; 1507 MainThreadOnly().timer_queue_suspended_when_backgrounded = true;
1494 ForceUpdatePolicy(); 1508 ForceUpdatePolicy();
1495 } 1509 }
1496 1510
1497 void RendererSchedulerImpl::ResumeTimerQueueWhenForegroundedOrResumed() { 1511 void RendererSchedulerImpl::ResumeTimerQueueWhenForegroundedOrResumed() {
1498 DCHECK(!MainThreadOnly().renderer_backgrounded || 1512 DCHECK(!MainThreadOnly().renderer_backgrounded ||
1499 (MainThreadOnly().renderer_backgrounded && 1513 (MainThreadOnly().renderer_backgrounded &&
1500 !MainThreadOnly().renderer_suspended)); 1514 !MainThreadOnly().renderer_suspended));
1501 if (!MainThreadOnly().timer_queue_suspended_when_backgrounded) 1515 if (!MainThreadOnly().timer_queue_suspended_when_backgrounded)
1502 return; 1516 return;
1503 1517
1504 MainThreadOnly().timer_queue_suspended_when_backgrounded = false; 1518 MainThreadOnly().timer_queue_suspended_when_backgrounded = false;
1505 ForceUpdatePolicy(); 1519 ForceUpdatePolicy();
1506 } 1520 }
1507 1521
1508 void RendererSchedulerImpl::ResetForNavigationLocked() { 1522 void RendererSchedulerImpl::ResetForNavigationLocked() {
1509 helper_.CheckOnValidThread(); 1523 helper_.CheckOnValidThread();
1510 any_thread_lock_.AssertAcquired(); 1524 any_thread_lock_.AssertAcquired();
1511 AnyThread().user_model.Reset(helper_.scheduler_tqm_delegate()->NowTicks()); 1525 AnyThread().user_model.Reset(helper_.scheduler_tqm_delegate()->NowTicks());
1512 AnyThread().have_seen_touchstart = false; 1526 AnyThread().have_seen_touchstart = false;
1527 AnyThread().waiting_for_meaningful_paint = true;
1528 AnyThread().have_seen_input_since_navigation = false;
1513 MainThreadOnly().loading_task_cost_estimator.Clear(); 1529 MainThreadOnly().loading_task_cost_estimator.Clear();
1514 MainThreadOnly().timer_task_cost_estimator.Clear(); 1530 MainThreadOnly().timer_task_cost_estimator.Clear();
1515 MainThreadOnly().idle_time_estimator.Clear(); 1531 MainThreadOnly().idle_time_estimator.Clear();
1516 MainThreadOnly().have_seen_a_begin_main_frame = false; 1532 MainThreadOnly().have_seen_a_begin_main_frame = false;
1517 MainThreadOnly().have_reported_blocking_intervention_since_navigation = false; 1533 MainThreadOnly().have_reported_blocking_intervention_since_navigation = false;
1518 for (WebViewSchedulerImpl* web_view_scheduler : 1534 for (WebViewSchedulerImpl* web_view_scheduler :
1519 MainThreadOnly().web_view_schedulers) { 1535 MainThreadOnly().web_view_schedulers) {
1520 web_view_scheduler->OnNavigation(); 1536 web_view_scheduler->OnNavigation();
1521 } 1537 }
1522 UpdatePolicyLocked(UpdateType::MAY_EARLY_OUT_IF_POLICY_UNCHANGED); 1538 UpdatePolicyLocked(UpdateType::MAY_EARLY_OUT_IF_POLICY_UNCHANGED);
(...skipping 229 matching lines...) Expand 10 before | Expand all | Expand 10 after
1752 case TimeDomainType::VIRTUAL: 1768 case TimeDomainType::VIRTUAL:
1753 return "virtual"; 1769 return "virtual";
1754 default: 1770 default:
1755 NOTREACHED(); 1771 NOTREACHED();
1756 return nullptr; 1772 return nullptr;
1757 } 1773 }
1758 } 1774 }
1759 1775
1760 } // namespace scheduler 1776 } // namespace scheduler
1761 } // namespace blink 1777 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698