| OLD | NEW |
| 1 // Copyright 2011 The Chromium Authors. All rights reserved. | 1 // Copyright 2011 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 "cc/scheduler/scheduler.h" | 5 #include "cc/scheduler/scheduler.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "base/auto_reset.h" | 9 #include "base/auto_reset.h" |
| 10 #include "base/debug/trace_event.h" | 10 #include "base/debug/trace_event.h" |
| 11 #include "base/debug/trace_event_argument.h" | 11 #include "base/debug/trace_event_argument.h" |
| 12 #include "base/logging.h" | 12 #include "base/logging.h" |
| 13 #include "base/single_thread_task_runner.h" | 13 #include "base/single_thread_task_runner.h" |
| 14 #include "cc/debug/devtools_instrumentation.h" | 14 #include "cc/debug/devtools_instrumentation.h" |
| 15 #include "cc/debug/traced_value.h" | 15 #include "cc/debug/traced_value.h" |
| 16 #include "cc/scheduler/delay_based_time_source.h" | 16 #include "cc/scheduler/delay_based_time_source.h" |
| 17 #include "ui/gfx/frame_time.h" | 17 #include "ui/gfx/frame_time.h" |
| 18 | 18 |
| 19 namespace cc { | 19 namespace cc { |
| 20 | 20 |
| 21 BeginFrameSource* SchedulerFrameSourcesConstructor::ConstructPrimaryFrameSource( | 21 BeginFrameSource* SchedulerFrameSourcesConstructor::ConstructPrimaryFrameSource( |
| 22 Scheduler* scheduler) { | 22 Scheduler* scheduler) { |
| 23 if (!scheduler->settings_.throttle_frame_production) { | 23 if (scheduler->settings_.use_external_begin_frame_source) { |
| 24 TRACE_EVENT1("cc", | 24 TRACE_EVENT1("cc", |
| 25 "Scheduler::Scheduler()", | 25 "Scheduler::Scheduler()", |
| 26 "PrimaryFrameSource", | 26 "PrimaryFrameSource", |
| 27 "BackToBackBeginFrameSource"); | |
| 28 DCHECK(!scheduler->primary_frame_source_internal_); | |
| 29 scheduler->primary_frame_source_internal_ = | |
| 30 BackToBackBeginFrameSource::Create(scheduler->task_runner_.get()); | |
| 31 return scheduler->primary_frame_source_internal_.get(); | |
| 32 } else if (scheduler->settings_.use_external_begin_frame_source) { | |
| 33 TRACE_EVENT1("cc", | |
| 34 "Scheduler::Scheduler()", | |
| 35 "PrimaryFrameSource", | |
| 36 "ExternalBeginFrameSource"); | 27 "ExternalBeginFrameSource"); |
| 37 DCHECK(scheduler->primary_frame_source_internal_) | 28 DCHECK(scheduler->primary_frame_source_internal_) |
| 38 << "Need external BeginFrameSource"; | 29 << "Need external BeginFrameSource"; |
| 39 return scheduler->primary_frame_source_internal_.get(); | 30 return scheduler->primary_frame_source_internal_.get(); |
| 40 } else { | 31 } else { |
| 41 TRACE_EVENT1("cc", | 32 TRACE_EVENT1("cc", |
| 42 "Scheduler::Scheduler()", | 33 "Scheduler::Scheduler()", |
| 43 "PrimaryFrameSource", | 34 "PrimaryFrameSource", |
| 44 "SyntheticBeginFrameSource"); | 35 "SyntheticBeginFrameSource"); |
| 45 scoped_ptr<SyntheticBeginFrameSource> synthetic_source = | 36 scoped_ptr<SyntheticBeginFrameSource> synthetic_source = |
| (...skipping 18 matching lines...) Expand all Loading... |
| 64 "BackgroundFrameSource", | 55 "BackgroundFrameSource", |
| 65 "SyntheticBeginFrameSource"); | 56 "SyntheticBeginFrameSource"); |
| 66 DCHECK(!(scheduler->background_frame_source_internal_)); | 57 DCHECK(!(scheduler->background_frame_source_internal_)); |
| 67 scheduler->background_frame_source_internal_ = | 58 scheduler->background_frame_source_internal_ = |
| 68 SyntheticBeginFrameSource::Create( | 59 SyntheticBeginFrameSource::Create( |
| 69 scheduler->task_runner_.get(), scheduler->Now(), | 60 scheduler->task_runner_.get(), scheduler->Now(), |
| 70 scheduler->settings_.background_frame_interval); | 61 scheduler->settings_.background_frame_interval); |
| 71 return scheduler->background_frame_source_internal_.get(); | 62 return scheduler->background_frame_source_internal_.get(); |
| 72 } | 63 } |
| 73 | 64 |
| 65 BeginFrameSource* |
| 66 SchedulerFrameSourcesConstructor::ConstructUnthrottledFrameSource( |
| 67 Scheduler* scheduler) { |
| 68 TRACE_EVENT1("cc", "Scheduler::Scheduler()", "UnthrottledFrameSource", |
| 69 "BackToBackBeginFrameSource"); |
| 70 DCHECK(!scheduler->unthrottled_frame_source_internal_); |
| 71 scheduler->unthrottled_frame_source_internal_ = |
| 72 BackToBackBeginFrameSource::Create(scheduler->task_runner_.get()); |
| 73 return scheduler->unthrottled_frame_source_internal_.get(); |
| 74 } |
| 75 |
| 74 Scheduler::Scheduler( | 76 Scheduler::Scheduler( |
| 75 SchedulerClient* client, | 77 SchedulerClient* client, |
| 76 const SchedulerSettings& scheduler_settings, | 78 const SchedulerSettings& scheduler_settings, |
| 77 int layer_tree_host_id, | 79 int layer_tree_host_id, |
| 78 const scoped_refptr<base::SingleThreadTaskRunner>& task_runner, | 80 const scoped_refptr<base::SingleThreadTaskRunner>& task_runner, |
| 79 base::PowerMonitor* power_monitor, | 81 base::PowerMonitor* power_monitor, |
| 80 scoped_ptr<BeginFrameSource> external_begin_frame_source, | 82 scoped_ptr<BeginFrameSource> external_begin_frame_source, |
| 81 SchedulerFrameSourcesConstructor* frame_sources_constructor) | 83 SchedulerFrameSourcesConstructor* frame_sources_constructor) |
| 82 : frame_source_(), | 84 : frame_source_(), |
| 83 primary_frame_source_(NULL), | 85 primary_frame_source_(NULL), |
| 84 background_frame_source_(NULL), | 86 background_frame_source_(NULL), |
| 85 primary_frame_source_internal_(external_begin_frame_source.Pass()), | 87 primary_frame_source_internal_(external_begin_frame_source.Pass()), |
| 86 background_frame_source_internal_(), | 88 background_frame_source_internal_(), |
| 87 vsync_observer_(NULL), | 89 vsync_observer_(NULL), |
| 90 throttle_frame_production_(scheduler_settings.throttle_frame_production), |
| 88 settings_(scheduler_settings), | 91 settings_(scheduler_settings), |
| 89 client_(client), | 92 client_(client), |
| 90 layer_tree_host_id_(layer_tree_host_id), | 93 layer_tree_host_id_(layer_tree_host_id), |
| 91 task_runner_(task_runner), | 94 task_runner_(task_runner), |
| 92 power_monitor_(power_monitor), | 95 power_monitor_(power_monitor), |
| 93 begin_retro_frame_posted_(false), | |
| 94 state_machine_(scheduler_settings), | 96 state_machine_(scheduler_settings), |
| 95 inside_process_scheduled_actions_(false), | 97 inside_process_scheduled_actions_(false), |
| 96 inside_action_(SchedulerStateMachine::ACTION_NONE), | 98 inside_action_(SchedulerStateMachine::ACTION_NONE), |
| 97 weak_factory_(this) { | 99 weak_factory_(this) { |
| 98 TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("cc.debug.scheduler"), | 100 TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("cc.debug.scheduler"), |
| 99 "Scheduler::Scheduler", | 101 "Scheduler::Scheduler", |
| 100 "settings", | 102 "settings", |
| 101 settings_.AsValue()); | 103 settings_.AsValue()); |
| 102 DCHECK(client_); | 104 DCHECK(client_); |
| 103 DCHECK(!state_machine_.BeginFrameNeeded()); | 105 DCHECK(!state_machine_.BeginFrameNeeded()); |
| (...skipping 14 matching lines...) Expand all Loading... |
| 118 primary_frame_source_ = | 120 primary_frame_source_ = |
| 119 frame_sources_constructor->ConstructPrimaryFrameSource(this); | 121 frame_sources_constructor->ConstructPrimaryFrameSource(this); |
| 120 frame_source_->AddSource(primary_frame_source_); | 122 frame_source_->AddSource(primary_frame_source_); |
| 121 primary_frame_source_->SetClientReady(); | 123 primary_frame_source_->SetClientReady(); |
| 122 | 124 |
| 123 // Background ticking frame source | 125 // Background ticking frame source |
| 124 background_frame_source_ = | 126 background_frame_source_ = |
| 125 frame_sources_constructor->ConstructBackgroundFrameSource(this); | 127 frame_sources_constructor->ConstructBackgroundFrameSource(this); |
| 126 frame_source_->AddSource(background_frame_source_); | 128 frame_source_->AddSource(background_frame_source_); |
| 127 | 129 |
| 130 // Unthrottled frame source |
| 131 unthrottled_frame_source_ = |
| 132 frame_sources_constructor->ConstructUnthrottledFrameSource(this); |
| 133 frame_source_->AddSource(unthrottled_frame_source_); |
| 134 |
| 128 SetupPowerMonitoring(); | 135 SetupPowerMonitoring(); |
| 129 } | 136 } |
| 130 | 137 |
| 131 Scheduler::~Scheduler() { | 138 Scheduler::~Scheduler() { |
| 132 TeardownPowerMonitoring(); | 139 TeardownPowerMonitoring(); |
| 133 if (frame_source_->NeedsBeginFrames()) | 140 if (frame_source_->NeedsBeginFrames()) |
| 134 frame_source_->SetNeedsBeginFrames(false); | 141 frame_source_->SetNeedsBeginFrames(false); |
| 135 } | 142 } |
| 136 | 143 |
| 137 base::TimeTicks Scheduler::Now() const { | 144 base::TimeTicks Scheduler::Now() const { |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 177 void Scheduler::SetEstimatedParentDrawTime(base::TimeDelta draw_time) { | 184 void Scheduler::SetEstimatedParentDrawTime(base::TimeDelta draw_time) { |
| 178 DCHECK_GE(draw_time.ToInternalValue(), 0); | 185 DCHECK_GE(draw_time.ToInternalValue(), 0); |
| 179 estimated_parent_draw_time_ = draw_time; | 186 estimated_parent_draw_time_ = draw_time; |
| 180 } | 187 } |
| 181 | 188 |
| 182 void Scheduler::SetCanStart() { | 189 void Scheduler::SetCanStart() { |
| 183 state_machine_.SetCanStart(); | 190 state_machine_.SetCanStart(); |
| 184 ProcessScheduledActions(); | 191 ProcessScheduledActions(); |
| 185 } | 192 } |
| 186 | 193 |
| 187 void Scheduler::SetVisible(bool visible) { | 194 void Scheduler::UpdateActiveFrameSource() { |
| 188 state_machine_.SetVisible(visible); | 195 if (state_machine_.visible()) { |
| 189 if (visible) { | 196 if (throttle_frame_production_) { |
| 190 frame_source_->SetActiveSource(primary_frame_source_); | 197 frame_source_->SetActiveSource(primary_frame_source_); |
| 198 } else { |
| 199 frame_source_->SetActiveSource(unthrottled_frame_source_); |
| 200 } |
| 191 } else { | 201 } else { |
| 192 frame_source_->SetActiveSource(background_frame_source_); | 202 frame_source_->SetActiveSource(background_frame_source_); |
| 193 } | 203 } |
| 194 ProcessScheduledActions(); | 204 ProcessScheduledActions(); |
| 195 } | 205 } |
| 196 | 206 |
| 207 void Scheduler::SetVisible(bool visible) { |
| 208 state_machine_.SetVisible(visible); |
| 209 UpdateActiveFrameSource(); |
| 210 } |
| 211 |
| 197 void Scheduler::SetCanDraw(bool can_draw) { | 212 void Scheduler::SetCanDraw(bool can_draw) { |
| 198 state_machine_.SetCanDraw(can_draw); | 213 state_machine_.SetCanDraw(can_draw); |
| 199 ProcessScheduledActions(); | 214 ProcessScheduledActions(); |
| 200 } | 215 } |
| 201 | 216 |
| 202 void Scheduler::NotifyReadyToActivate() { | 217 void Scheduler::NotifyReadyToActivate() { |
| 203 state_machine_.NotifyReadyToActivate(); | 218 state_machine_.NotifyReadyToActivate(); |
| 204 ProcessScheduledActions(); | 219 ProcessScheduledActions(); |
| 205 } | 220 } |
| 206 | 221 |
| 207 void Scheduler::NotifyReadyToDraw() { | 222 void Scheduler::NotifyReadyToDraw() { |
| 208 // Empty for now, until we take action based on the notification as part of | 223 // Empty for now, until we take action based on the notification as part of |
| 209 // crbugs 352894, 383157, 421923. | 224 // crbugs 352894, 383157, 421923. |
| 210 } | 225 } |
| 211 | 226 |
| 227 void Scheduler::SetThrottleFrameProduction(bool throttle) { |
| 228 throttle_frame_production_ = throttle; |
| 229 UpdateActiveFrameSource(); |
| 230 } |
| 231 |
| 212 void Scheduler::SetNeedsCommit() { | 232 void Scheduler::SetNeedsCommit() { |
| 213 state_machine_.SetNeedsCommit(); | 233 state_machine_.SetNeedsCommit(); |
| 214 ProcessScheduledActions(); | 234 ProcessScheduledActions(); |
| 215 } | 235 } |
| 216 | 236 |
| 217 void Scheduler::SetNeedsRedraw() { | 237 void Scheduler::SetNeedsRedraw() { |
| 218 state_machine_.SetNeedsRedraw(); | 238 state_machine_.SetNeedsRedraw(); |
| 219 ProcessScheduledActions(); | 239 ProcessScheduledActions(); |
| 220 } | 240 } |
| 221 | 241 |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 266 state_machine_.BeginMainFrameAborted(reason); | 286 state_machine_.BeginMainFrameAborted(reason); |
| 267 ProcessScheduledActions(); | 287 ProcessScheduledActions(); |
| 268 } | 288 } |
| 269 | 289 |
| 270 void Scheduler::DidPrepareTiles() { | 290 void Scheduler::DidPrepareTiles() { |
| 271 state_machine_.DidPrepareTiles(); | 291 state_machine_.DidPrepareTiles(); |
| 272 } | 292 } |
| 273 | 293 |
| 274 void Scheduler::DidLoseOutputSurface() { | 294 void Scheduler::DidLoseOutputSurface() { |
| 275 TRACE_EVENT0("cc", "Scheduler::DidLoseOutputSurface"); | 295 TRACE_EVENT0("cc", "Scheduler::DidLoseOutputSurface"); |
| 296 begin_retro_frame_args_.clear(); |
| 297 begin_retro_frame_task_.Cancel(); |
| 276 state_machine_.DidLoseOutputSurface(); | 298 state_machine_.DidLoseOutputSurface(); |
| 277 if (frame_source_->NeedsBeginFrames()) | |
| 278 frame_source_->SetNeedsBeginFrames(false); | |
| 279 begin_retro_frame_args_.clear(); | |
| 280 ProcessScheduledActions(); | 299 ProcessScheduledActions(); |
| 281 } | 300 } |
| 282 | 301 |
| 283 void Scheduler::DidCreateAndInitializeOutputSurface() { | 302 void Scheduler::DidCreateAndInitializeOutputSurface() { |
| 284 TRACE_EVENT0("cc", "Scheduler::DidCreateAndInitializeOutputSurface"); | 303 TRACE_EVENT0("cc", "Scheduler::DidCreateAndInitializeOutputSurface"); |
| 285 DCHECK(!frame_source_->NeedsBeginFrames()); | 304 DCHECK(!frame_source_->NeedsBeginFrames()); |
| 286 DCHECK(begin_impl_frame_deadline_task_.IsCancelled()); | 305 DCHECK(begin_impl_frame_deadline_task_.IsCancelled()); |
| 287 state_machine_.DidCreateAndInitializeOutputSurface(); | 306 state_machine_.DidCreateAndInitializeOutputSurface(); |
| 288 ProcessScheduledActions(); | 307 ProcessScheduledActions(); |
| 289 } | 308 } |
| (...skipping 16 matching lines...) Expand all Loading... |
| 306 } | 325 } |
| 307 | 326 |
| 308 base::TimeTicks Scheduler::LastBeginImplFrameTime() { | 327 base::TimeTicks Scheduler::LastBeginImplFrameTime() { |
| 309 return begin_impl_frame_args_.frame_time; | 328 return begin_impl_frame_args_.frame_time; |
| 310 } | 329 } |
| 311 | 330 |
| 312 void Scheduler::SetupNextBeginFrameIfNeeded() { | 331 void Scheduler::SetupNextBeginFrameIfNeeded() { |
| 313 if (!task_runner_.get()) | 332 if (!task_runner_.get()) |
| 314 return; | 333 return; |
| 315 | 334 |
| 316 bool needs_begin_frame = state_machine_.BeginFrameNeeded(); | 335 if (state_machine_.ShouldSetNeedsBeginFrames( |
| 317 | 336 frame_source_->NeedsBeginFrames())) { |
| 318 bool at_end_of_deadline = | 337 frame_source_->SetNeedsBeginFrames(state_machine_.BeginFrameNeeded()); |
| 319 (state_machine_.begin_impl_frame_state() == | |
| 320 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_INSIDE_DEADLINE); | |
| 321 | |
| 322 bool should_call_set_needs_begin_frame = | |
| 323 // Always request the BeginFrame immediately if it wasn't needed before. | |
| 324 (needs_begin_frame && !frame_source_->NeedsBeginFrames()) || | |
| 325 // Only stop requesting BeginFrames after a deadline. | |
| 326 (!needs_begin_frame && frame_source_->NeedsBeginFrames() && | |
| 327 at_end_of_deadline); | |
| 328 | |
| 329 if (should_call_set_needs_begin_frame) { | |
| 330 frame_source_->SetNeedsBeginFrames(needs_begin_frame); | |
| 331 } | 338 } |
| 332 | 339 |
| 333 if (at_end_of_deadline) { | 340 if (state_machine_.begin_impl_frame_state() == |
| 341 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_INSIDE_DEADLINE) { |
| 334 frame_source_->DidFinishFrame(begin_retro_frame_args_.size()); | 342 frame_source_->DidFinishFrame(begin_retro_frame_args_.size()); |
| 335 } | 343 } |
| 336 | 344 |
| 337 PostBeginRetroFrameIfNeeded(); | 345 PostBeginRetroFrameIfNeeded(); |
| 338 SetupPollingMechanisms(needs_begin_frame); | 346 SetupPollingMechanisms(); |
| 339 } | 347 } |
| 340 | 348 |
| 341 // We may need to poll when we can't rely on BeginFrame to advance certain | 349 // We may need to poll when we can't rely on BeginFrame to advance certain |
| 342 // state or to avoid deadlock. | 350 // state or to avoid deadlock. |
| 343 void Scheduler::SetupPollingMechanisms(bool needs_begin_frame) { | 351 void Scheduler::SetupPollingMechanisms() { |
| 344 bool needs_advance_commit_state_timer = false; | 352 bool needs_advance_commit_state_timer = false; |
| 345 // Setup PollForAnticipatedDrawTriggers if we need to monitor state but | 353 // Setup PollForAnticipatedDrawTriggers if we need to monitor state but |
| 346 // aren't expecting any more BeginFrames. This should only be needed by | 354 // aren't expecting any more BeginFrames. This should only be needed by |
| 347 // the synchronous compositor when BeginFrameNeeded is false. | 355 // the synchronous compositor when BeginFrameNeeded is false. |
| 348 if (state_machine_.ShouldPollForAnticipatedDrawTriggers()) { | 356 if (state_machine_.ShouldPollForAnticipatedDrawTriggers()) { |
| 349 DCHECK(!state_machine_.SupportsProactiveBeginFrame()); | 357 DCHECK(!state_machine_.SupportsProactiveBeginFrame()); |
| 350 DCHECK(!needs_begin_frame); | |
| 351 if (poll_for_draw_triggers_task_.IsCancelled()) { | 358 if (poll_for_draw_triggers_task_.IsCancelled()) { |
| 352 poll_for_draw_triggers_task_.Reset(poll_for_draw_triggers_closure_); | 359 poll_for_draw_triggers_task_.Reset(poll_for_draw_triggers_closure_); |
| 353 base::TimeDelta delay = begin_impl_frame_args_.IsValid() | 360 base::TimeDelta delay = begin_impl_frame_args_.IsValid() |
| 354 ? begin_impl_frame_args_.interval | 361 ? begin_impl_frame_args_.interval |
| 355 : BeginFrameArgs::DefaultInterval(); | 362 : BeginFrameArgs::DefaultInterval(); |
| 356 task_runner_->PostDelayedTask( | 363 task_runner_->PostDelayedTask( |
| 357 FROM_HERE, poll_for_draw_triggers_task_.callback(), delay); | 364 FROM_HERE, poll_for_draw_triggers_task_.callback(), delay); |
| 358 } | 365 } |
| 359 } else { | 366 } else { |
| 360 poll_for_draw_triggers_task_.Cancel(); | 367 poll_for_draw_triggers_task_.Cancel(); |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 420 } | 427 } |
| 421 | 428 |
| 422 BeginFrameArgs adjusted_args(args); | 429 BeginFrameArgs adjusted_args(args); |
| 423 adjusted_args.deadline -= EstimatedParentDrawTime(); | 430 adjusted_args.deadline -= EstimatedParentDrawTime(); |
| 424 | 431 |
| 425 bool should_defer_begin_frame; | 432 bool should_defer_begin_frame; |
| 426 if (settings_.using_synchronous_renderer_compositor) { | 433 if (settings_.using_synchronous_renderer_compositor) { |
| 427 should_defer_begin_frame = false; | 434 should_defer_begin_frame = false; |
| 428 } else { | 435 } else { |
| 429 should_defer_begin_frame = | 436 should_defer_begin_frame = |
| 430 !begin_retro_frame_args_.empty() || begin_retro_frame_posted_ || | 437 !begin_retro_frame_args_.empty() || |
| 438 !begin_retro_frame_task_.IsCancelled() || |
| 431 !frame_source_->NeedsBeginFrames() || | 439 !frame_source_->NeedsBeginFrames() || |
| 432 (state_machine_.begin_impl_frame_state() != | 440 (state_machine_.begin_impl_frame_state() != |
| 433 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_IDLE); | 441 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_IDLE); |
| 434 } | 442 } |
| 435 | 443 |
| 436 if (should_defer_begin_frame) { | 444 if (should_defer_begin_frame) { |
| 437 begin_retro_frame_args_.push_back(adjusted_args); | 445 begin_retro_frame_args_.push_back(adjusted_args); |
| 438 TRACE_EVENT_INSTANT0( | 446 TRACE_EVENT_INSTANT0( |
| 439 "cc", "Scheduler::BeginFrame deferred", TRACE_EVENT_SCOPE_THREAD); | 447 "cc", "Scheduler::BeginFrame deferred", TRACE_EVENT_SCOPE_THREAD); |
| 440 // Queuing the frame counts as "using it", so we need to return true. | 448 // Queuing the frame counts as "using it", so we need to return true. |
| 441 } else { | 449 } else { |
| 442 BeginImplFrame(adjusted_args); | 450 BeginImplFrame(adjusted_args); |
| 443 } | 451 } |
| 444 return true; | 452 return true; |
| 445 } | 453 } |
| 446 | 454 |
| 447 void Scheduler::SetChildrenNeedBeginFrames(bool children_need_begin_frames) { | 455 void Scheduler::SetChildrenNeedBeginFrames(bool children_need_begin_frames) { |
| 448 DCHECK(settings_.forward_begin_frames_to_children); | 456 DCHECK(settings_.forward_begin_frames_to_children); |
| 449 state_machine_.SetChildrenNeedBeginFrames(children_need_begin_frames); | 457 state_machine_.SetChildrenNeedBeginFrames(children_need_begin_frames); |
| 450 ProcessScheduledActions(); | 458 ProcessScheduledActions(); |
| 451 } | 459 } |
| 452 | 460 |
| 453 // BeginRetroFrame is called for BeginFrames that we've deferred because | 461 // BeginRetroFrame is called for BeginFrames that we've deferred because |
| 454 // the scheduler was in the middle of processing a previous BeginFrame. | 462 // the scheduler was in the middle of processing a previous BeginFrame. |
| 455 void Scheduler::BeginRetroFrame() { | 463 void Scheduler::BeginRetroFrame() { |
| 456 TRACE_EVENT0("cc", "Scheduler::BeginRetroFrame"); | 464 TRACE_EVENT0("cc", "Scheduler::BeginRetroFrame"); |
| 457 DCHECK(!settings_.using_synchronous_renderer_compositor); | 465 DCHECK(!settings_.using_synchronous_renderer_compositor); |
| 458 DCHECK(begin_retro_frame_posted_); | 466 DCHECK(!begin_retro_frame_args_.empty()); |
| 467 DCHECK(!begin_retro_frame_task_.IsCancelled()); |
| 459 DCHECK_EQ(state_machine_.begin_impl_frame_state(), | 468 DCHECK_EQ(state_machine_.begin_impl_frame_state(), |
| 460 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_IDLE); | 469 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_IDLE); |
| 461 begin_retro_frame_posted_ = false; | |
| 462 | 470 |
| 463 // If there aren't any retroactive BeginFrames, then we've lost the | 471 begin_retro_frame_task_.Cancel(); |
| 464 // OutputSurface and should abort. | |
| 465 if (begin_retro_frame_args_.empty()) | |
| 466 return; | |
| 467 | 472 |
| 468 // Discard expired BeginRetroFrames | 473 // Discard expired BeginRetroFrames |
| 469 // Today, we should always end up with at most one un-expired BeginRetroFrame | 474 // Today, we should always end up with at most one un-expired BeginRetroFrame |
| 470 // because deadlines will not be greater than the next frame time. We don't | 475 // because deadlines will not be greater than the next frame time. We don't |
| 471 // DCHECK though because some systems don't always have monotonic timestamps. | 476 // DCHECK though because some systems don't always have monotonic timestamps. |
| 472 // TODO(brianderson): In the future, long deadlines could result in us not | 477 // TODO(brianderson): In the future, long deadlines could result in us not |
| 473 // draining the queue if we don't catch up. If we consistently can't catch | 478 // draining the queue if we don't catch up. If we consistently can't catch |
| 474 // up, our fallback should be to lower our frame rate. | 479 // up, our fallback should be to lower our frame rate. |
| 475 base::TimeTicks now = Now(); | 480 base::TimeTicks now = Now(); |
| 476 | 481 |
| (...skipping 26 matching lines...) Expand all Loading... |
| 503 // will check if there is a pending BeginRetroFrame to ensure we handle | 508 // will check if there is a pending BeginRetroFrame to ensure we handle |
| 504 // BeginFrames in FIFO order. | 509 // BeginFrames in FIFO order. |
| 505 void Scheduler::PostBeginRetroFrameIfNeeded() { | 510 void Scheduler::PostBeginRetroFrameIfNeeded() { |
| 506 TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("cc.debug.scheduler"), | 511 TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("cc.debug.scheduler"), |
| 507 "Scheduler::PostBeginRetroFrameIfNeeded", | 512 "Scheduler::PostBeginRetroFrameIfNeeded", |
| 508 "state", | 513 "state", |
| 509 AsValue()); | 514 AsValue()); |
| 510 if (!frame_source_->NeedsBeginFrames()) | 515 if (!frame_source_->NeedsBeginFrames()) |
| 511 return; | 516 return; |
| 512 | 517 |
| 513 if (begin_retro_frame_args_.empty() || begin_retro_frame_posted_) | 518 if (begin_retro_frame_args_.empty() || !begin_retro_frame_task_.IsCancelled()) |
| 514 return; | 519 return; |
| 515 | 520 |
| 516 // begin_retro_frame_args_ should always be empty for the | 521 // begin_retro_frame_args_ should always be empty for the |
| 517 // synchronous compositor. | 522 // synchronous compositor. |
| 518 DCHECK(!settings_.using_synchronous_renderer_compositor); | 523 DCHECK(!settings_.using_synchronous_renderer_compositor); |
| 519 | 524 |
| 520 if (state_machine_.begin_impl_frame_state() != | 525 if (state_machine_.begin_impl_frame_state() != |
| 521 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_IDLE) | 526 SchedulerStateMachine::BEGIN_IMPL_FRAME_STATE_IDLE) |
| 522 return; | 527 return; |
| 523 | 528 |
| 524 begin_retro_frame_posted_ = true; | 529 begin_retro_frame_task_.Reset(begin_retro_frame_closure_); |
| 525 task_runner_->PostTask(FROM_HERE, begin_retro_frame_closure_); | 530 |
| 531 task_runner_->PostTask(FROM_HERE, begin_retro_frame_task_.callback()); |
| 526 } | 532 } |
| 527 | 533 |
| 528 // BeginImplFrame starts a compositor frame that will wait up until a deadline | 534 // BeginImplFrame starts a compositor frame that will wait up until a deadline |
| 529 // for a BeginMainFrame+activation to complete before it times out and draws | 535 // for a BeginMainFrame+activation to complete before it times out and draws |
| 530 // any asynchronous animation and scroll/pinch updates. | 536 // any asynchronous animation and scroll/pinch updates. |
| 531 void Scheduler::BeginImplFrame(const BeginFrameArgs& args) { | 537 void Scheduler::BeginImplFrame(const BeginFrameArgs& args) { |
| 532 bool main_thread_is_in_high_latency_mode = | 538 bool main_thread_is_in_high_latency_mode = |
| 533 state_machine_.MainThreadIsInHighLatencyMode(); | 539 state_machine_.MainThreadIsInHighLatencyMode(); |
| 534 TRACE_EVENT2("cc", | 540 TRACE_EVENT2("cc", |
| 535 "Scheduler::BeginImplFrame", | 541 "Scheduler::BeginImplFrame", |
| (...skipping 214 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 750 state->EndDictionary(); | 756 state->EndDictionary(); |
| 751 } | 757 } |
| 752 | 758 |
| 753 state->BeginDictionary("scheduler_state"); | 759 state->BeginDictionary("scheduler_state"); |
| 754 state->SetDouble("time_until_anticipated_draw_time_ms", | 760 state->SetDouble("time_until_anticipated_draw_time_ms", |
| 755 (AnticipatedDrawTime() - Now()).InMillisecondsF()); | 761 (AnticipatedDrawTime() - Now()).InMillisecondsF()); |
| 756 state->SetDouble("estimated_parent_draw_time_ms", | 762 state->SetDouble("estimated_parent_draw_time_ms", |
| 757 estimated_parent_draw_time_.InMillisecondsF()); | 763 estimated_parent_draw_time_.InMillisecondsF()); |
| 758 state->SetBoolean("last_set_needs_begin_frame_", | 764 state->SetBoolean("last_set_needs_begin_frame_", |
| 759 frame_source_->NeedsBeginFrames()); | 765 frame_source_->NeedsBeginFrames()); |
| 760 state->SetBoolean("begin_retro_frame_posted_", begin_retro_frame_posted_); | |
| 761 state->SetInteger("begin_retro_frame_args_", begin_retro_frame_args_.size()); | 766 state->SetInteger("begin_retro_frame_args_", begin_retro_frame_args_.size()); |
| 767 state->SetBoolean("begin_retro_frame_task_", |
| 768 !begin_retro_frame_task_.IsCancelled()); |
| 762 state->SetBoolean("begin_impl_frame_deadline_task_", | 769 state->SetBoolean("begin_impl_frame_deadline_task_", |
| 763 !begin_impl_frame_deadline_task_.IsCancelled()); | 770 !begin_impl_frame_deadline_task_.IsCancelled()); |
| 764 state->SetBoolean("poll_for_draw_triggers_task_", | 771 state->SetBoolean("poll_for_draw_triggers_task_", |
| 765 !poll_for_draw_triggers_task_.IsCancelled()); | 772 !poll_for_draw_triggers_task_.IsCancelled()); |
| 766 state->SetBoolean("advance_commit_state_task_", | 773 state->SetBoolean("advance_commit_state_task_", |
| 767 !advance_commit_state_task_.IsCancelled()); | 774 !advance_commit_state_task_.IsCancelled()); |
| 768 state->BeginDictionary("begin_impl_frame_args"); | 775 state->BeginDictionary("begin_impl_frame_args"); |
| 769 begin_impl_frame_args_.AsValueInto(state); | 776 begin_impl_frame_args_.AsValueInto(state); |
| 770 state->EndDictionary(); | 777 state->EndDictionary(); |
| 771 | 778 |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 803 } | 810 } |
| 804 | 811 |
| 805 bool Scheduler::IsBeginMainFrameSentOrStarted() const { | 812 bool Scheduler::IsBeginMainFrameSentOrStarted() const { |
| 806 return (state_machine_.commit_state() == | 813 return (state_machine_.commit_state() == |
| 807 SchedulerStateMachine::COMMIT_STATE_BEGIN_MAIN_FRAME_SENT || | 814 SchedulerStateMachine::COMMIT_STATE_BEGIN_MAIN_FRAME_SENT || |
| 808 state_machine_.commit_state() == | 815 state_machine_.commit_state() == |
| 809 SchedulerStateMachine::COMMIT_STATE_BEGIN_MAIN_FRAME_STARTED); | 816 SchedulerStateMachine::COMMIT_STATE_BEGIN_MAIN_FRAME_STARTED); |
| 810 } | 817 } |
| 811 | 818 |
| 812 } // namespace cc | 819 } // namespace cc |
| OLD | NEW |