OLD | NEW |
---|---|
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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/renderer_host/renderer_frame_manager.h" | 5 #include "content/browser/renderer_host/renderer_frame_manager.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
11 #include "base/memory/memory_coordinator_client_registry.h" | |
11 #include "base/memory/memory_pressure_listener.h" | 12 #include "base/memory/memory_pressure_listener.h" |
12 #include "base/memory/memory_pressure_monitor.h" | 13 #include "base/memory/memory_pressure_monitor.h" |
13 #include "base/memory/shared_memory.h" | 14 #include "base/memory/shared_memory.h" |
14 #include "base/sys_info.h" | 15 #include "base/sys_info.h" |
15 #include "build/build_config.h" | 16 #include "build/build_config.h" |
16 #include "content/common/host_shared_bitmap_manager.h" | 17 #include "content/common/host_shared_bitmap_manager.h" |
18 #include "content/public/common/content_features.h" | |
17 | 19 |
18 namespace content { | 20 namespace content { |
19 namespace { | 21 namespace { |
20 | 22 |
21 const int kModeratePressurePercentage = 50; | 23 const int kModeratePressurePercentage = 50; |
22 const int kCriticalPressurePercentage = 10; | 24 const int kCriticalPressurePercentage = 10; |
23 | 25 |
24 } // namespace | 26 } // namespace |
25 | 27 |
26 RendererFrameManager* RendererFrameManager::GetInstance() { | 28 RendererFrameManager* RendererFrameManager::GetInstance() { |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
65 if (locked_count > 1) { | 67 if (locked_count > 1) { |
66 locked_frames_[frame]--; | 68 locked_frames_[frame]--; |
67 } else { | 69 } else { |
68 RemoveFrame(frame); | 70 RemoveFrame(frame); |
69 unlocked_frames_.push_front(frame); | 71 unlocked_frames_.push_front(frame); |
70 CullUnlockedFrames(GetMaxNumberOfSavedFrames()); | 72 CullUnlockedFrames(GetMaxNumberOfSavedFrames()); |
71 } | 73 } |
72 } | 74 } |
73 | 75 |
74 size_t RendererFrameManager::GetMaxNumberOfSavedFrames() const { | 76 size_t RendererFrameManager::GetMaxNumberOfSavedFrames() const { |
75 base::MemoryPressureMonitor* monitor = base::MemoryPressureMonitor::Get(); | 77 int percentage = 100; |
78 if (base::FeatureList::IsEnabled(features::kMemoryCoordinator)) { | |
79 switch (memory_state_) { | |
80 case base::MemoryState::NORMAL: | |
81 percentage = 100; | |
82 break; | |
83 case base::MemoryState::THROTTLED: | |
84 percentage = kCriticalPressurePercentage; | |
85 break; | |
86 case base::MemoryState::SUSPENDED: | |
87 case base::MemoryState::UNKNOWN: | |
88 NOTREACHED(); | |
89 break; | |
90 } | |
91 } else { | |
92 base::MemoryPressureMonitor* monitor = base::MemoryPressureMonitor::Get(); | |
76 | 93 |
77 if (!monitor) | 94 if (!monitor) |
78 return max_number_of_saved_frames_; | 95 return max_number_of_saved_frames_; |
79 | 96 |
80 // Until we have a global OnMemoryPressureChanged event we need to query the | 97 // Until we have a global OnMemoryPressureChanged event we need to query the |
81 // value from our specific pressure monitor. | 98 // value from our specific pressure monitor. |
82 int percentage = 100; | 99 int percentage = 100; |
bashi
2016/09/20 07:56:51
Remove?
hajimehoshi
2016/09/20 08:09:43
Done.
| |
83 switch (monitor->GetCurrentPressureLevel()) { | 100 switch (monitor->GetCurrentPressureLevel()) { |
84 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_NONE: | 101 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_NONE: |
85 percentage = 100; | 102 percentage = 100; |
86 break; | 103 break; |
87 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_MODERATE: | 104 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_MODERATE: |
88 percentage = kModeratePressurePercentage; | 105 percentage = kModeratePressurePercentage; |
89 break; | 106 break; |
90 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_CRITICAL: | 107 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_CRITICAL: |
91 percentage = kCriticalPressurePercentage; | 108 percentage = kCriticalPressurePercentage; |
92 break; | 109 break; |
110 } | |
93 } | 111 } |
94 size_t frames = (max_number_of_saved_frames_ * percentage) / 100; | 112 size_t frames = (max_number_of_saved_frames_ * percentage) / 100; |
95 return std::max(static_cast<size_t>(1), frames); | 113 return std::max(static_cast<size_t>(1), frames); |
96 } | 114 } |
97 | 115 |
98 RendererFrameManager::RendererFrameManager() | 116 RendererFrameManager::RendererFrameManager() |
99 : memory_pressure_listener_( | 117 : memory_state_(base::MemoryState::NORMAL) { |
118 if (base::FeatureList::IsEnabled(features::kMemoryCoordinator)) { | |
119 base::MemoryCoordinatorClientRegistry::GetInstance()->Register(this); | |
120 } else { | |
121 memory_pressure_listener_.reset(new base::MemoryPressureListener( | |
100 base::Bind(&RendererFrameManager::OnMemoryPressure, | 122 base::Bind(&RendererFrameManager::OnMemoryPressure, |
101 base::Unretained(this))) { | 123 base::Unretained(this)))); |
102 // Note: With the destruction of this class the |memory_pressure_listener_| | 124 // Note: With the destruction of this class the |memory_pressure_listener_| |
103 // gets destroyed and the observer will remove itself. | 125 // gets destroyed and the observer will remove itself. |
126 } | |
104 max_number_of_saved_frames_ = | 127 max_number_of_saved_frames_ = |
105 #if defined(OS_ANDROID) | 128 #if defined(OS_ANDROID) |
106 1; | 129 1; |
107 #else | 130 #else |
108 std::min(5, 2 + (base::SysInfo::AmountOfPhysicalMemoryMB() / 256)); | 131 std::min(5, 2 + (base::SysInfo::AmountOfPhysicalMemoryMB() / 256)); |
109 #endif | 132 #endif |
110 max_handles_ = base::SharedMemory::GetHandleLimit() / 8.0f; | 133 max_handles_ = base::SharedMemory::GetHandleLimit() / 8.0f; |
111 } | 134 } |
112 | 135 |
113 RendererFrameManager::~RendererFrameManager() {} | 136 RendererFrameManager::~RendererFrameManager() {} |
(...skipping 13 matching lines...) Expand all Loading... | |
127 unlocked_frames_.size() + locked_frames_.size() > saved_frame_limit) { | 150 unlocked_frames_.size() + locked_frames_.size() > saved_frame_limit) { |
128 size_t old_size = unlocked_frames_.size(); | 151 size_t old_size = unlocked_frames_.size(); |
129 // Should remove self from list. | 152 // Should remove self from list. |
130 unlocked_frames_.back()->EvictCurrentFrame(); | 153 unlocked_frames_.back()->EvictCurrentFrame(); |
131 DCHECK_EQ(unlocked_frames_.size() + 1, old_size); | 154 DCHECK_EQ(unlocked_frames_.size() + 1, old_size); |
132 } | 155 } |
133 } | 156 } |
134 | 157 |
135 void RendererFrameManager::OnMemoryPressure( | 158 void RendererFrameManager::OnMemoryPressure( |
136 base::MemoryPressureListener::MemoryPressureLevel memory_pressure_level) { | 159 base::MemoryPressureListener::MemoryPressureLevel memory_pressure_level) { |
137 int saved_frame_limit = max_number_of_saved_frames_; | |
138 if (saved_frame_limit <= 1) | |
139 return; | |
140 int percentage = 100; | |
141 switch (memory_pressure_level) { | 160 switch (memory_pressure_level) { |
142 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_MODERATE: | 161 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_MODERATE: |
143 percentage = kModeratePressurePercentage; | 162 PurgeMemory(kModeratePressurePercentage); |
144 break; | 163 break; |
145 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_CRITICAL: | 164 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_CRITICAL: |
146 percentage = kCriticalPressurePercentage; | 165 PurgeMemory(kCriticalPressurePercentage); |
147 break; | 166 break; |
148 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_NONE: | 167 case base::MemoryPressureListener::MEMORY_PRESSURE_LEVEL_NONE: |
149 // No need to change anything when there is no pressure. | 168 // No need to change anything when there is no pressure. |
150 return; | 169 return; |
151 } | 170 } |
171 } | |
172 | |
173 void RendererFrameManager::OnMemoryStateChange(base::MemoryState state) { | |
174 memory_state_ = state; | |
175 switch (state) { | |
176 case base::MemoryState::NORMAL: | |
177 // Don't have to purge here. | |
178 break; | |
179 case base::MemoryState::THROTTLED: | |
180 // TOOD(hajimehoshi): We don't have throttling 'level' so far. When we | |
181 // have such value, let's change the argument accroding to the value. | |
182 PurgeMemory(kCriticalPressurePercentage); | |
183 break; | |
184 case base::MemoryState::SUSPENDED: | |
185 // Note that SUSPENDED never occurs in the main browser process so far. | |
186 // Fall through. | |
187 case base::MemoryState::UNKNOWN: | |
188 NOTREACHED(); | |
189 break; | |
190 } | |
191 } | |
192 | |
193 void RendererFrameManager::PurgeMemory(int percentage) { | |
194 int saved_frame_limit = max_number_of_saved_frames_; | |
195 if (saved_frame_limit <= 1) | |
196 return; | |
152 CullUnlockedFrames(std::max(1, (saved_frame_limit * percentage) / 100)); | 197 CullUnlockedFrames(std::max(1, (saved_frame_limit * percentage) / 100)); |
153 } | 198 } |
154 | 199 |
155 } // namespace content | 200 } // namespace content |
OLD | NEW |