| OLD | NEW |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 "content/browser/memory/memory_coordinator_impl.h" | 5 #include "content/browser/memory/memory_coordinator_impl.h" |
| 6 | 6 |
| 7 #include "base/memory/memory_coordinator_proxy.h" | 7 #include "base/memory/memory_coordinator_proxy.h" |
| 8 #include "base/run_loop.h" | 8 #include "base/run_loop.h" |
| 9 #include "base/test/scoped_feature_list.h" | 9 #include "base/test/scoped_feature_list.h" |
| 10 #include "base/test/test_mock_time_task_runner.h" | 10 #include "base/test/test_mock_time_task_runner.h" |
| 11 #include "content/browser/memory/memory_monitor.h" | 11 #include "content/browser/memory/memory_monitor.h" |
| 12 #include "content/browser/memory/memory_state_updater.h" |
| 12 #include "content/public/common/content_features.h" | 13 #include "content/public/common/content_features.h" |
| 13 #include "testing/gtest/include/gtest/gtest.h" | 14 #include "testing/gtest/include/gtest/gtest.h" |
| 14 | 15 |
| 15 namespace content { | 16 namespace content { |
| 16 | 17 |
| 17 namespace { | 18 namespace { |
| 18 | 19 |
| 19 class MockMemoryCoordinatorClient : public base::MemoryCoordinatorClient { | 20 class MockMemoryCoordinatorClient : public base::MemoryCoordinatorClient { |
| 20 public: | 21 public: |
| 21 void OnMemoryStateChange(base::MemoryState state) override { | 22 void OnMemoryStateChange(base::MemoryState state) override { |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 75 } | 76 } |
| 76 | 77 |
| 77 protected: | 78 protected: |
| 78 std::unique_ptr<MemoryCoordinatorImpl> coordinator_; | 79 std::unique_ptr<MemoryCoordinatorImpl> coordinator_; |
| 79 scoped_refptr<base::TestMockTimeTaskRunner> task_runner_; | 80 scoped_refptr<base::TestMockTimeTaskRunner> task_runner_; |
| 80 base::MessageLoop message_loop_; | 81 base::MessageLoop message_loop_; |
| 81 base::test::ScopedFeatureList scoped_feature_list_; | 82 base::test::ScopedFeatureList scoped_feature_list_; |
| 82 }; | 83 }; |
| 83 | 84 |
| 84 TEST_F(MemoryCoordinatorImplTest, CalculateNextState) { | 85 TEST_F(MemoryCoordinatorImplTest, CalculateNextState) { |
| 85 coordinator_->expected_renderer_size_ = 10; | 86 auto* state_updater = coordinator_->state_updater_.get(); |
| 86 coordinator_->new_renderers_until_throttled_ = 4; | 87 state_updater->expected_renderer_size_ = 10; |
| 87 coordinator_->new_renderers_until_suspended_ = 2; | 88 state_updater->new_renderers_until_throttled_ = 4; |
| 88 coordinator_->new_renderers_back_to_normal_ = 5; | 89 state_updater->new_renderers_until_suspended_ = 2; |
| 89 coordinator_->new_renderers_back_to_throttled_ = 3; | 90 state_updater->new_renderers_back_to_normal_ = 5; |
| 90 DCHECK(coordinator_->ValidateParameters()); | 91 state_updater->new_renderers_back_to_throttled_ = 3; |
| 92 DCHECK(state_updater->ValidateParameters()); |
| 91 | 93 |
| 92 // The default state is NORMAL. | 94 // The default state is NORMAL. |
| 93 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetCurrentMemoryState()); | 95 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetCurrentMemoryState()); |
| 94 EXPECT_EQ(base::MemoryState::NORMAL, | 96 EXPECT_EQ(base::MemoryState::NORMAL, |
| 95 base::MemoryCoordinatorProxy::GetInstance()-> | 97 base::MemoryCoordinatorProxy::GetInstance()-> |
| 96 GetCurrentMemoryState()); | 98 GetCurrentMemoryState()); |
| 97 | 99 |
| 98 // Transitions from NORMAL | 100 // Transitions from NORMAL |
| 99 coordinator_->current_state_ = base::MemoryState::NORMAL; | 101 coordinator_->current_state_ = base::MemoryState::NORMAL; |
| 100 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetCurrentMemoryState()); | 102 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetCurrentMemoryState()); |
| 101 EXPECT_EQ(base::MemoryState::NORMAL, | 103 EXPECT_EQ(base::MemoryState::NORMAL, |
| 102 base::MemoryCoordinatorProxy::GetInstance()-> | 104 base::MemoryCoordinatorProxy::GetInstance()-> |
| 103 GetCurrentMemoryState()); | 105 GetCurrentMemoryState()); |
| 104 | 106 |
| 105 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); | 107 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); |
| 106 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->CalculateNextState()); | 108 EXPECT_EQ(base::MemoryState::NORMAL, state_updater->CalculateNextState()); |
| 107 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); | 109 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); |
| 108 EXPECT_EQ(base::MemoryState::THROTTLED, coordinator_->CalculateNextState()); | 110 EXPECT_EQ(base::MemoryState::THROTTLED, state_updater->CalculateNextState()); |
| 109 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(20); | 111 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(20); |
| 110 EXPECT_EQ(base::MemoryState::SUSPENDED, coordinator_->CalculateNextState()); | 112 EXPECT_EQ(base::MemoryState::SUSPENDED, state_updater->CalculateNextState()); |
| 111 | 113 |
| 112 // Transitions from THROTTLED | 114 // Transitions from THROTTLED |
| 113 coordinator_->current_state_ = base::MemoryState::THROTTLED; | 115 coordinator_->current_state_ = base::MemoryState::THROTTLED; |
| 114 EXPECT_EQ(base::MemoryState::THROTTLED, | 116 EXPECT_EQ(base::MemoryState::THROTTLED, |
| 115 coordinator_->GetCurrentMemoryState()); | 117 coordinator_->GetCurrentMemoryState()); |
| 116 EXPECT_EQ(base::MemoryState::THROTTLED, | 118 EXPECT_EQ(base::MemoryState::THROTTLED, |
| 117 base::MemoryCoordinatorProxy::GetInstance()-> | 119 base::MemoryCoordinatorProxy::GetInstance()-> |
| 118 GetCurrentMemoryState()); | 120 GetCurrentMemoryState()); |
| 119 | 121 |
| 120 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); | 122 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); |
| 121 EXPECT_EQ(base::MemoryState::THROTTLED, coordinator_->CalculateNextState()); | 123 EXPECT_EQ(base::MemoryState::THROTTLED, state_updater->CalculateNextState()); |
| 122 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); | 124 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); |
| 123 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->CalculateNextState()); | 125 EXPECT_EQ(base::MemoryState::NORMAL, state_updater->CalculateNextState()); |
| 124 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(20); | 126 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(20); |
| 125 EXPECT_EQ(base::MemoryState::SUSPENDED, coordinator_->CalculateNextState()); | 127 EXPECT_EQ(base::MemoryState::SUSPENDED, state_updater->CalculateNextState()); |
| 126 | 128 |
| 127 // Transitions from SUSPENDED | 129 // Transitions from SUSPENDED |
| 128 coordinator_->current_state_ = base::MemoryState::SUSPENDED; | 130 coordinator_->current_state_ = base::MemoryState::SUSPENDED; |
| 129 // GetCurrentMemoryState() returns THROTTLED state for the browser process | 131 // GetCurrentMemoryState() returns THROTTLED state for the browser process |
| 130 // when the global state is SUSPENDED. | 132 // when the global state is SUSPENDED. |
| 131 EXPECT_EQ(base::MemoryState::THROTTLED, | 133 EXPECT_EQ(base::MemoryState::THROTTLED, |
| 132 coordinator_->GetCurrentMemoryState()); | 134 coordinator_->GetCurrentMemoryState()); |
| 133 EXPECT_EQ(base::MemoryState::THROTTLED, | 135 EXPECT_EQ(base::MemoryState::THROTTLED, |
| 134 base::MemoryCoordinatorProxy::GetInstance()-> | 136 base::MemoryCoordinatorProxy::GetInstance()-> |
| 135 GetCurrentMemoryState()); | 137 GetCurrentMemoryState()); |
| 136 | 138 |
| 137 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(20); | 139 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(20); |
| 138 EXPECT_EQ(base::MemoryState::SUSPENDED, coordinator_->CalculateNextState()); | 140 EXPECT_EQ(base::MemoryState::SUSPENDED, state_updater->CalculateNextState()); |
| 139 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(30); | 141 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(30); |
| 140 EXPECT_EQ(base::MemoryState::THROTTLED, coordinator_->CalculateNextState()); | 142 EXPECT_EQ(base::MemoryState::THROTTLED, state_updater->CalculateNextState()); |
| 141 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); | 143 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); |
| 142 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->CalculateNextState()); | 144 EXPECT_EQ(base::MemoryState::NORMAL, state_updater->CalculateNextState()); |
| 143 } | 145 } |
| 144 | 146 |
| 145 TEST_F(MemoryCoordinatorImplTest, UpdateState) { | 147 TEST_F(MemoryCoordinatorImplTest, UpdateState) { |
| 146 coordinator_->expected_renderer_size_ = 10; | 148 auto* state_updater = coordinator_->state_updater_.get(); |
| 147 coordinator_->new_renderers_until_throttled_ = 4; | 149 state_updater->expected_renderer_size_ = 10; |
| 148 coordinator_->new_renderers_until_suspended_ = 2; | 150 state_updater->new_renderers_until_throttled_ = 4; |
| 149 coordinator_->new_renderers_back_to_normal_ = 5; | 151 state_updater->new_renderers_until_suspended_ = 2; |
| 150 coordinator_->new_renderers_back_to_throttled_ = 3; | 152 state_updater->new_renderers_back_to_normal_ = 5; |
| 151 DCHECK(coordinator_->ValidateParameters()); | 153 state_updater->new_renderers_back_to_throttled_ = 3; |
| 154 DCHECK(state_updater->ValidateParameters()); |
| 152 | 155 |
| 153 { | 156 { |
| 154 // Transition happens (NORMAL -> THROTTLED). | 157 // Transition happens (NORMAL -> THROTTLED). |
| 155 MockMemoryCoordinatorClient client; | 158 MockMemoryCoordinatorClient client; |
| 156 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(&client); | 159 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(&client); |
| 157 coordinator_->current_state_ = base::MemoryState::NORMAL; | 160 coordinator_->current_state_ = base::MemoryState::NORMAL; |
| 158 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); | 161 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); |
| 159 coordinator_->UpdateState(); | 162 state_updater->UpdateState(); |
| 160 base::RunLoop loop; | 163 base::RunLoop loop; |
| 161 loop.RunUntilIdle(); | 164 loop.RunUntilIdle(); |
| 162 EXPECT_TRUE(client.is_called()); | 165 EXPECT_TRUE(client.is_called()); |
| 163 EXPECT_EQ(base::MemoryState::THROTTLED, client.state()); | 166 EXPECT_EQ(base::MemoryState::THROTTLED, client.state()); |
| 164 base::MemoryCoordinatorClientRegistry::GetInstance()->Unregister(&client); | 167 base::MemoryCoordinatorClientRegistry::GetInstance()->Unregister(&client); |
| 165 } | 168 } |
| 166 | 169 |
| 167 { | 170 { |
| 168 // No transtion (NORMAL -> NORMAL). OnStateChange shouldn't be called. | 171 // No transtion (NORMAL -> NORMAL). OnStateChange shouldn't be called. |
| 169 MockMemoryCoordinatorClient client; | 172 MockMemoryCoordinatorClient client; |
| 170 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(&client); | 173 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(&client); |
| 171 coordinator_->current_state_ = base::MemoryState::NORMAL; | 174 coordinator_->current_state_ = base::MemoryState::NORMAL; |
| 172 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); | 175 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); |
| 173 coordinator_->UpdateState(); | 176 state_updater->UpdateState(); |
| 174 base::RunLoop loop; | 177 base::RunLoop loop; |
| 175 loop.RunUntilIdle(); | 178 loop.RunUntilIdle(); |
| 176 EXPECT_FALSE(client.is_called()); | 179 EXPECT_FALSE(client.is_called()); |
| 177 EXPECT_EQ(base::MemoryState::NORMAL, client.state()); | 180 EXPECT_EQ(base::MemoryState::NORMAL, client.state()); |
| 178 base::MemoryCoordinatorClientRegistry::GetInstance()->Unregister(&client); | 181 base::MemoryCoordinatorClientRegistry::GetInstance()->Unregister(&client); |
| 179 } | 182 } |
| 180 } | 183 } |
| 181 | 184 |
| 182 TEST_F(MemoryCoordinatorImplTest, SetMemoryStateForTesting) { | 185 TEST_F(MemoryCoordinatorImplTest, SetMemoryStateForTesting) { |
| 183 coordinator_->expected_renderer_size_ = 10; | 186 auto* state_updater = coordinator_->state_updater_.get(); |
| 184 coordinator_->new_renderers_until_throttled_ = 4; | 187 state_updater->expected_renderer_size_ = 10; |
| 185 coordinator_->new_renderers_until_suspended_ = 2; | 188 state_updater->new_renderers_until_throttled_ = 4; |
| 186 coordinator_->new_renderers_back_to_normal_ = 5; | 189 state_updater->new_renderers_until_suspended_ = 2; |
| 187 coordinator_->new_renderers_back_to_throttled_ = 3; | 190 state_updater->new_renderers_back_to_normal_ = 5; |
| 188 DCHECK(coordinator_->ValidateParameters()); | 191 state_updater->new_renderers_back_to_throttled_ = 3; |
| 192 DCHECK(state_updater->ValidateParameters()); |
| 189 | 193 |
| 190 MockMemoryCoordinatorClient client; | 194 MockMemoryCoordinatorClient client; |
| 191 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(&client); | 195 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(&client); |
| 192 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetCurrentMemoryState()); | 196 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetCurrentMemoryState()); |
| 193 EXPECT_EQ(base::MemoryState::NORMAL, | 197 EXPECT_EQ(base::MemoryState::NORMAL, |
| 194 base::MemoryCoordinatorProxy::GetInstance()-> | 198 base::MemoryCoordinatorProxy::GetInstance()-> |
| 195 GetCurrentMemoryState()); | 199 GetCurrentMemoryState()); |
| 196 EXPECT_EQ(base::MemoryState::NORMAL, client.state()); | 200 EXPECT_EQ(base::MemoryState::NORMAL, client.state()); |
| 197 | 201 |
| 198 base::MemoryCoordinatorProxy::GetInstance()->SetCurrentMemoryStateForTesting( | 202 base::MemoryCoordinatorProxy::GetInstance()->SetCurrentMemoryStateForTesting( |
| (...skipping 14 matching lines...) Expand all Loading... |
| 213 base::MemoryCoordinatorProxy::GetInstance()-> | 217 base::MemoryCoordinatorProxy::GetInstance()-> |
| 214 GetCurrentMemoryState()); | 218 GetCurrentMemoryState()); |
| 215 base::RunLoop loop; | 219 base::RunLoop loop; |
| 216 loop.RunUntilIdle(); | 220 loop.RunUntilIdle(); |
| 217 EXPECT_TRUE(client.is_called()); | 221 EXPECT_TRUE(client.is_called()); |
| 218 EXPECT_EQ(base::MemoryState::THROTTLED, client.state()); | 222 EXPECT_EQ(base::MemoryState::THROTTLED, client.state()); |
| 219 base::MemoryCoordinatorClientRegistry::GetInstance()->Unregister(&client); | 223 base::MemoryCoordinatorClientRegistry::GetInstance()->Unregister(&client); |
| 220 } | 224 } |
| 221 | 225 |
| 222 TEST_F(MemoryCoordinatorImplTest, ForceSetGlobalState) { | 226 TEST_F(MemoryCoordinatorImplTest, ForceSetGlobalState) { |
| 223 coordinator_->expected_renderer_size_ = 10; | 227 auto* state_updater = coordinator_->state_updater_.get(); |
| 224 coordinator_->new_renderers_until_throttled_ = 4; | 228 state_updater->expected_renderer_size_ = 10; |
| 225 coordinator_->new_renderers_until_suspended_ = 2; | 229 state_updater->new_renderers_until_throttled_ = 4; |
| 226 coordinator_->new_renderers_back_to_normal_ = 5; | 230 state_updater->new_renderers_until_suspended_ = 2; |
| 227 coordinator_->new_renderers_back_to_throttled_ = 3; | 231 state_updater->new_renderers_back_to_normal_ = 5; |
| 228 DCHECK(coordinator_->ValidateParameters()); | 232 state_updater->new_renderers_back_to_throttled_ = 3; |
| 233 DCHECK(state_updater->ValidateParameters()); |
| 229 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); | 234 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(50); |
| 230 | 235 |
| 231 base::TimeDelta interval = base::TimeDelta::FromSeconds(5); | 236 base::TimeDelta interval = base::TimeDelta::FromSeconds(5); |
| 232 base::TimeDelta minimum_transition = base::TimeDelta::FromSeconds(30); | 237 base::TimeDelta minimum_transition = base::TimeDelta::FromSeconds(30); |
| 233 coordinator_->monitoring_interval_ = interval; | 238 state_updater->monitoring_interval_ = interval; |
| 234 coordinator_->minimum_transition_period_ = minimum_transition; | 239 state_updater->minimum_transition_period_ = minimum_transition; |
| 235 | 240 |
| 236 // Starts updating states. The initial state should be NORMAL with above | 241 // Starts updating states. The initial state should be NORMAL with above |
| 237 // configuration. | 242 // configuration. |
| 238 coordinator_->Start(); | 243 coordinator_->Start(); |
| 239 task_runner_->RunUntilIdle(); | 244 task_runner_->RunUntilIdle(); |
| 240 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetGlobalMemoryState()); | 245 EXPECT_EQ(base::MemoryState::NORMAL, coordinator_->GetGlobalMemoryState()); |
| 241 | 246 |
| 242 base::TimeDelta force_set_duration = interval * 3; | 247 base::TimeDelta force_set_duration = interval * 3; |
| 243 coordinator_->ForceSetGlobalState(base::MemoryState::SUSPENDED, | 248 coordinator_->ForceSetGlobalState(base::MemoryState::SUSPENDED, |
| 244 force_set_duration); | 249 force_set_duration); |
| (...skipping 13 matching lines...) Expand all Loading... |
| 258 // Also make sure that the state is updated based on free avaiable memory. | 263 // Also make sure that the state is updated based on free avaiable memory. |
| 259 // Since the global state has changed in the previous task, we have to wait | 264 // Since the global state has changed in the previous task, we have to wait |
| 260 // for |minimum_transition|. | 265 // for |minimum_transition|. |
| 261 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); | 266 GetMockMemoryMonitor()->SetFreeMemoryUntilCriticalMB(40); |
| 262 task_runner_->FastForwardBy(minimum_transition); | 267 task_runner_->FastForwardBy(minimum_transition); |
| 263 task_runner_->RunUntilIdle(); | 268 task_runner_->RunUntilIdle(); |
| 264 EXPECT_EQ(base::MemoryState::THROTTLED, coordinator_->GetGlobalMemoryState()); | 269 EXPECT_EQ(base::MemoryState::THROTTLED, coordinator_->GetGlobalMemoryState()); |
| 265 } | 270 } |
| 266 | 271 |
| 267 } // namespace content | 272 } // namespace content |
| OLD | NEW |