Chromium Code Reviews| OLD | NEW |
|---|---|
| 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 <map> | 5 #include <map> |
| 6 #include <vector> | 6 #include <vector> |
| 7 | 7 |
| 8 #include "base/basictypes.h" | 8 #include "base/basictypes.h" |
| 9 #include "base/command_line.h" | 9 #include "base/command_line.h" |
| 10 #if defined(OS_MACOSX) | 10 #if defined(OS_MACOSX) |
| 11 #include "base/mac/mac_util.h" | 11 #include "base/mac/mac_util.h" |
| 12 #endif | 12 #endif |
| 13 #include "base/strings/stringprintf.h" | 13 #include "base/strings/stringprintf.h" |
| 14 #include "base/test/trace_event_analyzer.h" | 14 #include "base/test/trace_event_analyzer.h" |
| 15 #include "base/time/default_tick_clock.h" | |
| 15 #include "base/win/windows_version.h" | 16 #include "base/win/windows_version.h" |
| 16 #include "chrome/browser/extensions/extension_apitest.h" | 17 #include "chrome/browser/extensions/extension_apitest.h" |
| 17 #include "chrome/browser/extensions/extension_service.h" | 18 #include "chrome/browser/extensions/extension_service.h" |
| 18 #include "chrome/browser/extensions/extension_test_message_listener.h" | 19 #include "chrome/browser/extensions/extension_test_message_listener.h" |
| 19 #include "chrome/browser/extensions/tab_helper.h" | 20 #include "chrome/browser/extensions/tab_helper.h" |
| 20 #include "chrome/browser/profiles/profile.h" | 21 #include "chrome/browser/profiles/profile.h" |
| 21 #include "chrome/browser/ui/fullscreen/fullscreen_controller.h" | 22 #include "chrome/browser/ui/fullscreen/fullscreen_controller.h" |
| 22 #include "chrome/common/chrome_switches.h" | 23 #include "chrome/common/chrome_switches.h" |
| 23 #include "chrome/common/chrome_version_info.h" | 24 #include "chrome/common/chrome_version_info.h" |
| 24 #include "chrome/test/base/test_launcher_utils.h" | 25 #include "chrome/test/base/test_launcher_utils.h" |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 65 // on the command line. This is required for | 66 // on the command line. This is required for |
| 66 // tests that run on GPU. | 67 // tests that run on GPU. |
| 67 kDisableVsync = 1 << 1, // Do not limit framerate to vertical refresh. | 68 kDisableVsync = 1 << 1, // Do not limit framerate to vertical refresh. |
| 68 // when on GPU, nor to 60hz when not on GPU. | 69 // when on GPU, nor to 60hz when not on GPU. |
| 69 kSmallWindow = 1 << 2, // 1 = 800x600, 0 = 2000x1000 | 70 kSmallWindow = 1 << 2, // 1 = 800x600, 0 = 2000x1000 |
| 70 k24fps = 1 << 3, // use 24 fps video | 71 k24fps = 1 << 3, // use 24 fps video |
| 71 k30fps = 1 << 4, // use 30 fps video | 72 k30fps = 1 << 4, // use 30 fps video |
| 72 k60fps = 1 << 5, // use 60 fps video | 73 k60fps = 1 << 5, // use 60 fps video |
| 73 kProxyWifi = 1 << 6, // Run UDP through UDPProxy wifi profile | 74 kProxyWifi = 1 << 6, // Run UDP through UDPProxy wifi profile |
| 74 kProxyEvil = 1 << 7, // Run UDP through UDPProxy evil profile | 75 kProxyEvil = 1 << 7, // Run UDP through UDPProxy evil profile |
| 76 kSlowClock = 1 << 8, // Receiver clock is 10 seconds slow | |
| 77 kFastClock = 1 << 9, // Receiver clock is 10 seconds fast | |
| 78 }; | |
| 79 | |
| 80 class SkewedTickClock : public base::DefaultTickClock { | |
| 81 public: | |
| 82 explicit SkewedTickClock(const base::TimeDelta& delta) : delta_(delta) { | |
| 83 } | |
| 84 virtual base::TimeTicks NowTicks() OVERRIDE { | |
| 85 return DefaultTickClock::NowTicks() + delta_; | |
| 86 } | |
| 87 private: | |
| 88 base::TimeDelta delta_; | |
| 75 }; | 89 }; |
| 76 | 90 |
| 77 // We log one of these for each call to OnAudioFrame/OnVideoFrame. | 91 // We log one of these for each call to OnAudioFrame/OnVideoFrame. |
| 78 struct TimeData { | 92 struct TimeData { |
| 79 TimeData(uint16 frame_no_, base::TimeTicks render_time_) : | 93 TimeData(uint16 frame_no_, base::TimeTicks render_time_) : |
| 80 frame_no(frame_no_), | 94 frame_no(frame_no_), |
| 81 render_time(render_time_) { | 95 render_time(render_time_) { |
| 82 } | 96 } |
| 83 // The unit here is video frames, for audio data there can be duplicates. | 97 // The unit here is video frames, for audio data there can be duplicates. |
| 84 // This was decoded from the actual audio/video data. | 98 // This was decoded from the actual audio/video data. |
| (...skipping 30 matching lines...) Expand all Loading... | |
| 115 const std::string& unit) { | 129 const std::string& unit) { |
| 116 if (num_values >= 20) { | 130 if (num_values >= 20) { |
| 117 perf_test::PrintResultMeanAndError(measurement, | 131 perf_test::PrintResultMeanAndError(measurement, |
| 118 modifier, | 132 modifier, |
| 119 trace, | 133 trace, |
| 120 AsString(), | 134 AsString(), |
| 121 unit, | 135 unit, |
| 122 true); | 136 true); |
| 123 } else { | 137 } else { |
| 124 LOG(ERROR) << "Not enough events for " | 138 LOG(ERROR) << "Not enough events for " |
| 125 << measurement << " " << modifier << " " << trace; | 139 << measurement << modifier << " " << trace; |
| 126 } | 140 } |
| 127 } | 141 } |
| 128 | 142 |
| 129 size_t num_values; | 143 size_t num_values; |
| 130 double mean; | 144 double mean; |
| 131 double std_dev; | 145 double std_dev; |
| 132 }; | 146 }; |
| 133 | 147 |
| 134 // This function checks how smooth the data in |data| is. | 148 // This function checks how smooth the data in |data| is. |
| 135 // It computes the average error of deltas and the average delta. | 149 // It computes the average error of deltas and the average delta. |
| (...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 284 if (HasFlag(k24fps)) | 298 if (HasFlag(k24fps)) |
| 285 suffix += "_24fps"; | 299 suffix += "_24fps"; |
| 286 if (HasFlag(k30fps)) | 300 if (HasFlag(k30fps)) |
| 287 suffix += "_30fps"; | 301 suffix += "_30fps"; |
| 288 if (HasFlag(k60fps)) | 302 if (HasFlag(k60fps)) |
| 289 suffix += "_60fps"; | 303 suffix += "_60fps"; |
| 290 if (HasFlag(kProxyWifi)) | 304 if (HasFlag(kProxyWifi)) |
| 291 suffix += "_wifi"; | 305 suffix += "_wifi"; |
| 292 if (HasFlag(kProxyEvil)) | 306 if (HasFlag(kProxyEvil)) |
| 293 suffix += "_evil"; | 307 suffix += "_evil"; |
| 308 if (HasFlag(kSlowClock)) | |
| 309 suffix += "_slow"; | |
| 310 if (HasFlag(kFastClock)) | |
| 311 suffix += "_fast"; | |
| 294 return suffix; | 312 return suffix; |
| 295 } | 313 } |
| 296 | 314 |
| 297 int getfps() { | 315 int getfps() { |
| 298 if (HasFlag(k24fps)) | 316 if (HasFlag(k24fps)) |
| 299 return 24; | 317 return 24; |
| 300 if (HasFlag(k30fps)) | 318 if (HasFlag(k30fps)) |
| 301 return 30; | 319 return 30; |
| 302 if (HasFlag(k60fps)) | 320 if (HasFlag(k60fps)) |
| 303 return 60; | 321 return 60; |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 360 } | 378 } |
| 361 | 379 |
| 362 void GetTraceEvents(trace_analyzer::TraceAnalyzer* analyzer, | 380 void GetTraceEvents(trace_analyzer::TraceAnalyzer* analyzer, |
| 363 const std::string& event_name, | 381 const std::string& event_name, |
| 364 trace_analyzer::TraceEventVector* events) { | 382 trace_analyzer::TraceEventVector* events) { |
| 365 trace_analyzer::Query query = | 383 trace_analyzer::Query query = |
| 366 trace_analyzer::Query::EventNameIs(event_name) && | 384 trace_analyzer::Query::EventNameIs(event_name) && |
| 367 (trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_BEGIN) || | 385 (trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_BEGIN) || |
| 368 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_ASYNC_BEGIN) || | 386 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_ASYNC_BEGIN) || |
| 369 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_FLOW_BEGIN) || | 387 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_FLOW_BEGIN) || |
| 370 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_INSTANT)); | 388 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_INSTANT) || |
| 389 trace_analyzer::Query::EventPhaseIs(TRACE_EVENT_PHASE_COMPLETE)); | |
| 371 analyzer->FindEvents(query, events); | 390 analyzer->FindEvents(query, events); |
| 372 } | 391 } |
| 373 | 392 |
| 374 // The key contains the name of the argument and the argument. | 393 // The key contains the name of the argument and the argument. |
| 375 typedef std::pair<std::string, double> EventMapKey; | 394 typedef std::pair<std::string, double> EventMapKey; |
| 376 typedef std::map<EventMapKey, const trace_analyzer::TraceEvent*> EventMap; | 395 typedef std::map<EventMapKey, const trace_analyzer::TraceEvent*> EventMap; |
| 377 | 396 |
| 378 // Make events findable by their arguments, for instance, if an | 397 // Make events findable by their arguments, for instance, if an |
| 379 // event has a "timestamp": 238724 argument, the map will contain | 398 // event has a "timestamp": 238724 argument, the map will contain |
| 380 // pair<"timestamp", 238724> -> &event. All arguments are indexed. | 399 // pair<"timestamp", 238724> -> &event. All arguments are indexed. |
| (...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 547 | 566 |
| 548 ASSERT_EQ(1, | 567 ASSERT_EQ(1, |
| 549 (HasFlag(k24fps) ? 1 : 0) + | 568 (HasFlag(k24fps) ? 1 : 0) + |
| 550 (HasFlag(k30fps) ? 1 : 0) + | 569 (HasFlag(k30fps) ? 1 : 0) + |
| 551 (HasFlag(k60fps) ? 1 : 0)); | 570 (HasFlag(k60fps) ? 1 : 0)); |
| 552 | 571 |
| 553 net::IPEndPoint receiver_end_point = GetFreeLocalPort(); | 572 net::IPEndPoint receiver_end_point = GetFreeLocalPort(); |
| 554 | 573 |
| 555 // Start the in-process receiver that examines audio/video for the expected | 574 // Start the in-process receiver that examines audio/video for the expected |
| 556 // test patterns. | 575 // test patterns. |
| 576 base::TimeDelta delta = base::TimeDelta::FromSeconds(0); | |
| 577 if (HasFlag(kFastClock)) { | |
| 578 delta = base::TimeDelta::FromSeconds(10); | |
| 579 } | |
| 580 if (HasFlag(kSlowClock)) { | |
| 581 delta = base::TimeDelta::FromSeconds(-10); | |
| 582 } | |
| 557 scoped_refptr<media::cast::StandaloneCastEnvironment> cast_environment( | 583 scoped_refptr<media::cast::StandaloneCastEnvironment> cast_environment( |
| 558 new media::cast::StandaloneCastEnvironment); | 584 new media::cast::StandaloneCastEnvironment( |
| 585 make_scoped_ptr<base::TickClock>(new SkewedTickClock(delta)))); | |
| 559 TestPatternReceiver* const receiver = | 586 TestPatternReceiver* const receiver = |
| 560 new TestPatternReceiver(cast_environment, receiver_end_point); | 587 new TestPatternReceiver(cast_environment, receiver_end_point); |
| 561 receiver->Start(); | 588 receiver->Start(); |
| 562 | 589 |
| 563 scoped_ptr<media::cast::test::UDPProxy> udp_proxy; | 590 scoped_ptr<media::cast::test::UDPProxy> udp_proxy; |
| 564 if (HasFlag(kProxyWifi) || HasFlag(kProxyEvil)) { | 591 if (HasFlag(kProxyWifi) || HasFlag(kProxyEvil)) { |
| 565 net::IPEndPoint proxy_end_point = GetFreeLocalPort(); | 592 net::IPEndPoint proxy_end_point = GetFreeLocalPort(); |
| 566 if (HasFlag(kProxyWifi)) { | 593 if (HasFlag(kProxyWifi)) { |
| 567 udp_proxy = media::cast::test::UDPProxy::Create( | 594 udp_proxy = media::cast::test::UDPProxy::Create( |
| 568 proxy_end_point, | 595 proxy_end_point, |
| 569 receiver_end_point, | 596 receiver_end_point, |
| 570 media::cast::test::WifiNetwork().Pass(), | 597 media::cast::test::WifiNetwork().Pass(), |
| 571 media::cast::test::WifiNetwork().Pass(), | 598 media::cast::test::WifiNetwork().Pass(), |
| 572 NULL); | 599 NULL); |
| 573 } else if (HasFlag(kProxyEvil)) { | 600 } else if (HasFlag(kProxyEvil)) { |
| 574 udp_proxy = media::cast::test::UDPProxy::Create( | 601 udp_proxy = media::cast::test::UDPProxy::Create( |
| 575 proxy_end_point, | 602 proxy_end_point, |
| 576 receiver_end_point, | 603 receiver_end_point, |
| 577 media::cast::test::EvilNetwork().Pass(), | 604 media::cast::test::EvilNetwork().Pass(), |
| 578 media::cast::test::EvilNetwork().Pass(), | 605 media::cast::test::EvilNetwork().Pass(), |
| 579 NULL); | 606 NULL); |
| 580 } | 607 } |
| 581 receiver_end_point = proxy_end_point; | 608 receiver_end_point = proxy_end_point; |
| 582 } | 609 } |
| 583 | 610 |
| 584 std::string json_events; | 611 std::string json_events; |
| 585 ASSERT_TRUE(tracing::BeginTracing("test_fps,mirroring,cast_perf_test")); | 612 ASSERT_TRUE(tracing::BeginTracing( |
| 613 "renderer_host,mirroring,cast_perf_test")); | |
| 586 const std::string page_url = base::StringPrintf( | 614 const std::string page_url = base::StringPrintf( |
| 587 "performance%d.html?port=%d", | 615 "performance%d.html?port=%d", |
| 588 getfps(), | 616 getfps(), |
| 589 receiver_end_point.port()); | 617 receiver_end_point.port()); |
| 590 ASSERT_TRUE(RunExtensionSubtest("cast_streaming", page_url)) << message_; | 618 ASSERT_TRUE(RunExtensionSubtest("cast_streaming", page_url)) << message_; |
| 591 ASSERT_TRUE(tracing::EndTracing(&json_events)); | 619 ASSERT_TRUE(tracing::EndTracing(&json_events)); |
| 592 receiver->Stop(); | 620 receiver->Stop(); |
| 593 | 621 |
| 594 // Stop all threads, removes the need for synchronization when analyzing | 622 // Stop all threads, removes the need for synchronization when analyzing |
| 595 // the data. | 623 // the data. |
| 596 cast_environment->Shutdown(); | 624 cast_environment->Shutdown(); |
| 597 scoped_ptr<trace_analyzer::TraceAnalyzer> analyzer; | 625 scoped_ptr<trace_analyzer::TraceAnalyzer> analyzer; |
| 598 analyzer.reset(trace_analyzer::TraceAnalyzer::Create(json_events)); | 626 analyzer.reset(trace_analyzer::TraceAnalyzer::Create(json_events)); |
| 599 analyzer->AssociateAsyncBeginEndEvents(); | 627 analyzer->AssociateAsyncBeginEndEvents(); |
| 600 | 628 |
| 601 // Only one of these PrintResults should actually print something. | 629 // Only one of these PrintResults should actually print something. |
| 602 // The printed result will be the average time between frames in the | 630 // The printed result will be the average time between frames in the |
| 603 // browser window. | 631 // browser window. |
| 604 MeanAndError sw_frame_data = AnalyzeTraceDistance(analyzer.get(), | 632 MeanAndError frame_data = AnalyzeTraceDistance( |
| 605 "TestFrameTickSW"); | 633 analyzer.get(), |
| 606 MeanAndError frame_data = AnalyzeTraceDistance(analyzer.get(), | 634 #ifdef OS_MACOSX |
| 607 "TestFrameTickGPU"); | 635 "RenderWidgetHostImpl::OnCompositorSurfaceBuffersSwapped" |
| 608 if (frame_data.num_values == 0) { | 636 #else |
| 609 frame_data = sw_frame_data; | 637 "RenderWidgetHostImpl::OnSwapCompositorFrame" |
| 610 } | 638 #endif |
|
piman
2014/04/08 22:46:03
This hardcodes the knowledge that "on mac we don't
hubbe
2014/04/08 22:58:29
Now uses a special trace event which is normally O
| |
| 639 ); | |
| 611 EXPECT_GT(frame_data.num_values, 0UL); | 640 EXPECT_GT(frame_data.num_values, 0UL); |
| 612 // Lower is better. | 641 // Lower is better. |
| 613 frame_data.Print(test_name, | 642 frame_data.Print(test_name, |
| 614 GetSuffixForTestFlags(), | 643 GetSuffixForTestFlags(), |
| 615 "time_between_frames", | 644 "time_between_frames", |
| 616 "ms"); | 645 "ms"); |
| 617 | 646 |
| 618 // This prints out the average time between capture events. | 647 // This prints out the average time between capture events. |
| 619 // As the capture frame rate is capped at 30fps, this score | 648 // As the capture frame rate is capped at 30fps, this score |
| 620 // cannot get any better than (lower) 33.33 ms. | 649 // cannot get any better than (lower) 33.33 ms. |
| (...skipping 20 matching lines...) Expand all Loading... | |
| 641 // (it's a prefix for the generated test cases) | 670 // (it's a prefix for the generated test cases) |
| 642 INSTANTIATE_TEST_CASE_P( | 671 INSTANTIATE_TEST_CASE_P( |
| 643 , | 672 , |
| 644 CastV2PerformanceTest, | 673 CastV2PerformanceTest, |
| 645 testing::Values( | 674 testing::Values( |
| 646 kUseGpu | k24fps, | 675 kUseGpu | k24fps, |
| 647 kUseGpu | k30fps, | 676 kUseGpu | k30fps, |
| 648 kUseGpu | k60fps, | 677 kUseGpu | k60fps, |
| 649 kUseGpu | k24fps | kDisableVsync, | 678 kUseGpu | k24fps | kDisableVsync, |
| 650 kUseGpu | k30fps | kProxyWifi, | 679 kUseGpu | k30fps | kProxyWifi, |
| 651 kUseGpu | k30fps | kProxyEvil)); | 680 kUseGpu | k30fps | kProxyEvil, |
| 681 kUseGpu | k30fps | kSlowClock, | |
| 682 kUseGpu | k30fps | kFastClock)); | |
| OLD | NEW |