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 #include "cc/scheduler/scheduler.h" | 4 #include "cc/scheduler/scheduler.h" |
5 | 5 |
6 #include <string> | 6 #include <string> |
7 #include <vector> | 7 #include <vector> |
8 | 8 |
9 #include "base/debug/trace_event.h" | 9 #include "base/debug/trace_event.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
11 #include "base/memory/scoped_vector.h" | 11 #include "base/memory/scoped_vector.h" |
12 #include "base/message_loop/message_loop.h" | 12 #include "base/message_loop/message_loop.h" |
| 13 #include "base/power_monitor/power_monitor.h" |
| 14 #include "base/power_monitor/power_monitor_source.h" |
13 #include "base/run_loop.h" | 15 #include "base/run_loop.h" |
14 #include "base/time/time.h" | 16 #include "base/time/time.h" |
15 #include "cc/test/begin_frame_args_test.h" | 17 #include "cc/test/begin_frame_args_test.h" |
16 #include "cc/test/ordered_simple_task_runner.h" | 18 #include "cc/test/ordered_simple_task_runner.h" |
17 #include "cc/test/scheduler_test_common.h" | 19 #include "cc/test/scheduler_test_common.h" |
18 #include "testing/gmock/include/gmock/gmock.h" | 20 #include "testing/gmock/include/gmock/gmock.h" |
19 #include "testing/gtest/include/gtest/gtest.h" | 21 #include "testing/gtest/include/gtest/gtest.h" |
20 | 22 |
21 #define EXPECT_ACTION(action, client, action_index, expected_num_actions) \ | 23 #define EXPECT_ACTION(action, client, action_index, expected_num_actions) \ |
22 do { \ | 24 do { \ |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
56 virtual void OnNeedsBeginFramesChange(bool needs_begin_frames) override { | 58 virtual void OnNeedsBeginFramesChange(bool needs_begin_frames) override { |
57 if (needs_begin_frames) { | 59 if (needs_begin_frames) { |
58 client_->actions_.push_back("SetNeedsBeginFrames(true)"); | 60 client_->actions_.push_back("SetNeedsBeginFrames(true)"); |
59 } else { | 61 } else { |
60 client_->actions_.push_back("SetNeedsBeginFrames(false)"); | 62 client_->actions_.push_back("SetNeedsBeginFrames(false)"); |
61 } | 63 } |
62 client_->states_.push_back(client_->scheduler_->AsValue()); | 64 client_->states_.push_back(client_->scheduler_->AsValue()); |
63 } | 65 } |
64 }; | 66 }; |
65 | 67 |
| 68 class FakePowerMonitorSource : public base::PowerMonitorSource { |
| 69 public: |
| 70 FakePowerMonitorSource() {} |
| 71 virtual ~FakePowerMonitorSource() {} |
| 72 void GeneratePowerStateEvent(bool on_battery_power) { |
| 73 on_battery_power_impl_ = on_battery_power; |
| 74 ProcessPowerEvent(POWER_STATE_EVENT); |
| 75 base::MessageLoop::current()->RunUntilIdle(); |
| 76 } |
| 77 virtual bool IsOnBatteryPowerImpl() override { |
| 78 return on_battery_power_impl_; |
| 79 } |
| 80 |
| 81 private: |
| 82 bool on_battery_power_impl_; |
| 83 }; |
| 84 |
66 FakeSchedulerClient() | 85 FakeSchedulerClient() |
67 : automatic_swap_ack_(true), | 86 : automatic_swap_ack_(true), |
68 swap_contains_incomplete_tile_(false), | 87 swap_contains_incomplete_tile_(false), |
69 redraw_will_happen_if_update_visible_tiles_happens_(false), | 88 redraw_will_happen_if_update_visible_tiles_happens_(false), |
70 now_src_(TestNowSource::Create()), | 89 now_src_(TestNowSource::Create()), |
71 fake_frame_source_(this) { | 90 fake_frame_source_(this), |
| 91 fake_power_monitor_source_(new FakePowerMonitorSource), |
| 92 power_monitor_(make_scoped_ptr<base::PowerMonitorSource>( |
| 93 fake_power_monitor_source_)) { |
72 Reset(); | 94 Reset(); |
73 } | 95 } |
74 | 96 |
75 void Reset() { | 97 void Reset() { |
76 actions_.clear(); | 98 actions_.clear(); |
77 states_.clear(); | 99 states_.clear(); |
78 draw_will_happen_ = true; | 100 draw_will_happen_ = true; |
79 swap_will_happen_if_draw_happens_ = true; | 101 swap_will_happen_if_draw_happens_ = true; |
80 num_draws_ = 0; | 102 num_draws_ = 0; |
81 log_anticipated_draw_time_change_ = false; | 103 log_anticipated_draw_time_change_ = false; |
(...skipping 22 matching lines...) Expand all Loading... |
104 } | 126 } |
105 | 127 |
106 bool ExternalBeginFrame() { | 128 bool ExternalBeginFrame() { |
107 return scheduler_->settings().begin_frame_scheduling_enabled && | 129 return scheduler_->settings().begin_frame_scheduling_enabled && |
108 scheduler_->settings().throttle_frame_production; | 130 scheduler_->settings().throttle_frame_production; |
109 } | 131 } |
110 virtual FakeBeginFrameSource* ExternalBeginFrameSource() override { | 132 virtual FakeBeginFrameSource* ExternalBeginFrameSource() override { |
111 return &fake_frame_source_; | 133 return &fake_frame_source_; |
112 } | 134 } |
113 | 135 |
| 136 virtual base::PowerMonitor* PowerMonitor() override { |
| 137 return &power_monitor_; |
| 138 } |
| 139 |
| 140 FakePowerMonitorSource* PowerMonitorSource() { |
| 141 return fake_power_monitor_source_; |
| 142 } |
| 143 |
114 void AdvanceFrame() { | 144 void AdvanceFrame() { |
115 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("cc.debug.scheduler.frames"), | 145 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("cc.debug.scheduler.frames"), |
116 "FakeSchedulerClient::AdvanceFrame"); | 146 "FakeSchedulerClient::AdvanceFrame"); |
117 // EXPECT_TRUE(needs_begin_frames()); | 147 // EXPECT_TRUE(needs_begin_frames()); |
118 if (ExternalBeginFrame()) { | 148 if (ExternalBeginFrame()) { |
119 // Creep the time forward so that any BeginFrameArgs is not equal to the | 149 // Creep the time forward so that any BeginFrameArgs is not equal to the |
120 // last one otherwise we violate the BeginFrameSource contract. | 150 // last one otherwise we violate the BeginFrameSource contract. |
121 now_src_->AdvanceNowMicroseconds(1); | 151 now_src_->AdvanceNowMicroseconds(1); |
122 fake_frame_source_.TestOnBeginFrame( | 152 fake_frame_source_.TestOnBeginFrame( |
123 CreateBeginFrameArgsForTesting(now_src_)); | 153 CreateBeginFrameArgsForTesting(now_src_)); |
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
250 bool draw_will_happen_; | 280 bool draw_will_happen_; |
251 bool swap_will_happen_if_draw_happens_; | 281 bool swap_will_happen_if_draw_happens_; |
252 bool automatic_swap_ack_; | 282 bool automatic_swap_ack_; |
253 int num_draws_; | 283 int num_draws_; |
254 bool log_anticipated_draw_time_change_; | 284 bool log_anticipated_draw_time_change_; |
255 bool swap_contains_incomplete_tile_; | 285 bool swap_contains_incomplete_tile_; |
256 bool redraw_will_happen_if_update_visible_tiles_happens_; | 286 bool redraw_will_happen_if_update_visible_tiles_happens_; |
257 base::TimeTicks posted_begin_impl_frame_deadline_; | 287 base::TimeTicks posted_begin_impl_frame_deadline_; |
258 std::vector<const char*> actions_; | 288 std::vector<const char*> actions_; |
259 std::vector<scoped_refptr<base::debug::ConvertableToTraceFormat> > states_; | 289 std::vector<scoped_refptr<base::debug::ConvertableToTraceFormat> > states_; |
260 scoped_ptr<TestScheduler> scheduler_; | |
261 scoped_refptr<TestNowSource> now_src_; | 290 scoped_refptr<TestNowSource> now_src_; |
262 FakeBeginFrameSourceForFakeSchedulerClient fake_frame_source_; | 291 FakeBeginFrameSourceForFakeSchedulerClient fake_frame_source_; |
| 292 FakePowerMonitorSource* fake_power_monitor_source_; |
| 293 base::PowerMonitor power_monitor_; |
| 294 scoped_ptr<TestScheduler> scheduler_; |
263 }; | 295 }; |
264 | 296 |
265 void InitializeOutputSurfaceAndFirstCommit(Scheduler* scheduler, | 297 void InitializeOutputSurfaceAndFirstCommit(Scheduler* scheduler, |
266 FakeSchedulerClient* client) { | 298 FakeSchedulerClient* client) { |
267 TRACE_EVENT0("cc", | 299 TRACE_EVENT0("cc", |
268 "SchedulerUnitTest::InitializeOutputSurfaceAndFirstCommit"); | 300 "SchedulerUnitTest::InitializeOutputSurfaceAndFirstCommit"); |
269 | 301 |
270 scheduler->DidCreateAndInitializeOutputSurface(); | 302 scheduler->DidCreateAndInitializeOutputSurface(); |
271 scheduler->SetNeedsCommit(); | 303 scheduler->SetNeedsCommit(); |
272 scheduler->NotifyBeginMainFrameStarted(); | 304 scheduler->NotifyBeginMainFrameStarted(); |
(...skipping 1689 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1962 scheduler->NotifyReadyToCommit(); | 1994 scheduler->NotifyReadyToCommit(); |
1963 EXPECT_SINGLE_ACTION("ScheduledActionCommit", client); | 1995 EXPECT_SINGLE_ACTION("ScheduledActionCommit", client); |
1964 | 1996 |
1965 client.Reset(); | 1997 client.Reset(); |
1966 scheduler->SetVisible(false); | 1998 scheduler->SetVisible(false); |
1967 // Sync tree should be forced to activate. | 1999 // Sync tree should be forced to activate. |
1968 EXPECT_ACTION("SetNeedsBeginFrames(false)", client, 0, 2); | 2000 EXPECT_ACTION("SetNeedsBeginFrames(false)", client, 0, 2); |
1969 EXPECT_ACTION("ScheduledActionActivateSyncTree", client, 1, 2); | 2001 EXPECT_ACTION("ScheduledActionActivateSyncTree", client, 1, 2); |
1970 } | 2002 } |
1971 | 2003 |
| 2004 TEST(SchedulerTest, SchedulerPowerMonitoring) { |
| 2005 FakeSchedulerClient client; |
| 2006 SchedulerSettings settings; |
| 2007 settings.prioritize_impl_latency_on_battery = true; |
| 2008 TestScheduler* scheduler = client.CreateScheduler(settings); |
| 2009 |
| 2010 base::TimeTicks before_deadline, after_deadline; |
| 2011 |
| 2012 scheduler->SetCanStart(); |
| 2013 scheduler->SetVisible(true); |
| 2014 scheduler->SetCanDraw(true); |
| 2015 |
| 2016 InitializeOutputSurfaceAndFirstCommit(scheduler, &client); |
| 2017 |
| 2018 scheduler->SetNeedsCommit(); |
| 2019 scheduler->SetNeedsRedraw(); |
| 2020 client.Reset(); |
| 2021 |
| 2022 // On non-battery power |
| 2023 EXPECT_FALSE(client.PowerMonitor()->IsOnBatteryPower()); |
| 2024 |
| 2025 client.AdvanceFrame(); |
| 2026 client.Reset(); |
| 2027 |
| 2028 before_deadline = client.now_src()->Now(); |
| 2029 EXPECT_TRUE(client.task_runner().RunTasksWhile( |
| 2030 client.ImplFrameDeadlinePending(true))); |
| 2031 after_deadline = client.now_src()->Now(); |
| 2032 |
| 2033 // We post a non-zero deadline task when not on battery |
| 2034 EXPECT_LT(before_deadline, after_deadline); |
| 2035 |
| 2036 // Switch to battery power |
| 2037 client.PowerMonitorSource()->GeneratePowerStateEvent(true); |
| 2038 EXPECT_TRUE(client.PowerMonitor()->IsOnBatteryPower()); |
| 2039 |
| 2040 client.AdvanceFrame(); |
| 2041 scheduler->SetNeedsCommit(); |
| 2042 scheduler->SetNeedsRedraw(); |
| 2043 client.Reset(); |
| 2044 |
| 2045 before_deadline = client.now_src()->Now(); |
| 2046 EXPECT_TRUE(client.task_runner().RunTasksWhile( |
| 2047 client.ImplFrameDeadlinePending(true))); |
| 2048 after_deadline = client.now_src()->Now(); |
| 2049 |
| 2050 // We post a zero deadline task when on battery |
| 2051 EXPECT_EQ(before_deadline, after_deadline); |
| 2052 |
| 2053 // Switch to non-battery power |
| 2054 client.PowerMonitorSource()->GeneratePowerStateEvent(false); |
| 2055 EXPECT_FALSE(client.PowerMonitor()->IsOnBatteryPower()); |
| 2056 |
| 2057 client.AdvanceFrame(); |
| 2058 scheduler->SetNeedsCommit(); |
| 2059 scheduler->SetNeedsRedraw(); |
| 2060 client.Reset(); |
| 2061 |
| 2062 // Same as before |
| 2063 before_deadline = client.now_src()->Now(); |
| 2064 EXPECT_TRUE(client.task_runner().RunTasksWhile( |
| 2065 client.ImplFrameDeadlinePending(true))); |
| 2066 after_deadline = client.now_src()->Now(); |
| 2067 } |
| 2068 |
| 2069 TEST(SchedulerTest, |
| 2070 SimulateWindowsLowResolutionTimerOnBattery_PrioritizeImplLatencyOff) { |
| 2071 FakeSchedulerClient client; |
| 2072 SchedulerSettings settings; |
| 2073 TestScheduler* scheduler = client.CreateScheduler(settings); |
| 2074 |
| 2075 scheduler->SetCanStart(); |
| 2076 scheduler->SetVisible(true); |
| 2077 scheduler->SetCanDraw(true); |
| 2078 |
| 2079 InitializeOutputSurfaceAndFirstCommit(scheduler, &client); |
| 2080 |
| 2081 // Set needs commit so that the scheduler tries to wait for the main thread |
| 2082 scheduler->SetNeedsCommit(); |
| 2083 // Set needs redraw so that the scheduler doesn't wait too long |
| 2084 scheduler->SetNeedsRedraw(); |
| 2085 client.Reset(); |
| 2086 |
| 2087 // Switch to battery power |
| 2088 client.PowerMonitorSource()->GeneratePowerStateEvent(true); |
| 2089 EXPECT_TRUE(client.PowerMonitor()->IsOnBatteryPower()); |
| 2090 |
| 2091 client.AdvanceFrame(); |
| 2092 scheduler->SetNeedsCommit(); |
| 2093 scheduler->SetNeedsRedraw(); |
| 2094 client.Reset(); |
| 2095 |
| 2096 // Disable auto-advancing of now_src |
| 2097 client.task_runner().SetAutoAdvanceNowToPendingTasks(false); |
| 2098 |
| 2099 // Deadline task is pending |
| 2100 EXPECT_TRUE(scheduler->BeginImplFrameDeadlinePending()); |
| 2101 client.task_runner().RunPendingTasks(); |
| 2102 // Deadline task is still pending |
| 2103 EXPECT_TRUE(scheduler->BeginImplFrameDeadlinePending()); |
| 2104 |
| 2105 // Advance now by 15 ms - same as windows low res timer |
| 2106 client.now_src()->AdvanceNowMicroseconds(15000); |
| 2107 EXPECT_TRUE(scheduler->BeginImplFrameDeadlinePending()); |
| 2108 client.task_runner().RunPendingTasks(); |
| 2109 // Deadline task finally completes |
| 2110 EXPECT_FALSE(scheduler->BeginImplFrameDeadlinePending()); |
| 2111 } |
| 2112 |
| 2113 TEST(SchedulerTest, |
| 2114 SimulateWindowsLowResolutionTimerOnBattery_PrioritizeImplLatencyOn) { |
| 2115 FakeSchedulerClient client; |
| 2116 SchedulerSettings settings; |
| 2117 settings.prioritize_impl_latency_on_battery = true; |
| 2118 TestScheduler* scheduler = client.CreateScheduler(settings); |
| 2119 |
| 2120 scheduler->SetCanStart(); |
| 2121 scheduler->SetVisible(true); |
| 2122 scheduler->SetCanDraw(true); |
| 2123 |
| 2124 InitializeOutputSurfaceAndFirstCommit(scheduler, &client); |
| 2125 |
| 2126 // Set needs commit so that the scheduler tries to wait for the main thread |
| 2127 scheduler->SetNeedsCommit(); |
| 2128 // Set needs redraw so that the scheduler doesn't wait too long |
| 2129 scheduler->SetNeedsRedraw(); |
| 2130 client.Reset(); |
| 2131 |
| 2132 // Switch to battery power |
| 2133 client.PowerMonitorSource()->GeneratePowerStateEvent(true); |
| 2134 EXPECT_TRUE(client.PowerMonitor()->IsOnBatteryPower()); |
| 2135 |
| 2136 client.AdvanceFrame(); |
| 2137 scheduler->SetNeedsCommit(); |
| 2138 scheduler->SetNeedsRedraw(); |
| 2139 client.Reset(); |
| 2140 |
| 2141 // Disable auto-advancing of now_src |
| 2142 client.task_runner().SetAutoAdvanceNowToPendingTasks(false); |
| 2143 |
| 2144 // Deadline task is pending |
| 2145 EXPECT_TRUE(scheduler->BeginImplFrameDeadlinePending()); |
| 2146 client.task_runner().RunPendingTasks(); |
| 2147 // Deadline task runs immediately |
| 2148 EXPECT_FALSE(scheduler->BeginImplFrameDeadlinePending()); |
| 2149 } |
| 2150 |
1972 } // namespace | 2151 } // namespace |
1973 } // namespace cc | 2152 } // namespace cc |
OLD | NEW |