OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 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 | 4 |
5 #include "ppapi/proxy/ppb_graphics_3d_proxy.h" | 5 #include "ppapi/proxy/ppb_graphics_3d_proxy.h" |
6 | 6 |
7 #include "gpu/command_buffer/client/gles2_implementation.h" | 7 #include "gpu/command_buffer/client/gles2_implementation.h" |
8 #include "ppapi/c/pp_errors.h" | 8 #include "ppapi/c/pp_errors.h" |
9 #include "ppapi/proxy/enter_proxy.h" | 9 #include "ppapi/proxy/enter_proxy.h" |
10 #include "ppapi/proxy/plugin_dispatcher.h" | 10 #include "ppapi/proxy/plugin_dispatcher.h" |
(...skipping 13 matching lines...) Expand all Loading... |
24 namespace { | 24 namespace { |
25 const int32 kCommandBufferSize = 1024 * 1024; | 25 const int32 kCommandBufferSize = 1024 * 1024; |
26 const int32 kTransferBufferSize = 1024 * 1024; | 26 const int32 kTransferBufferSize = 1024 * 1024; |
27 | 27 |
28 class CommandBuffer : public gpu::CommandBuffer { | 28 class CommandBuffer : public gpu::CommandBuffer { |
29 public: | 29 public: |
30 CommandBuffer(const HostResource& resource, PluginDispatcher* dispatcher); | 30 CommandBuffer(const HostResource& resource, PluginDispatcher* dispatcher); |
31 virtual ~CommandBuffer(); | 31 virtual ~CommandBuffer(); |
32 | 32 |
33 // gpu::CommandBuffer implementation: | 33 // gpu::CommandBuffer implementation: |
34 virtual bool Initialize(); | 34 virtual bool Initialize(int32 size); |
| 35 virtual bool Initialize(base::SharedMemory* buffer, int32 size); |
| 36 virtual gpu::Buffer GetRingBuffer(); |
35 virtual State GetState(); | 37 virtual State GetState(); |
36 virtual State GetLastState(); | 38 virtual State GetLastState(); |
37 virtual void Flush(int32 put_offset); | 39 virtual void Flush(int32 put_offset); |
38 virtual State FlushSync(int32 put_offset, int32 last_known_get); | 40 virtual State FlushSync(int32 put_offset, int32 last_known_get); |
39 virtual void SetGetBuffer(int32 transfer_buffer_id); | |
40 virtual void SetGetOffset(int32 get_offset); | 41 virtual void SetGetOffset(int32 get_offset); |
41 virtual int32 CreateTransferBuffer(size_t size, int32 id_request); | 42 virtual int32 CreateTransferBuffer(size_t size, int32 id_request); |
42 virtual int32 RegisterTransferBuffer(base::SharedMemory* shared_memory, | 43 virtual int32 RegisterTransferBuffer(base::SharedMemory* shared_memory, |
43 size_t size, | 44 size_t size, |
44 int32 id_request); | 45 int32 id_request); |
45 virtual void DestroyTransferBuffer(int32 id); | 46 virtual void DestroyTransferBuffer(int32 id); |
46 virtual gpu::Buffer GetTransferBuffer(int32 handle); | 47 virtual gpu::Buffer GetTransferBuffer(int32 handle); |
47 virtual void SetToken(int32 token); | 48 virtual void SetToken(int32 token); |
48 virtual void SetParseError(gpu::error::Error error); | 49 virtual void SetParseError(gpu::error::Error error); |
49 virtual void SetContextLostReason(gpu::error::ContextLostReason reason); | 50 virtual void SetContextLostReason(gpu::error::ContextLostReason reason); |
50 | 51 |
51 private: | 52 private: |
52 bool Send(IPC::Message* msg); | 53 bool Send(IPC::Message* msg); |
53 void UpdateState(const gpu::CommandBuffer::State& state); | 54 void UpdateState(const gpu::CommandBuffer::State& state); |
54 | 55 |
| 56 int32 num_entries_; |
| 57 scoped_ptr<base::SharedMemory> ring_buffer_; |
| 58 |
55 typedef base::hash_map<int32, gpu::Buffer> TransferBufferMap; | 59 typedef base::hash_map<int32, gpu::Buffer> TransferBufferMap; |
56 TransferBufferMap transfer_buffers_; | 60 TransferBufferMap transfer_buffers_; |
57 | 61 |
58 State last_state_; | 62 State last_state_; |
59 | 63 |
60 HostResource resource_; | 64 HostResource resource_; |
61 PluginDispatcher* dispatcher_; | 65 PluginDispatcher* dispatcher_; |
62 | 66 |
63 DISALLOW_COPY_AND_ASSIGN(CommandBuffer); | 67 DISALLOW_COPY_AND_ASSIGN(CommandBuffer); |
64 }; | 68 }; |
65 | 69 |
66 CommandBuffer::CommandBuffer(const HostResource& resource, | 70 CommandBuffer::CommandBuffer(const HostResource& resource, |
67 PluginDispatcher* dispatcher) | 71 PluginDispatcher* dispatcher) |
68 : resource_(resource), | 72 : num_entries_(0), |
| 73 resource_(resource), |
69 dispatcher_(dispatcher) { | 74 dispatcher_(dispatcher) { |
70 } | 75 } |
71 | 76 |
72 CommandBuffer::~CommandBuffer() { | 77 CommandBuffer::~CommandBuffer() { |
73 // Delete all the locally cached shared memory objects, closing the handle | 78 // Delete all the locally cached shared memory objects, closing the handle |
74 // in this process. | 79 // in this process. |
75 for (TransferBufferMap::iterator it = transfer_buffers_.begin(); | 80 for (TransferBufferMap::iterator it = transfer_buffers_.begin(); |
76 it != transfer_buffers_.end(); ++it) { | 81 it != transfer_buffers_.end(); ++it) { |
77 delete it->second.shared_memory; | 82 delete it->second.shared_memory; |
78 it->second.shared_memory = NULL; | 83 it->second.shared_memory = NULL; |
79 } | 84 } |
80 } | 85 } |
81 | 86 |
82 bool CommandBuffer::Initialize() { | 87 bool CommandBuffer::Initialize(int32 size) { |
83 return Send(new PpapiHostMsg_PPBGraphics3D_InitCommandBuffer( | 88 DCHECK(!ring_buffer_.get()); |
84 API_ID_PPB_GRAPHICS_3D, resource_)); | 89 |
| 90 // Initialize the service. Assuming we are sandboxed, the GPU |
| 91 // process is responsible for duplicating the handle. This might not be true |
| 92 // for NaCl. |
| 93 base::SharedMemoryHandle handle; |
| 94 if (Send(new PpapiHostMsg_PPBGraphics3D_InitCommandBuffer( |
| 95 API_ID_PPB_GRAPHICS_3D, resource_, size, &handle)) && |
| 96 base::SharedMemory::IsHandleValid(handle)) { |
| 97 ring_buffer_.reset(new base::SharedMemory(handle, false)); |
| 98 if (ring_buffer_->Map(size)) { |
| 99 num_entries_ = size / sizeof(gpu::CommandBufferEntry); |
| 100 return true; |
| 101 } |
| 102 |
| 103 ring_buffer_.reset(); |
| 104 } |
| 105 |
| 106 return false; |
| 107 } |
| 108 |
| 109 bool CommandBuffer::Initialize(base::SharedMemory* buffer, int32 size) { |
| 110 // Not implemented in proxy. |
| 111 NOTREACHED(); |
| 112 return false; |
| 113 } |
| 114 |
| 115 gpu::Buffer CommandBuffer::GetRingBuffer() { |
| 116 // Return locally cached ring buffer. |
| 117 gpu::Buffer buffer; |
| 118 if (ring_buffer_.get()) { |
| 119 buffer.ptr = ring_buffer_->memory(); |
| 120 buffer.size = num_entries_ * sizeof(gpu::CommandBufferEntry); |
| 121 buffer.shared_memory = ring_buffer_.get(); |
| 122 } else { |
| 123 buffer.ptr = NULL; |
| 124 buffer.size = 0; |
| 125 buffer.shared_memory = NULL; |
| 126 } |
| 127 return buffer; |
85 } | 128 } |
86 | 129 |
87 gpu::CommandBuffer::State CommandBuffer::GetState() { | 130 gpu::CommandBuffer::State CommandBuffer::GetState() { |
88 // Send will flag state with lost context if IPC fails. | 131 // Send will flag state with lost context if IPC fails. |
89 if (last_state_.error == gpu::error::kNoError) { | 132 if (last_state_.error == gpu::error::kNoError) { |
90 gpu::CommandBuffer::State state; | 133 gpu::CommandBuffer::State state; |
91 if (Send(new PpapiHostMsg_PPBGraphics3D_GetState( | 134 if (Send(new PpapiHostMsg_PPBGraphics3D_GetState( |
92 API_ID_PPB_GRAPHICS_3D, resource_, &state))) | 135 API_ID_PPB_GRAPHICS_3D, resource_, &state))) |
93 UpdateState(state); | 136 UpdateState(state); |
94 } | 137 } |
(...skipping 30 matching lines...) Expand all Loading... |
125 last_known_get, &state))) | 168 last_known_get, &state))) |
126 UpdateState(state); | 169 UpdateState(state); |
127 } | 170 } |
128 } else { | 171 } else { |
129 Flush(put_offset); | 172 Flush(put_offset); |
130 } | 173 } |
131 | 174 |
132 return last_state_; | 175 return last_state_; |
133 } | 176 } |
134 | 177 |
135 void CommandBuffer::SetGetBuffer(int32 transfer_buffer_id) { | |
136 if (last_state_.error == gpu::error::kNoError) { | |
137 Send(new PpapiHostMsg_PPBGraphics3D_SetGetBuffer( | |
138 API_ID_PPB_GRAPHICS_3D, resource_, transfer_buffer_id)); | |
139 } | |
140 } | |
141 | |
142 void CommandBuffer::SetGetOffset(int32 get_offset) { | 178 void CommandBuffer::SetGetOffset(int32 get_offset) { |
143 // Not implemented in proxy. | 179 // Not implemented in proxy. |
144 NOTREACHED(); | 180 NOTREACHED(); |
145 } | 181 } |
146 | 182 |
147 int32 CommandBuffer::CreateTransferBuffer(size_t size, int32 id_request) { | 183 int32 CommandBuffer::CreateTransferBuffer(size_t size, int32 id_request) { |
148 if (last_state_.error == gpu::error::kNoError) { | 184 if (last_state_.error == gpu::error::kNoError) { |
149 int32 id; | 185 int32 id; |
150 if (Send(new PpapiHostMsg_PPBGraphics3D_CreateTransferBuffer( | 186 if (Send(new PpapiHostMsg_PPBGraphics3D_CreateTransferBuffer( |
151 API_ID_PPB_GRAPHICS_3D, resource_, size, &id))) { | 187 API_ID_PPB_GRAPHICS_3D, resource_, size, &id))) { |
(...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
295 Graphics3D::~Graphics3D() { | 331 Graphics3D::~Graphics3D() { |
296 DestroyGLES2Impl(); | 332 DestroyGLES2Impl(); |
297 } | 333 } |
298 | 334 |
299 bool Graphics3D::Init() { | 335 bool Graphics3D::Init() { |
300 PluginDispatcher* dispatcher = PluginDispatcher::GetForResource(this); | 336 PluginDispatcher* dispatcher = PluginDispatcher::GetForResource(this); |
301 if (!dispatcher) | 337 if (!dispatcher) |
302 return false; | 338 return false; |
303 | 339 |
304 command_buffer_.reset(new CommandBuffer(host_resource(), dispatcher)); | 340 command_buffer_.reset(new CommandBuffer(host_resource(), dispatcher)); |
305 if (!command_buffer_->Initialize()) | 341 if (!command_buffer_->Initialize(kCommandBufferSize)) |
306 return false; | 342 return false; |
307 | 343 |
308 return CreateGLES2Impl(kCommandBufferSize, kTransferBufferSize); | 344 return CreateGLES2Impl(kCommandBufferSize, kTransferBufferSize); |
309 } | 345 } |
310 | 346 |
311 PP_Bool Graphics3D::InitCommandBuffer() { | 347 PP_Bool Graphics3D::InitCommandBuffer(int32_t size) { |
312 return PP_FALSE; | 348 return PP_FALSE; |
313 } | 349 } |
314 | 350 |
315 PP_Bool Graphics3D::SetGetBuffer(int32_t /* transfer_buffer_id */) { | 351 PP_Bool Graphics3D::GetRingBuffer(int* shm_handle, uint32_t* shm_size) { |
316 return PP_FALSE; | 352 return PP_FALSE; |
317 } | 353 } |
318 | 354 |
319 PP_Graphics3DTrustedState Graphics3D::GetState() { | 355 PP_Graphics3DTrustedState Graphics3D::GetState() { |
320 return GetErrorState(); | 356 return GetErrorState(); |
321 } | 357 } |
322 | 358 |
323 PP_Bool Graphics3D::Flush(int32_t put_offset) { | 359 PP_Bool Graphics3D::Flush(int32_t put_offset) { |
324 return PP_FALSE; | 360 return PP_FALSE; |
325 } | 361 } |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
406 return graphics_3d->GetReference(); | 442 return graphics_3d->GetReference(); |
407 } | 443 } |
408 | 444 |
409 bool PPB_Graphics3D_Proxy::OnMessageReceived(const IPC::Message& msg) { | 445 bool PPB_Graphics3D_Proxy::OnMessageReceived(const IPC::Message& msg) { |
410 bool handled = true; | 446 bool handled = true; |
411 IPC_BEGIN_MESSAGE_MAP(PPB_Graphics3D_Proxy, msg) | 447 IPC_BEGIN_MESSAGE_MAP(PPB_Graphics3D_Proxy, msg) |
412 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_Create, | 448 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_Create, |
413 OnMsgCreate) | 449 OnMsgCreate) |
414 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_InitCommandBuffer, | 450 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_InitCommandBuffer, |
415 OnMsgInitCommandBuffer) | 451 OnMsgInitCommandBuffer) |
416 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_SetGetBuffer, | |
417 OnMsgSetGetBuffer) | |
418 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_GetState, | 452 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_GetState, |
419 OnMsgGetState) | 453 OnMsgGetState) |
420 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_Flush, | 454 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_Flush, |
421 OnMsgFlush) | 455 OnMsgFlush) |
422 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_AsyncFlush, | 456 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_AsyncFlush, |
423 OnMsgAsyncFlush) | 457 OnMsgAsyncFlush) |
424 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_CreateTransferBuffer, | 458 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_CreateTransferBuffer, |
425 OnMsgCreateTransferBuffer) | 459 OnMsgCreateTransferBuffer) |
426 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_DestroyTransferBuffer, | 460 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBGraphics3D_DestroyTransferBuffer, |
427 OnMsgDestroyTransferBuffer) | 461 OnMsgDestroyTransferBuffer) |
(...skipping 19 matching lines...) Expand all Loading... |
447 | 481 |
448 thunk::EnterResourceCreation enter(instance); | 482 thunk::EnterResourceCreation enter(instance); |
449 if (enter.succeeded()) { | 483 if (enter.succeeded()) { |
450 result->SetHostResource( | 484 result->SetHostResource( |
451 instance, | 485 instance, |
452 enter.functions()->CreateGraphics3DRaw(instance, 0, &attribs.front())); | 486 enter.functions()->CreateGraphics3DRaw(instance, 0, &attribs.front())); |
453 } | 487 } |
454 } | 488 } |
455 | 489 |
456 void PPB_Graphics3D_Proxy::OnMsgInitCommandBuffer( | 490 void PPB_Graphics3D_Proxy::OnMsgInitCommandBuffer( |
457 const HostResource& context) { | 491 const HostResource& context, |
| 492 int32 size, |
| 493 base::SharedMemoryHandle* ring_buffer) { |
| 494 *ring_buffer = base::SharedMemory::NULLHandle(); |
458 EnterHostFromHostResource<PPB_Graphics3D_API> enter(context); | 495 EnterHostFromHostResource<PPB_Graphics3D_API> enter(context); |
459 if (enter.failed()) | 496 if (enter.failed()) |
460 return; | 497 return; |
461 | 498 |
462 if (!enter.object()->InitCommandBuffer()) | 499 if (!enter.object()->InitCommandBuffer(size)) |
463 return; | 500 return; |
464 } | |
465 | 501 |
466 void PPB_Graphics3D_Proxy::OnMsgSetGetBuffer( | 502 int shm_handle; |
467 const HostResource& context, | 503 uint32_t shm_size; |
468 int32 transfer_buffer_id) { | 504 if (!enter.object()->GetRingBuffer(&shm_handle, &shm_size)) |
469 EnterHostFromHostResource<PPB_Graphics3D_API> enter(context); | 505 return; |
470 if (enter.succeeded()) | 506 *ring_buffer = TransportSHMHandleFromInt(dispatcher(), shm_handle); |
471 enter.object()->SetGetBuffer(transfer_buffer_id); | |
472 } | 507 } |
473 | 508 |
474 void PPB_Graphics3D_Proxy::OnMsgGetState(const HostResource& context, | 509 void PPB_Graphics3D_Proxy::OnMsgGetState(const HostResource& context, |
475 gpu::CommandBuffer::State* state) { | 510 gpu::CommandBuffer::State* state) { |
476 EnterHostFromHostResource<PPB_Graphics3D_API> enter(context); | 511 EnterHostFromHostResource<PPB_Graphics3D_API> enter(context); |
477 if (enter.failed()) | 512 if (enter.failed()) |
478 return; | 513 return; |
479 PP_Graphics3DTrustedState pp_state = enter.object()->GetState(); | 514 PP_Graphics3DTrustedState pp_state = enter.object()->GetState(); |
480 *state = GPUStateFromPPState(pp_state); | 515 *state = GPUStateFromPPState(pp_state); |
481 } | 516 } |
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
554 void PPB_Graphics3D_Proxy::SendSwapBuffersACKToPlugin( | 589 void PPB_Graphics3D_Proxy::SendSwapBuffersACKToPlugin( |
555 int32_t result, | 590 int32_t result, |
556 const HostResource& context) { | 591 const HostResource& context) { |
557 dispatcher()->Send(new PpapiMsg_PPBGraphics3D_SwapBuffersACK( | 592 dispatcher()->Send(new PpapiMsg_PPBGraphics3D_SwapBuffersACK( |
558 API_ID_PPB_GRAPHICS_3D, context, result)); | 593 API_ID_PPB_GRAPHICS_3D, context, result)); |
559 } | 594 } |
560 | 595 |
561 } // namespace proxy | 596 } // namespace proxy |
562 } // namespace ppapi | 597 } // namespace ppapi |
563 | 598 |
OLD | NEW |