OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 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 "gpu/ipc/service/gpu_command_buffer_stub.h" | 5 #include "gpu/ipc/service/gpu_command_buffer_stub.h" |
6 | 6 |
7 #include <utility> | 7 #include <utility> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/bind_helpers.h" | 10 #include "base/bind_helpers.h" |
11 #include "base/command_line.h" | |
11 #include "base/hash.h" | 12 #include "base/hash.h" |
12 #include "base/json/json_writer.h" | 13 #include "base/json/json_writer.h" |
13 #include "base/macros.h" | 14 #include "base/macros.h" |
14 #include "base/memory/memory_pressure_listener.h" | 15 #include "base/memory/memory_pressure_listener.h" |
15 #include "base/memory/ptr_util.h" | 16 #include "base/memory/ptr_util.h" |
16 #include "base/memory/shared_memory.h" | 17 #include "base/memory/shared_memory.h" |
18 #include "base/metrics/field_trial.h" | |
17 #include "base/metrics/histogram_macros.h" | 19 #include "base/metrics/histogram_macros.h" |
18 #include "base/time/time.h" | 20 #include "base/time/time.h" |
19 #include "base/trace_event/trace_event.h" | 21 #include "base/trace_event/trace_event.h" |
20 #include "build/build_config.h" | 22 #include "build/build_config.h" |
21 #include "gpu/command_buffer/common/constants.h" | 23 #include "gpu/command_buffer/common/constants.h" |
22 #include "gpu/command_buffer/common/gpu_memory_buffer_support.h" | 24 #include "gpu/command_buffer/common/gpu_memory_buffer_support.h" |
23 #include "gpu/command_buffer/common/mailbox.h" | 25 #include "gpu/command_buffer/common/mailbox.h" |
24 #include "gpu/command_buffer/common/sync_token.h" | 26 #include "gpu/command_buffer/common/sync_token.h" |
25 #include "gpu/command_buffer/service/gl_context_virtual.h" | 27 #include "gpu/command_buffer/service/gl_context_virtual.h" |
26 #include "gpu/command_buffer/service/gl_state_restorer_impl.h" | 28 #include "gpu/command_buffer/service/gl_state_restorer_impl.h" |
27 #include "gpu/command_buffer/service/image_manager.h" | 29 #include "gpu/command_buffer/service/image_manager.h" |
28 #include "gpu/command_buffer/service/logger.h" | 30 #include "gpu/command_buffer/service/logger.h" |
29 #include "gpu/command_buffer/service/mailbox_manager.h" | 31 #include "gpu/command_buffer/service/mailbox_manager.h" |
30 #include "gpu/command_buffer/service/memory_tracking.h" | 32 #include "gpu/command_buffer/service/memory_tracking.h" |
31 #include "gpu/command_buffer/service/query_manager.h" | 33 #include "gpu/command_buffer/service/query_manager.h" |
32 #include "gpu/command_buffer/service/service_utils.h" | 34 #include "gpu/command_buffer/service/service_utils.h" |
33 #include "gpu/command_buffer/service/sync_point_manager.h" | 35 #include "gpu/command_buffer/service/sync_point_manager.h" |
34 #include "gpu/command_buffer/service/transfer_buffer_manager.h" | 36 #include "gpu/command_buffer/service/transfer_buffer_manager.h" |
35 #include "gpu/ipc/common/gpu_messages.h" | 37 #include "gpu/ipc/common/gpu_messages.h" |
36 #include "gpu/ipc/service/gpu_channel.h" | 38 #include "gpu/ipc/service/gpu_channel.h" |
37 #include "gpu/ipc/service/gpu_channel_manager.h" | 39 #include "gpu/ipc/service/gpu_channel_manager.h" |
38 #include "gpu/ipc/service/gpu_channel_manager_delegate.h" | 40 #include "gpu/ipc/service/gpu_channel_manager_delegate.h" |
39 #include "gpu/ipc/service/gpu_memory_buffer_factory.h" | 41 #include "gpu/ipc/service/gpu_memory_buffer_factory.h" |
40 #include "gpu/ipc/service/gpu_memory_manager.h" | 42 #include "gpu/ipc/service/gpu_memory_manager.h" |
41 #include "gpu/ipc/service/gpu_memory_tracking.h" | 43 #include "gpu/ipc/service/gpu_memory_tracking.h" |
44 #include "gpu/ipc/service/gpu_vsync_provider.h" | |
42 #include "gpu/ipc/service/gpu_watchdog_thread.h" | 45 #include "gpu/ipc/service/gpu_watchdog_thread.h" |
43 #include "gpu/ipc/service/image_transport_surface.h" | 46 #include "gpu/ipc/service/image_transport_surface.h" |
44 #include "ui/gl/gl_bindings.h" | 47 #include "ui/gl/gl_bindings.h" |
45 #include "ui/gl/gl_context.h" | 48 #include "ui/gl/gl_context.h" |
46 #include "ui/gl/gl_image.h" | 49 #include "ui/gl/gl_image.h" |
47 #include "ui/gl/gl_implementation.h" | 50 #include "ui/gl/gl_implementation.h" |
48 #include "ui/gl/gl_switches.h" | 51 #include "ui/gl/gl_switches.h" |
49 #include "ui/gl/init/gl_factory.h" | 52 #include "ui/gl/init/gl_factory.h" |
50 | 53 |
51 #if defined(OS_WIN) | 54 #if defined(OS_WIN) |
(...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
211 res->SetInteger("renderer_pid", channel->GetClientPID()); | 214 res->SetInteger("renderer_pid", channel->GetClientPID()); |
212 res->SetDouble("used_bytes", channel->GetMemoryUsage()); | 215 res->SetDouble("used_bytes", channel->GetMemoryUsage()); |
213 return base::WrapUnique(new DevToolsChannelData(res.release())); | 216 return base::WrapUnique(new DevToolsChannelData(res.release())); |
214 } | 217 } |
215 | 218 |
216 CommandBufferId GetCommandBufferID(int channel_id, int32_t route_id) { | 219 CommandBufferId GetCommandBufferID(int channel_id, int32_t route_id) { |
217 return CommandBufferId::FromUnsafeValue( | 220 return CommandBufferId::FromUnsafeValue( |
218 (static_cast<uint64_t>(channel_id) << 32) | route_id); | 221 (static_cast<uint64_t>(channel_id) << 32) | route_id); |
219 } | 222 } |
220 | 223 |
224 bool IsGpuVSyncSignalSupported() { | |
sunnyps
2017/01/25 01:36:41
This should be passed from the browser to gpu proc
stanisc
2017/01/26 02:14:13
I think it is doesn't make much sense to over-comp
| |
225 #if defined(OS_WIN) | |
226 base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); | |
227 if (command_line->HasSwitch(switches::kUseD3DVSync)) | |
228 return true; | |
229 | |
230 const std::string group_name = | |
231 base::FieldTrialList::FindFullName("UseD3DVSync"); | |
jbauman
2017/01/25 00:00:16
Could you use base::Feature here instead?
stanisc
2017/01/26 02:14:12
Done.
| |
232 return group_name == "Enabled"; | |
233 #else | |
234 return false; | |
235 #endif // defined(OS_WIN) | |
236 } | |
237 | |
221 } // namespace | 238 } // namespace |
222 | 239 |
223 std::unique_ptr<GpuCommandBufferStub> GpuCommandBufferStub::Create( | 240 std::unique_ptr<GpuCommandBufferStub> GpuCommandBufferStub::Create( |
224 GpuChannel* channel, | 241 GpuChannel* channel, |
225 GpuCommandBufferStub* share_command_buffer_stub, | 242 GpuCommandBufferStub* share_command_buffer_stub, |
226 const GPUCreateCommandBufferConfig& init_params, | 243 const GPUCreateCommandBufferConfig& init_params, |
227 int32_t route_id, | 244 int32_t route_id, |
228 std::unique_ptr<base::SharedMemory> shared_state_shm) { | 245 std::unique_ptr<base::SharedMemory> shared_state_shm) { |
229 std::unique_ptr<GpuCommandBufferStub> stub( | 246 std::unique_ptr<GpuCommandBufferStub> stub( |
230 new GpuCommandBufferStub(channel, init_params, route_id)); | 247 new GpuCommandBufferStub(channel, init_params, route_id)); |
(...skipping 11 matching lines...) Expand all Loading... | |
242 initialized_(false), | 259 initialized_(false), |
243 surface_handle_(init_params.surface_handle), | 260 surface_handle_(init_params.surface_handle), |
244 use_virtualized_gl_context_(false), | 261 use_virtualized_gl_context_(false), |
245 command_buffer_id_(GetCommandBufferID(channel->client_id(), route_id)), | 262 command_buffer_id_(GetCommandBufferID(channel->client_id(), route_id)), |
246 stream_id_(init_params.stream_id), | 263 stream_id_(init_params.stream_id), |
247 route_id_(route_id), | 264 route_id_(route_id), |
248 last_flush_count_(0), | 265 last_flush_count_(0), |
249 waiting_for_sync_point_(false), | 266 waiting_for_sync_point_(false), |
250 previous_processed_num_(0), | 267 previous_processed_num_(0), |
251 active_url_(init_params.active_url), | 268 active_url_(init_params.active_url), |
252 active_url_hash_(base::Hash(active_url_.possibly_invalid_spec())) {} | 269 active_url_hash_(base::Hash(active_url_.possibly_invalid_spec())), |
270 gpu_vsync_signal_supported_(IsGpuVSyncSignalSupported()) {} | |
253 | 271 |
254 GpuCommandBufferStub::~GpuCommandBufferStub() { | 272 GpuCommandBufferStub::~GpuCommandBufferStub() { |
255 Destroy(); | 273 Destroy(); |
256 } | 274 } |
257 | 275 |
258 GpuMemoryManager* GpuCommandBufferStub::GetMemoryManager() const { | 276 GpuMemoryManager* GpuCommandBufferStub::GetMemoryManager() const { |
259 return channel()->gpu_channel_manager()->gpu_memory_manager(); | 277 return channel()->gpu_channel_manager()->gpu_memory_manager(); |
260 } | 278 } |
261 | 279 |
262 bool GpuCommandBufferStub::OnMessageReceived(const IPC::Message& message) { | 280 bool GpuCommandBufferStub::OnMessageReceived(const IPC::Message& message) { |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
303 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_WaitSyncToken, | 321 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_WaitSyncToken, |
304 OnWaitSyncToken) | 322 OnWaitSyncToken) |
305 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_SignalSyncToken, | 323 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_SignalSyncToken, |
306 OnSignalSyncToken) | 324 OnSignalSyncToken) |
307 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_SignalQuery, | 325 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_SignalQuery, |
308 OnSignalQuery) | 326 OnSignalQuery) |
309 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_CreateImage, OnCreateImage); | 327 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_CreateImage, OnCreateImage); |
310 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_DestroyImage, OnDestroyImage); | 328 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_DestroyImage, OnDestroyImage); |
311 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_CreateStreamTexture, | 329 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_CreateStreamTexture, |
312 OnCreateStreamTexture) | 330 OnCreateStreamTexture) |
331 IPC_MESSAGE_HANDLER(GpuCommandBufferMsg_SetNeedsVSync, OnSetNeedsVSync); | |
313 IPC_MESSAGE_UNHANDLED(handled = false) | 332 IPC_MESSAGE_UNHANDLED(handled = false) |
314 IPC_END_MESSAGE_MAP() | 333 IPC_END_MESSAGE_MAP() |
315 | 334 |
316 CheckCompleteWaits(); | 335 CheckCompleteWaits(); |
317 | 336 |
318 // Ensure that any delayed work that was created will be handled. | 337 // Ensure that any delayed work that was created will be handled. |
319 if (have_context) { | 338 if (have_context) { |
320 if (executor_) | 339 if (executor_) |
321 executor_->ProcessPendingQueries(); | 340 executor_->ProcessPendingQueries(); |
322 ScheduleDelayedWork( | 341 ScheduleDelayedWork( |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
363 return context_group_->feature_info(); | 382 return context_group_->feature_info(); |
364 } | 383 } |
365 | 384 |
366 void GpuCommandBufferStub::SetLatencyInfoCallback( | 385 void GpuCommandBufferStub::SetLatencyInfoCallback( |
367 const LatencyInfoCallback& callback) { | 386 const LatencyInfoCallback& callback) { |
368 latency_info_callback_ = callback; | 387 latency_info_callback_ = callback; |
369 } | 388 } |
370 | 389 |
371 void GpuCommandBufferStub::UpdateVSyncParameters(base::TimeTicks timebase, | 390 void GpuCommandBufferStub::UpdateVSyncParameters(base::TimeTicks timebase, |
372 base::TimeDelta interval) { | 391 base::TimeDelta interval) { |
392 #if defined(OS_WIN) | |
393 if (gpu_vsync_signal_supported_) { | |
394 base::AutoLock lock(vsync_lock_); | |
395 vsync_interval_ = interval; | |
396 return; | |
397 } | |
398 #endif // defined(OS_WIN) | |
399 | |
400 SendUpdatedVSyncParameters(timebase, interval); | |
401 } | |
402 | |
403 void GpuCommandBufferStub::UpdateGpuVSync(base::TimeTicks timestamp) { | |
404 DCHECK(gpu_vsync_signal_supported_); | |
405 | |
406 #if defined(OS_WIN) | |
407 | |
408 base::TimeDelta interval; | |
409 { | |
410 base::AutoLock lock(vsync_lock_); | |
411 interval = vsync_interval_; | |
412 } | |
413 | |
414 SendUpdatedVSyncParameters(timestamp, interval); | |
415 #endif // defined(OS_WIN) | |
416 } | |
417 | |
418 void GpuCommandBufferStub::SendUpdatedVSyncParameters( | |
jbauman
2017/01/25 00:00:16
Technically Send on an IPC::SyncChannel can only b
stanisc
2017/01/26 02:14:13
Done.
| |
419 base::TimeTicks timebase, | |
420 base::TimeDelta interval) { | |
373 Send(new GpuCommandBufferMsg_UpdateVSyncParameters(route_id_, timebase, | 421 Send(new GpuCommandBufferMsg_UpdateVSyncParameters(route_id_, timebase, |
374 interval)); | 422 interval)); |
375 } | 423 } |
376 | 424 |
377 bool GpuCommandBufferStub::IsScheduled() { | 425 bool GpuCommandBufferStub::IsScheduled() { |
378 return (!executor_.get() || executor_->scheduled()); | 426 return (!executor_.get() || executor_->scheduled()); |
379 } | 427 } |
380 | 428 |
381 void GpuCommandBufferStub::PollWork() { | 429 void GpuCommandBufferStub::PollWork() { |
382 // Post another delayed task if we have not yet reached the time at which | 430 // Post another delayed task if we have not yet reached the time at which |
(...skipping 131 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
514 | 562 |
515 if (decoder_) | 563 if (decoder_) |
516 decoder_->set_engine(NULL); | 564 decoder_->set_engine(NULL); |
517 | 565 |
518 // The scheduler has raw references to the decoder and the command buffer so | 566 // The scheduler has raw references to the decoder and the command buffer so |
519 // destroy it before those. | 567 // destroy it before those. |
520 executor_.reset(); | 568 executor_.reset(); |
521 | 569 |
522 sync_point_client_.reset(); | 570 sync_point_client_.reset(); |
523 | 571 |
572 vsync_provider_.reset(); | |
573 | |
524 bool have_context = false; | 574 bool have_context = false; |
525 if (decoder_ && decoder_->GetGLContext()) { | 575 if (decoder_ && decoder_->GetGLContext()) { |
526 // Try to make the context current regardless of whether it was lost, so we | 576 // Try to make the context current regardless of whether it was lost, so we |
527 // don't leak resources. | 577 // don't leak resources. |
528 have_context = decoder_->GetGLContext()->MakeCurrent(surface_.get()); | 578 have_context = decoder_->GetGLContext()->MakeCurrent(surface_.get()); |
529 } | 579 } |
530 for (auto& observer : destruction_observers_) | 580 for (auto& observer : destruction_observers_) |
531 observer.OnWillDestroyStub(); | 581 observer.OnWillDestroyStub(); |
532 | 582 |
533 if (decoder_) { | 583 if (decoder_) { |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
627 } else { | 677 } else { |
628 surface_ = ImageTransportSurface::CreateNativeSurface( | 678 surface_ = ImageTransportSurface::CreateNativeSurface( |
629 AsWeakPtr(), surface_handle_, surface_format); | 679 AsWeakPtr(), surface_handle_, surface_format); |
630 if (!surface_ || !surface_->Initialize(surface_format)) { | 680 if (!surface_ || !surface_->Initialize(surface_format)) { |
631 surface_ = nullptr; | 681 surface_ = nullptr; |
632 DLOG(ERROR) << "Failed to create surface."; | 682 DLOG(ERROR) << "Failed to create surface."; |
633 return false; | 683 return false; |
634 } | 684 } |
635 } | 685 } |
636 | 686 |
687 if (IsGpuVSyncSignalSupported()) { | |
688 vsync_provider_ = GpuVSyncProvider::Create( | |
jbauman
2017/01/25 00:00:16
Only create this for stubs that aren't "offscreen"
stanisc
2017/01/26 02:14:13
Done.
| |
689 base::Bind(&GpuCommandBufferStub::UpdateGpuVSync, | |
690 base::Unretained(this)), | |
691 surface_handle_); | |
692 } | |
693 | |
637 scoped_refptr<gl::GLContext> context; | 694 scoped_refptr<gl::GLContext> context; |
638 gl::GLShareGroup* gl_share_group = channel_->share_group(); | 695 gl::GLShareGroup* gl_share_group = channel_->share_group(); |
639 if (use_virtualized_gl_context_ && gl_share_group) { | 696 if (use_virtualized_gl_context_ && gl_share_group) { |
640 context = gl_share_group->GetSharedContext(surface_.get()); | 697 context = gl_share_group->GetSharedContext(surface_.get()); |
641 if (!context.get()) { | 698 if (!context.get()) { |
642 context = gl::init::CreateGLContext( | 699 context = gl::init::CreateGLContext( |
643 gl_share_group, surface_.get(), | 700 gl_share_group, surface_.get(), |
644 GenerateGLContextAttribs(init_params.attribs, | 701 GenerateGLContextAttribs(init_params.attribs, |
645 context_group_->gpu_preferences())); | 702 context_group_->gpu_preferences())); |
646 if (!context.get()) { | 703 if (!context.get()) { |
(...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
763 } | 820 } |
764 | 821 |
765 void GpuCommandBufferStub::OnSetGetBuffer(int32_t shm_id, | 822 void GpuCommandBufferStub::OnSetGetBuffer(int32_t shm_id, |
766 IPC::Message* reply_message) { | 823 IPC::Message* reply_message) { |
767 TRACE_EVENT0("gpu", "GpuCommandBufferStub::OnSetGetBuffer"); | 824 TRACE_EVENT0("gpu", "GpuCommandBufferStub::OnSetGetBuffer"); |
768 if (command_buffer_) | 825 if (command_buffer_) |
769 command_buffer_->SetGetBuffer(shm_id); | 826 command_buffer_->SetGetBuffer(shm_id); |
770 Send(reply_message); | 827 Send(reply_message); |
771 } | 828 } |
772 | 829 |
830 void GpuCommandBufferStub::OnSetNeedsVSync(bool needs_vsync) { | |
831 DCHECK(vsync_provider_); | |
jbauman
2017/01/25 00:00:16
if (!vsync_provider_) return;
This message could
stanisc
2017/01/26 02:14:13
Done.
| |
832 vsync_provider_->SetNeedsVSync(needs_vsync); | |
833 } | |
834 | |
773 void GpuCommandBufferStub::OnTakeFrontBuffer(const Mailbox& mailbox) { | 835 void GpuCommandBufferStub::OnTakeFrontBuffer(const Mailbox& mailbox) { |
774 TRACE_EVENT0("gpu", "GpuCommandBufferStub::OnTakeFrontBuffer"); | 836 TRACE_EVENT0("gpu", "GpuCommandBufferStub::OnTakeFrontBuffer"); |
775 if (!decoder_) { | 837 if (!decoder_) { |
776 LOG(ERROR) << "Can't take front buffer before initialization."; | 838 LOG(ERROR) << "Can't take front buffer before initialization."; |
777 return; | 839 return; |
778 } | 840 } |
779 | 841 |
780 decoder_->TakeFrontBuffer(mailbox); | 842 decoder_->TakeFrontBuffer(mailbox); |
781 } | 843 } |
782 | 844 |
(...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1202 command_buffer_->GetLastState().error == error::kLostContext) | 1264 command_buffer_->GetLastState().error == error::kLostContext) |
1203 return; | 1265 return; |
1204 | 1266 |
1205 command_buffer_->SetContextLostReason(error::kUnknown); | 1267 command_buffer_->SetContextLostReason(error::kUnknown); |
1206 if (decoder_) | 1268 if (decoder_) |
1207 decoder_->MarkContextLost(error::kUnknown); | 1269 decoder_->MarkContextLost(error::kUnknown); |
1208 command_buffer_->SetParseError(error::kLostContext); | 1270 command_buffer_->SetParseError(error::kLostContext); |
1209 } | 1271 } |
1210 | 1272 |
1211 } // namespace gpu | 1273 } // namespace gpu |
OLD | NEW |