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

Side by Side Diff: content/common/gpu/gpu_channel_manager.cc

Issue 1845563005: Refactor content/common/gpu into gpu/ipc/service (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Drop ref to deleted content_tests_gypi_values.content_unittests_ozone_sources Created 4 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
OLDNEW
(Empty)
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "content/common/gpu/gpu_channel_manager.h"
6
7 #include <algorithm>
8 #include <utility>
9
10 #include "base/bind.h"
11 #include "base/location.h"
12 #include "base/single_thread_task_runner.h"
13 #include "base/thread_task_runner_handle.h"
14 #include "build/build_config.h"
15 #include "content/common/gpu/gpu_channel.h"
16 #include "content/common/gpu/gpu_channel_manager_delegate.h"
17 #include "content/common/gpu/gpu_memory_buffer_factory.h"
18 #include "content/common/gpu/gpu_memory_manager.h"
19 #include "gpu/command_buffer/common/sync_token.h"
20 #include "gpu/command_buffer/common/value_state.h"
21 #include "gpu/command_buffer/service/feature_info.h"
22 #include "gpu/command_buffer/service/mailbox_manager.h"
23 #include "gpu/command_buffer/service/memory_program_cache.h"
24 #include "gpu/command_buffer/service/shader_translator_cache.h"
25 #include "gpu/command_buffer/service/sync_point_manager.h"
26 #include "gpu/ipc/common/gpu_messages.h"
27 #include "ui/gl/gl_bindings.h"
28 #include "ui/gl/gl_share_group.h"
29
30 namespace content {
31
32 namespace {
33 #if defined(OS_ANDROID)
34 // Amount of time we expect the GPU to stay powered up without being used.
35 const int kMaxGpuIdleTimeMs = 40;
36 // Maximum amount of time we keep pinging the GPU waiting for the client to
37 // draw.
38 const int kMaxKeepAliveTimeMs = 200;
39 #endif
40
41 }
42
43 GpuChannelManager::GpuChannelManager(
44 const gpu::GpuPreferences& gpu_preferences,
45 GpuChannelManagerDelegate* delegate,
46 GpuWatchdog* watchdog,
47 base::SingleThreadTaskRunner* task_runner,
48 base::SingleThreadTaskRunner* io_task_runner,
49 base::WaitableEvent* shutdown_event,
50 gpu::SyncPointManager* sync_point_manager,
51 GpuMemoryBufferFactory* gpu_memory_buffer_factory)
52 : task_runner_(task_runner),
53 io_task_runner_(io_task_runner),
54 gpu_preferences_(gpu_preferences),
55 delegate_(delegate),
56 watchdog_(watchdog),
57 shutdown_event_(shutdown_event),
58 share_group_(new gfx::GLShareGroup),
59 mailbox_manager_(gpu::gles2::MailboxManager::Create(gpu_preferences)),
60 gpu_memory_manager_(this),
61 sync_point_manager_(sync_point_manager),
62 sync_point_client_waiter_(
63 sync_point_manager->CreateSyncPointClientWaiter()),
64 gpu_memory_buffer_factory_(gpu_memory_buffer_factory),
65 weak_factory_(this) {
66 DCHECK(task_runner);
67 DCHECK(io_task_runner);
68 if (gpu_preferences_.ui_prioritize_in_gpu_process)
69 preemption_flag_ = new gpu::PreemptionFlag;
70 }
71
72 GpuChannelManager::~GpuChannelManager() {
73 // Destroy channels before anything else because of dependencies.
74 gpu_channels_.clear();
75 if (default_offscreen_surface_.get()) {
76 default_offscreen_surface_->Destroy();
77 default_offscreen_surface_ = NULL;
78 }
79 }
80
81 gpu::gles2::ProgramCache* GpuChannelManager::program_cache() {
82 if (!program_cache_.get() &&
83 (gfx::g_driver_gl.ext.b_GL_ARB_get_program_binary ||
84 gfx::g_driver_gl.ext.b_GL_OES_get_program_binary) &&
85 !gpu_preferences_.disable_gpu_program_cache) {
86 program_cache_.reset(new gpu::gles2::MemoryProgramCache(
87 gpu_preferences_.gpu_program_cache_size,
88 gpu_preferences_.disable_gpu_shader_disk_cache));
89 }
90 return program_cache_.get();
91 }
92
93 gpu::gles2::ShaderTranslatorCache*
94 GpuChannelManager::shader_translator_cache() {
95 if (!shader_translator_cache_.get()) {
96 shader_translator_cache_ =
97 new gpu::gles2::ShaderTranslatorCache(gpu_preferences_);
98 }
99 return shader_translator_cache_.get();
100 }
101
102 gpu::gles2::FramebufferCompletenessCache*
103 GpuChannelManager::framebuffer_completeness_cache() {
104 if (!framebuffer_completeness_cache_.get())
105 framebuffer_completeness_cache_ =
106 new gpu::gles2::FramebufferCompletenessCache;
107 return framebuffer_completeness_cache_.get();
108 }
109
110 void GpuChannelManager::RemoveChannel(int client_id) {
111 delegate_->DidDestroyChannel(client_id);
112 gpu_channels_.erase(client_id);
113 }
114
115 #if defined(OS_MACOSX)
116 void GpuChannelManager::AddBufferPresentedCallback(
117 int32_t surface_id,
118 const BufferPresentedCallback& callback) {
119 DCHECK(buffer_presented_callback_map_.find(surface_id) ==
120 buffer_presented_callback_map_.end());
121 buffer_presented_callback_map_[surface_id] = callback;
122 }
123
124 void GpuChannelManager::RemoveBufferPresentedCallback(int32_t surface_id) {
125 auto it = buffer_presented_callback_map_.find(surface_id);
126 DCHECK(it != buffer_presented_callback_map_.end());
127 buffer_presented_callback_map_.erase(it);
128 }
129
130 void GpuChannelManager::BufferPresented(int32_t surface_id,
131 const base::TimeTicks& vsync_timebase,
132 const base::TimeDelta& vsync_interval) {
133 auto it = buffer_presented_callback_map_.find(surface_id);
134 if (it != buffer_presented_callback_map_.end())
135 it->second.Run(surface_id, vsync_timebase, vsync_interval);
136 }
137 #endif
138
139 GpuChannel* GpuChannelManager::LookupChannel(int32_t client_id) const {
140 const auto& it = gpu_channels_.find(client_id);
141 return it != gpu_channels_.end() ? it->second : nullptr;
142 }
143
144 scoped_ptr<GpuChannel> GpuChannelManager::CreateGpuChannel(
145 int client_id,
146 uint64_t client_tracing_id,
147 bool preempts,
148 bool allow_view_command_buffers,
149 bool allow_real_time_streams) {
150 return make_scoped_ptr(
151 new GpuChannel(this, sync_point_manager(), watchdog_, share_group(),
152 mailbox_manager(), preempts ? preemption_flag() : nullptr,
153 preempts ? nullptr : preemption_flag(), task_runner_.get(),
154 io_task_runner_.get(), client_id, client_tracing_id,
155 allow_view_command_buffers, allow_real_time_streams));
156 }
157
158 IPC::ChannelHandle GpuChannelManager::EstablishChannel(
159 int client_id,
160 uint64_t client_tracing_id,
161 bool preempts,
162 bool allow_view_command_buffers,
163 bool allow_real_time_streams) {
164 scoped_ptr<GpuChannel> channel(
165 CreateGpuChannel(client_id, client_tracing_id, preempts,
166 allow_view_command_buffers, allow_real_time_streams));
167 IPC::ChannelHandle channel_handle = channel->Init(shutdown_event_);
168 gpu_channels_.set(client_id, std::move(channel));
169 return channel_handle;
170 }
171
172 void GpuChannelManager::InternalDestroyGpuMemoryBuffer(
173 gfx::GpuMemoryBufferId id,
174 int client_id) {
175 io_task_runner_->PostTask(
176 FROM_HERE,
177 base::Bind(&GpuChannelManager::InternalDestroyGpuMemoryBufferOnIO,
178 base::Unretained(this), id, client_id));
179 }
180
181 void GpuChannelManager::InternalDestroyGpuMemoryBufferOnIO(
182 gfx::GpuMemoryBufferId id,
183 int client_id) {
184 gpu_memory_buffer_factory_->DestroyGpuMemoryBuffer(id, client_id);
185 }
186
187 void GpuChannelManager::DestroyGpuMemoryBuffer(
188 gfx::GpuMemoryBufferId id,
189 int client_id,
190 const gpu::SyncToken& sync_token) {
191 if (sync_token.HasData()) {
192 scoped_refptr<gpu::SyncPointClientState> release_state =
193 sync_point_manager()->GetSyncPointClientState(
194 sync_token.namespace_id(), sync_token.command_buffer_id());
195 if (release_state) {
196 sync_point_client_waiter_->WaitOutOfOrder(
197 release_state.get(), sync_token.release_count(),
198 base::Bind(&GpuChannelManager::InternalDestroyGpuMemoryBuffer,
199 base::Unretained(this), id, client_id));
200 return;
201 }
202 }
203
204 // No sync token or invalid sync token, destroy immediately.
205 InternalDestroyGpuMemoryBuffer(id, client_id);
206 }
207
208 void GpuChannelManager::UpdateValueState(int client_id,
209 unsigned int target,
210 const gpu::ValueState& state) {
211 // Only pass updated state to the channel corresponding to the
212 // render_widget_host where the event originated.
213 auto it = gpu_channels_.find(client_id);
214 if (it != gpu_channels_.end())
215 it->second->HandleUpdateValueState(target, state);
216 }
217
218 void GpuChannelManager::PopulateShaderCache(const std::string& program_proto) {
219 if (program_cache())
220 program_cache()->LoadProgram(program_proto);
221 }
222
223 uint32_t GpuChannelManager::GetUnprocessedOrderNum() const {
224 uint32_t unprocessed_order_num = 0;
225 for (auto& kv : gpu_channels_) {
226 unprocessed_order_num =
227 std::max(unprocessed_order_num, kv.second->GetUnprocessedOrderNum());
228 }
229 return unprocessed_order_num;
230 }
231
232 uint32_t GpuChannelManager::GetProcessedOrderNum() const {
233 uint32_t processed_order_num = 0;
234 for (auto& kv : gpu_channels_) {
235 processed_order_num =
236 std::max(processed_order_num, kv.second->GetProcessedOrderNum());
237 }
238 return processed_order_num;
239 }
240
241 void GpuChannelManager::LoseAllContexts() {
242 for (auto& kv : gpu_channels_) {
243 kv.second->MarkAllContextsLost();
244 }
245 task_runner_->PostTask(FROM_HERE,
246 base::Bind(&GpuChannelManager::DestroyAllChannels,
247 weak_factory_.GetWeakPtr()));
248 }
249
250 void GpuChannelManager::DestroyAllChannels() {
251 gpu_channels_.clear();
252 }
253
254 gfx::GLSurface* GpuChannelManager::GetDefaultOffscreenSurface() {
255 if (!default_offscreen_surface_.get()) {
256 default_offscreen_surface_ =
257 gfx::GLSurface::CreateOffscreenGLSurface(gfx::Size());
258 }
259 return default_offscreen_surface_.get();
260 }
261
262 #if defined(OS_ANDROID)
263 void GpuChannelManager::DidAccessGpu() {
264 last_gpu_access_time_ = base::TimeTicks::Now();
265 }
266
267 void GpuChannelManager::WakeUpGpu() {
268 begin_wake_up_time_ = base::TimeTicks::Now();
269 ScheduleWakeUpGpu();
270 }
271
272 void GpuChannelManager::ScheduleWakeUpGpu() {
273 base::TimeTicks now = base::TimeTicks::Now();
274 TRACE_EVENT2("gpu", "GpuChannelManager::ScheduleWakeUp",
275 "idle_time", (now - last_gpu_access_time_).InMilliseconds(),
276 "keep_awake_time", (now - begin_wake_up_time_).InMilliseconds());
277 if (now - last_gpu_access_time_ <
278 base::TimeDelta::FromMilliseconds(kMaxGpuIdleTimeMs))
279 return;
280 if (now - begin_wake_up_time_ >
281 base::TimeDelta::FromMilliseconds(kMaxKeepAliveTimeMs))
282 return;
283
284 DoWakeUpGpu();
285
286 base::MessageLoop::current()->PostDelayedTask(
287 FROM_HERE, base::Bind(&GpuChannelManager::ScheduleWakeUpGpu,
288 weak_factory_.GetWeakPtr()),
289 base::TimeDelta::FromMilliseconds(kMaxGpuIdleTimeMs));
290 }
291
292 void GpuChannelManager::DoWakeUpGpu() {
293 const GpuCommandBufferStub* stub = nullptr;
294 for (const auto& kv : gpu_channels_) {
295 const GpuChannel* channel = kv.second;
296 stub = channel->GetOneStub();
297 if (stub) {
298 DCHECK(stub->decoder());
299 break;
300 }
301 }
302 if (!stub || !stub->decoder()->MakeCurrent())
303 return;
304 glFinish();
305 DidAccessGpu();
306 }
307 #endif
308
309 } // namespace content
OLDNEW
« no previous file with comments | « content/common/gpu/gpu_channel_manager.h ('k') | content/common/gpu/gpu_channel_manager_delegate.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698