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

Side by Side Diff: cc/scheduler/begin_frame_source.cc

Issue 2819723002: cc: Add more info to the BeginMainFrame dump. (Closed)
Patch Set: more tracing Created 3 years, 8 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
« no previous file with comments | « cc/scheduler/begin_frame_source.h ('k') | cc/scheduler/scheduler.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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 "cc/scheduler/begin_frame_source.h" 5 #include "cc/scheduler/begin_frame_source.h"
6 6
7 #include <stddef.h> 7 #include <stddef.h>
8 8
9 #include "base/atomic_sequence_num.h" 9 #include "base/atomic_sequence_num.h"
10 #include "base/auto_reset.h" 10 #include "base/auto_reset.h"
11 #include "base/location.h" 11 #include "base/location.h"
12 #include "base/logging.h" 12 #include "base/logging.h"
13 #include "base/memory/ptr_util.h" 13 #include "base/memory/ptr_util.h"
14 #include "base/strings/string_number_conversions.h" 14 #include "base/strings/string_number_conversions.h"
15 #include "base/strings/stringprintf.h" 15 #include "base/strings/stringprintf.h"
16 #include "base/trace_event/trace_event.h" 16 #include "base/trace_event/trace_event.h"
17 #include "base/trace_event/trace_event_argument.h" 17 #include "base/trace_event/trace_event_argument.h"
18 #include "cc/scheduler/delay_based_time_source.h" 18 #include "cc/scheduler/delay_based_time_source.h"
19 #include "cc/scheduler/scheduler.h" 19 #include "cc/scheduler/scheduler.h"
20 20
21 namespace cc { 21 namespace cc {
22 22
23 namespace { 23 namespace {
24 // kDoubleTickDivisor prevents the SyntheticBFS from sending BeginFrames too 24 // kDoubleTickDivisor prevents the SyntheticBFS from sending BeginFrames too
25 // often to an observer. 25 // often to an observer.
26 static const double kDoubleTickDivisor = 2.0; 26 static const double kDoubleTickDivisor = 2.0;
27 } 27 }
28 28
29 // BeginFrameObserverBase ------------------------------------------------- 29 // BeginFrameObserverBase -------------------------------------------------
30 BeginFrameObserverBase::BeginFrameObserverBase() 30 BeginFrameObserverBase::BeginFrameObserverBase() = default;
31 : last_begin_frame_args_(), dropped_begin_frame_args_(0) { 31
32 } 32 BeginFrameObserverBase::~BeginFrameObserverBase() = default;
33 33
34 const BeginFrameArgs& BeginFrameObserverBase::LastUsedBeginFrameArgs() const { 34 const BeginFrameArgs& BeginFrameObserverBase::LastUsedBeginFrameArgs() const {
35 return last_begin_frame_args_; 35 return last_begin_frame_args_;
36 } 36 }
37 37
38 void BeginFrameObserverBase::OnBeginFrame(const BeginFrameArgs& args) { 38 void BeginFrameObserverBase::OnBeginFrame(const BeginFrameArgs& args) {
39 DCHECK(args.IsValid()); 39 DCHECK(args.IsValid());
40 DCHECK(args.frame_time >= last_begin_frame_args_.frame_time); 40 DCHECK(args.frame_time >= last_begin_frame_args_.frame_time);
41 DCHECK(args.sequence_number > last_begin_frame_args_.sequence_number || 41 DCHECK(args.sequence_number > last_begin_frame_args_.sequence_number ||
42 args.source_id != last_begin_frame_args_.source_id) 42 args.source_id != last_begin_frame_args_.source_id)
43 << "current " << args.AsValue()->ToString() << ", last " 43 << "current " << args.AsValue()->ToString() << ", last "
44 << last_begin_frame_args_.AsValue()->ToString(); 44 << last_begin_frame_args_.AsValue()->ToString();
45 bool used = OnBeginFrameDerivedImpl(args); 45 bool used = OnBeginFrameDerivedImpl(args);
46 if (used) { 46 if (used) {
47 last_begin_frame_args_ = args; 47 last_begin_frame_args_ = args;
48 } else { 48 } else {
49 ++dropped_begin_frame_args_; 49 ++dropped_begin_frame_args_;
50 } 50 }
51 } 51 }
52 52
53 void BeginFrameObserverBase::AsValueInto(
54 base::trace_event::TracedValue* state) const {
55 state->SetInteger("dropped_begin_frame_args", dropped_begin_frame_args_);
56
57 state->BeginDictionary("last_begin_frame_args");
58 last_begin_frame_args_.AsValueInto(state);
59 state->EndDictionary();
60 }
61
53 // BeginFrameSource ------------------------------------------------------- 62 // BeginFrameSource -------------------------------------------------------
54 namespace { 63 namespace {
55 static base::StaticAtomicSequenceNumber g_next_source_id; 64 static base::StaticAtomicSequenceNumber g_next_source_id;
56 } // namespace 65 } // namespace
57 66
58 BeginFrameSource::BeginFrameSource() : source_id_(g_next_source_id.GetNext()) {} 67 BeginFrameSource::BeginFrameSource() : source_id_(g_next_source_id.GetNext()) {}
59 68
60 uint32_t BeginFrameSource::source_id() const { 69 BeginFrameSource::~BeginFrameSource() = default;
61 return source_id_; 70
71 void BeginFrameSource::AsValueInto(
72 base::trace_event::TracedValue* state) const {
73 state->SetInteger("source_id", source_id_);
62 } 74 }
63 75
64 // StubBeginFrameSource --------------------------------------------------- 76 // StubBeginFrameSource ---------------------------------------------------
65 bool StubBeginFrameSource::IsThrottled() const { 77 bool StubBeginFrameSource::IsThrottled() const {
66 return true; 78 return true;
67 } 79 }
68 80
69 // SyntheticBeginFrameSource ---------------------------------------------- 81 // SyntheticBeginFrameSource ----------------------------------------------
70 SyntheticBeginFrameSource::~SyntheticBeginFrameSource() = default; 82 SyntheticBeginFrameSource::~SyntheticBeginFrameSource() = default;
71 83
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after
234 if (!last_args.IsValid() || 246 if (!last_args.IsValid() ||
235 (current_begin_frame_args_.frame_time > 247 (current_begin_frame_args_.frame_time >
236 last_args.frame_time + 248 last_args.frame_time +
237 current_begin_frame_args_.interval / kDoubleTickDivisor)) { 249 current_begin_frame_args_.interval / kDoubleTickDivisor)) {
238 obs->OnBeginFrame(current_begin_frame_args_); 250 obs->OnBeginFrame(current_begin_frame_args_);
239 } 251 }
240 } 252 }
241 } 253 }
242 254
243 // BeginFrameObserverAckTracker ------------------------------------------- 255 // BeginFrameObserverAckTracker -------------------------------------------
244 BeginFrameObserverAckTracker::BeginFrameObserverAckTracker() 256 BeginFrameObserverAckTracker::BeginFrameObserverAckTracker() = default;
245 : current_source_id_(0),
246 current_sequence_number_(BeginFrameArgs::kStartingFrameNumber),
247 observers_had_damage_(false) {}
248 257
249 BeginFrameObserverAckTracker::~BeginFrameObserverAckTracker() {} 258 BeginFrameObserverAckTracker::~BeginFrameObserverAckTracker() = default;
250 259
251 void BeginFrameObserverAckTracker::OnBeginFrame(const BeginFrameArgs& args) { 260 void BeginFrameObserverAckTracker::OnBeginFrame(const BeginFrameArgs& args) {
252 if (current_source_id_ != args.source_id) 261 if (current_source_id_ != args.source_id)
253 SourceChanged(args); 262 SourceChanged(args);
254 263
255 DCHECK_GE(args.sequence_number, current_sequence_number_); 264 DCHECK_GE(args.sequence_number, current_sequence_number_);
256 // Reset for new BeginFrame. 265 // Reset for new BeginFrame.
257 current_sequence_number_ = args.sequence_number; 266 current_sequence_number_ = args.sequence_number;
258 finished_observers_.clear(); 267 finished_observers_.clear();
259 observers_had_damage_ = false; 268 observers_had_damage_ = false;
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
327 336
328 uint64_t BeginFrameObserverAckTracker::LatestConfirmedSequenceNumber() const { 337 uint64_t BeginFrameObserverAckTracker::LatestConfirmedSequenceNumber() const {
329 uint64_t latest_confirmed_sequence_number = current_sequence_number_; 338 uint64_t latest_confirmed_sequence_number = current_sequence_number_;
330 for (const auto& entry : latest_confirmed_sequence_numbers_) { 339 for (const auto& entry : latest_confirmed_sequence_numbers_) {
331 latest_confirmed_sequence_number = 340 latest_confirmed_sequence_number =
332 std::min(latest_confirmed_sequence_number, entry.second); 341 std::min(latest_confirmed_sequence_number, entry.second);
333 } 342 }
334 return latest_confirmed_sequence_number; 343 return latest_confirmed_sequence_number;
335 } 344 }
336 345
346 void BeginFrameObserverAckTracker::AsValueInto(
347 base::trace_event::TracedValue* state) const {
348 base::SmallMap<std::map<BeginFrameObserver*, uint64_t>, 4>
349 latest_confirmed_sequence_numbers_;
350 state->SetInteger("current_source_id", current_source_id_);
351 state->SetInteger("current_sequence_number", current_sequence_number_);
352 state->SetInteger("num_observers", observers_.size());
353 state->SetInteger("num_finished_observers", finished_observers_.size());
354 state->SetBoolean("observers_had_damage", observers_had_damage_);
355
356 state->BeginArray("latest_confirmed_sequence_numbers");
357 for (const auto& kv : latest_confirmed_sequence_numbers_) {
358 state->AppendInteger(kv.second);
359 }
360 state->EndArray();
361 }
362
337 // ExternalBeginFrameSource ----------------------------------------------- 363 // ExternalBeginFrameSource -----------------------------------------------
338 ExternalBeginFrameSource::ExternalBeginFrameSource( 364 ExternalBeginFrameSource::ExternalBeginFrameSource(
339 ExternalBeginFrameSourceClient* client) 365 ExternalBeginFrameSourceClient* client)
340 : client_(client) { 366 : client_(client) {
341 DCHECK(client_); 367 DCHECK(client_);
342 } 368 }
343 369
344 ExternalBeginFrameSource::~ExternalBeginFrameSource() = default; 370 ExternalBeginFrameSource::~ExternalBeginFrameSource() = default;
345 371
372 void ExternalBeginFrameSource::AsValueInto(
373 base::trace_event::TracedValue* state) const {
374 BeginFrameSource::AsValueInto(state);
375
376 state->SetBoolean("paused", paused_);
377 state->SetBoolean("frame_active", frame_active_);
378 state->SetInteger("num_observers", observers_.size());
379
380 state->BeginDictionary("last_begin_frame_args");
381 last_begin_frame_args_.AsValueInto(state);
382 state->EndDictionary();
383
384 state->BeginDictionary("ack_tracker_state");
385 ack_tracker_.AsValueInto(state);
386 state->EndDictionary();
387 }
388
346 void ExternalBeginFrameSource::AddObserver(BeginFrameObserver* obs) { 389 void ExternalBeginFrameSource::AddObserver(BeginFrameObserver* obs) {
347 DCHECK(obs); 390 DCHECK(obs);
348 DCHECK(observers_.find(obs) == observers_.end()); 391 DCHECK(observers_.find(obs) == observers_.end());
349 392
350 bool observers_was_empty = observers_.empty(); 393 bool observers_was_empty = observers_.empty();
351 observers_.insert(obs); 394 observers_.insert(obs);
352 ack_tracker_.OnObserverAdded(obs); 395 ack_tracker_.OnObserverAdded(obs);
353 obs->OnBeginFrameSourcePausedChanged(paused_); 396 obs->OnBeginFrameSourcePausedChanged(paused_);
354 if (observers_was_empty) 397 if (observers_was_empty)
355 client_->OnNeedsBeginFrames(true); 398 client_->OnNeedsBeginFrames(true);
356 399
357 // Send a MISSED begin frame if necessary. 400 // Send a MISSED begin frame if necessary.
358 if (missed_begin_frame_args_.IsValid()) { 401 if (last_begin_frame_args_.IsValid()) {
359 const BeginFrameArgs& last_args = obs->LastUsedBeginFrameArgs(); 402 const BeginFrameArgs& last_args = obs->LastUsedBeginFrameArgs();
360 if (!last_args.IsValid() || 403 if (!last_args.IsValid() ||
361 (missed_begin_frame_args_.frame_time > last_args.frame_time)) { 404 (last_begin_frame_args_.frame_time > last_args.frame_time)) {
362 DCHECK((missed_begin_frame_args_.source_id != last_args.source_id) || 405 DCHECK(
363 (missed_begin_frame_args_.sequence_number > 406 (last_begin_frame_args_.source_id != last_args.source_id) ||
364 last_args.sequence_number)) 407 (last_begin_frame_args_.sequence_number > last_args.sequence_number))
365 << "current " << missed_begin_frame_args_.AsValue()->ToString() 408 << "current " << last_begin_frame_args_.AsValue()->ToString()
366 << ", last " << last_args.AsValue()->ToString(); 409 << ", last " << last_args.AsValue()->ToString();
367 obs->OnBeginFrame(missed_begin_frame_args_); 410 BeginFrameArgs missed_args = last_begin_frame_args_;
411 missed_args.type = BeginFrameArgs::MISSED;
412 obs->OnBeginFrame(missed_args);
368 } 413 }
369 } 414 }
370 } 415 }
371 416
372 void ExternalBeginFrameSource::RemoveObserver(BeginFrameObserver* obs) { 417 void ExternalBeginFrameSource::RemoveObserver(BeginFrameObserver* obs) {
373 DCHECK(obs); 418 DCHECK(obs);
374 DCHECK(observers_.find(obs) != observers_.end()); 419 DCHECK(observers_.find(obs) != observers_.end());
375 420
376 observers_.erase(obs); 421 observers_.erase(obs);
377 ack_tracker_.OnObserverRemoved(obs); 422 ack_tracker_.OnObserverRemoved(obs);
378 MaybeFinishFrame(); 423 MaybeFinishFrame();
379 if (observers_.empty()) { 424 if (observers_.empty()) {
380 missed_begin_frame_args_ = BeginFrameArgs(); 425 last_begin_frame_args_ = BeginFrameArgs();
381 client_->OnNeedsBeginFrames(false); 426 client_->OnNeedsBeginFrames(false);
382 } 427 }
383 } 428 }
384 429
385 void ExternalBeginFrameSource::DidFinishFrame(BeginFrameObserver* obs, 430 void ExternalBeginFrameSource::DidFinishFrame(BeginFrameObserver* obs,
386 const BeginFrameAck& ack) { 431 const BeginFrameAck& ack) {
387 ack_tracker_.OnObserverFinishedFrame(obs, ack); 432 ack_tracker_.OnObserverFinishedFrame(obs, ack);
388 MaybeFinishFrame(); 433 MaybeFinishFrame();
389 } 434 }
390 435
391 bool ExternalBeginFrameSource::IsThrottled() const { 436 bool ExternalBeginFrameSource::IsThrottled() const {
392 return true; 437 return true;
393 } 438 }
394 439
395 void ExternalBeginFrameSource::OnSetBeginFrameSourcePaused(bool paused) { 440 void ExternalBeginFrameSource::OnSetBeginFrameSourcePaused(bool paused) {
396 if (paused_ == paused) 441 if (paused_ == paused)
397 return; 442 return;
398 paused_ = paused; 443 paused_ = paused;
399 std::unordered_set<BeginFrameObserver*> observers(observers_); 444 std::unordered_set<BeginFrameObserver*> observers(observers_);
400 for (auto* obs : observers) 445 for (auto* obs : observers)
401 obs->OnBeginFrameSourcePausedChanged(paused_); 446 obs->OnBeginFrameSourcePausedChanged(paused_);
402 } 447 }
403 448
404 void ExternalBeginFrameSource::OnBeginFrame(const BeginFrameArgs& args) { 449 void ExternalBeginFrameSource::OnBeginFrame(const BeginFrameArgs& args) {
405 if (frame_active_) 450 if (frame_active_)
406 FinishFrame(); 451 FinishFrame();
407 452
408 frame_active_ = true; 453 frame_active_ = true;
409 missed_begin_frame_args_ = args; 454 last_begin_frame_args_ = args;
sunnyps 2017/04/14 23:24:11 NOTE: I don't set type to MISSED here because I wa
410 missed_begin_frame_args_.type = BeginFrameArgs::MISSED;
411 ack_tracker_.OnBeginFrame(args); 455 ack_tracker_.OnBeginFrame(args);
412 std::unordered_set<BeginFrameObserver*> observers(observers_); 456 std::unordered_set<BeginFrameObserver*> observers(observers_);
413 for (auto* obs : observers) { 457 for (auto* obs : observers) {
414 // It is possible that the source in which |args| originate changes, or that 458 // It is possible that the source in which |args| originate changes, or that
415 // our hookup to this source changes, so we have to check for continuity. 459 // our hookup to this source changes, so we have to check for continuity.
416 // See also https://crbug.com/690127 for what may happen without this check. 460 // See also https://crbug.com/690127 for what may happen without this check.
417 const BeginFrameArgs& last_args = obs->LastUsedBeginFrameArgs(); 461 const BeginFrameArgs& last_args = obs->LastUsedBeginFrameArgs();
418 if (!last_args.IsValid() || (args.frame_time > last_args.frame_time)) { 462 if (!last_args.IsValid() || (args.frame_time > last_args.frame_time)) {
419 DCHECK((args.source_id != last_args.source_id) || 463 DCHECK((args.source_id != last_args.source_id) ||
420 (args.sequence_number > last_args.sequence_number)) 464 (args.sequence_number > last_args.sequence_number))
421 << "current " << args.AsValue()->ToString() << ", last " 465 << "current " << args.AsValue()->ToString() << ", last "
422 << last_args.AsValue()->ToString(); 466 << last_args.AsValue()->ToString();
423 obs->OnBeginFrame(args); 467 obs->OnBeginFrame(args);
424 } 468 }
425 } 469 }
426 MaybeFinishFrame(); 470 MaybeFinishFrame();
427 } 471 }
428 472
429 void ExternalBeginFrameSource::MaybeFinishFrame() { 473 void ExternalBeginFrameSource::MaybeFinishFrame() {
430 if (!frame_active_ || !ack_tracker_.AllObserversFinishedFrame()) 474 if (!frame_active_ || !ack_tracker_.AllObserversFinishedFrame())
431 return; 475 return;
432 FinishFrame(); 476 FinishFrame();
433 } 477 }
434 478
435 void ExternalBeginFrameSource::FinishFrame() { 479 void ExternalBeginFrameSource::FinishFrame() {
436 frame_active_ = false; 480 frame_active_ = false;
437 481
438 BeginFrameAck ack(missed_begin_frame_args_.source_id, 482 BeginFrameAck ack(last_begin_frame_args_.source_id,
439 missed_begin_frame_args_.sequence_number, 483 last_begin_frame_args_.sequence_number,
440 ack_tracker_.LatestConfirmedSequenceNumber(), 484 ack_tracker_.LatestConfirmedSequenceNumber(),
441 ack_tracker_.AnyObserversHadDamage()); 485 ack_tracker_.AnyObserversHadDamage());
442 client_->OnDidFinishFrame(ack); 486 client_->OnDidFinishFrame(ack);
443 } 487 }
444 488
445 } // namespace cc 489 } // namespace cc
OLDNEW
« no previous file with comments | « cc/scheduler/begin_frame_source.h ('k') | cc/scheduler/scheduler.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698