| 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 "ppapi/proxy/ppb_image_data_proxy.h" | 5 #include "ppapi/proxy/ppb_image_data_proxy.h" |
| 6 | 6 |
| 7 #include <string.h> // For memcpy | 7 #include <string.h> // For memcpy |
| 8 | 8 |
| 9 #include <map> | 9 #include <map> |
| 10 #include <vector> | 10 #include <vector> |
| (...skipping 308 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 319 ImageData::ImageData(const HostResource& resource, | 319 ImageData::ImageData(const HostResource& resource, |
| 320 const PP_ImageDataDesc& desc, | 320 const PP_ImageDataDesc& desc, |
| 321 const base::SharedMemoryHandle& handle) | 321 const base::SharedMemoryHandle& handle) |
| 322 : Resource(OBJECT_IS_PROXY, resource), | 322 : Resource(OBJECT_IS_PROXY, resource), |
| 323 desc_(desc), | 323 desc_(desc), |
| 324 shm_(handle, false /* read_only */), | 324 shm_(handle, false /* read_only */), |
| 325 size_(desc.size.width * desc.size.height * 4), | 325 size_(desc.size.width * desc.size.height * 4), |
| 326 map_count_(0), | 326 map_count_(0), |
| 327 used_in_replace_contents_(false) { | 327 used_in_replace_contents_(false) { |
| 328 } | 328 } |
| 329 #endif // !defined(OS_NACL) | 329 #endif // else, !defined(OS_NACL) |
| 330 | 330 |
| 331 ImageData::~ImageData() { | 331 ImageData::~ImageData() { |
| 332 } | 332 } |
| 333 | 333 |
| 334 PPB_ImageData_API* ImageData::AsPPB_ImageData_API() { | 334 PPB_ImageData_API* ImageData::AsPPB_ImageData_API() { |
| 335 return this; | 335 return this; |
| 336 } | 336 } |
| 337 | 337 |
| 338 void ImageData::LastPluginRefWasDeleted() { | 338 void ImageData::LastPluginRefWasDeleted() { |
| 339 // The plugin no longer needs this ImageData, add it to our cache if it's | 339 // The plugin no longer needs this ImageData, add it to our cache if it's |
| (...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 458 format); | 458 format); |
| 459 if (cached_image_data.get()) { | 459 if (cached_image_data.get()) { |
| 460 // We have one we can re-use rather than allocating a new one. | 460 // We have one we can re-use rather than allocating a new one. |
| 461 cached_image_data->RecycleToPlugin(PP_ToBool(init_to_zero)); | 461 cached_image_data->RecycleToPlugin(PP_ToBool(init_to_zero)); |
| 462 return cached_image_data->GetReference(); | 462 return cached_image_data->GetReference(); |
| 463 } | 463 } |
| 464 | 464 |
| 465 HostResource result; | 465 HostResource result; |
| 466 std::string image_data_desc; | 466 std::string image_data_desc; |
| 467 #if defined(OS_NACL) | 467 #if defined(OS_NACL) |
| 468 base::SharedMemoryHandle image_handle = base::SharedMemory::NULLHandle(); | 468 ppapi::proxy::SerializedHandle image_handle_wrapper; |
| 469 dispatcher->Send(new PpapiHostMsg_PPBImageData_CreateNaCl( | 469 dispatcher->Send(new PpapiHostMsg_PPBImageData_CreateNaCl( |
| 470 kApiID, instance, format, size, init_to_zero, | 470 kApiID, instance, format, size, init_to_zero, |
| 471 &result, &image_data_desc, &image_handle)); | 471 &result, &image_data_desc, &image_handle_wrapper)); |
| 472 if (!image_handle_wrapper.is_shmem()) |
| 473 return 0; |
| 474 base::SharedMemoryHandle image_handle = image_handle_wrapper.shmem(); |
| 472 #else | 475 #else |
| 473 ImageHandle image_handle = ImageData::NullHandle(); | 476 ImageHandle image_handle = ImageData::NullHandle(); |
| 474 dispatcher->Send(new PpapiHostMsg_PPBImageData_Create( | 477 dispatcher->Send(new PpapiHostMsg_PPBImageData_Create( |
| 475 kApiID, instance, format, size, init_to_zero, | 478 kApiID, instance, format, size, init_to_zero, |
| 476 &result, &image_data_desc, &image_handle)); | 479 &result, &image_data_desc, &image_handle)); |
| 477 #endif | 480 #endif |
| 478 | 481 |
| 479 if (result.is_null() || image_data_desc.size() != sizeof(PP_ImageDataDesc)) | 482 if (result.is_null() || image_data_desc.size() != sizeof(PP_ImageDataDesc)) |
| 480 return 0; | 483 return 0; |
| 481 | 484 |
| (...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 547 #endif // defined(OS_NACL) | 550 #endif // defined(OS_NACL) |
| 548 } | 551 } |
| 549 | 552 |
| 550 void PPB_ImageData_Proxy::OnHostMsgCreateNaCl( | 553 void PPB_ImageData_Proxy::OnHostMsgCreateNaCl( |
| 551 PP_Instance instance, | 554 PP_Instance instance, |
| 552 int32_t format, | 555 int32_t format, |
| 553 const PP_Size& size, | 556 const PP_Size& size, |
| 554 PP_Bool init_to_zero, | 557 PP_Bool init_to_zero, |
| 555 HostResource* result, | 558 HostResource* result, |
| 556 std::string* image_data_desc, | 559 std::string* image_data_desc, |
| 557 base::SharedMemoryHandle* result_image_handle) { | 560 ppapi::proxy::SerializedHandle* result_image_handle) { |
| 558 #if defined(OS_NACL) | 561 #if defined(OS_NACL) |
| 559 // This message should never be received in untrusted code. To minimize the | 562 // This message should never be received in untrusted code. To minimize the |
| 560 // size of the IRT, we just don't handle it. | 563 // size of the IRT, we just don't handle it. |
| 561 return; | 564 return; |
| 562 #else | 565 #else |
| 563 *result_image_handle = base::SharedMemory::NULLHandle(); | 566 result_image_handle->set_null_shmem(); |
| 564 HostDispatcher* dispatcher = HostDispatcher::GetForInstance(instance); | 567 HostDispatcher* dispatcher = HostDispatcher::GetForInstance(instance); |
| 565 if (!dispatcher) | 568 if (!dispatcher) |
| 566 return; | 569 return; |
| 567 | 570 |
| 568 thunk::EnterResourceCreation enter(instance); | 571 thunk::EnterResourceCreation enter(instance); |
| 569 if (enter.failed()) | 572 if (enter.failed()) |
| 570 return; | 573 return; |
| 571 | 574 |
| 572 PP_Resource resource = enter.functions()->CreateImageDataNaCl( | 575 PP_Resource resource = enter.functions()->CreateImageDataNaCl( |
| 573 instance, static_cast<PP_ImageDataFormat>(format), size, init_to_zero); | 576 instance, static_cast<PP_ImageDataFormat>(format), size, init_to_zero); |
| 574 if (!resource) | 577 if (!resource) |
| 575 return; | 578 return; |
| 576 result->SetHostResource(instance, resource); | 579 result->SetHostResource(instance, resource); |
| 577 | 580 |
| 578 // Get the description, it's just serialized as a string. | 581 // Get the description, it's just serialized as a string. |
| 579 thunk::EnterResourceNoLock<PPB_ImageData_API> enter_resource(resource, false); | 582 thunk::EnterResourceNoLock<PPB_ImageData_API> enter_resource(resource, false); |
| 580 if (enter_resource.failed()) | 583 if (enter_resource.failed()) |
| 581 return; | 584 return; |
| 582 PP_ImageDataDesc desc; | 585 PP_ImageDataDesc desc; |
| 583 if (enter_resource.object()->Describe(&desc) == PP_TRUE) { | 586 if (enter_resource.object()->Describe(&desc) == PP_TRUE) { |
| 584 image_data_desc->resize(sizeof(PP_ImageDataDesc)); | 587 image_data_desc->resize(sizeof(PP_ImageDataDesc)); |
| 585 memcpy(&(*image_data_desc)[0], &desc, sizeof(PP_ImageDataDesc)); | 588 memcpy(&(*image_data_desc)[0], &desc, sizeof(PP_ImageDataDesc)); |
| 586 } | 589 } |
| 587 int local_fd; | 590 int local_fd; |
| 588 uint32_t byte_count; | 591 uint32_t byte_count; |
| 589 if (enter_resource.object()->GetSharedMemory(&local_fd, &byte_count) != PP_OK) | 592 if (enter_resource.object()->GetSharedMemory(&local_fd, &byte_count) != PP_OK) |
| 590 return; | 593 return; |
| 591 | |
| 592 // TODO(dmichael): Change trusted interface to return a PP_FileHandle, those | 594 // TODO(dmichael): Change trusted interface to return a PP_FileHandle, those |
| 593 // casts are ugly. | 595 // casts are ugly. |
| 594 base::PlatformFile platform_file = | 596 base::PlatformFile platform_file = |
| 595 #if defined(OS_WIN) | 597 #if defined(OS_WIN) |
| 596 reinterpret_cast<HANDLE>(static_cast<intptr_t>(local_fd)); | 598 reinterpret_cast<HANDLE>(static_cast<intptr_t>(local_fd)); |
| 597 #elif defined(OS_POSIX) | 599 #elif defined(OS_POSIX) |
| 598 local_fd; | 600 local_fd; |
| 599 #else | 601 #else |
| 600 #error Not implemented. | 602 #error Not implemented. |
| 601 #endif // defined(OS_WIN) | 603 #endif // defined(OS_WIN) |
| 602 *result_image_handle = | 604 result_image_handle->set_shmem( |
| 603 dispatcher->ShareHandleWithRemote(platform_file, false); | 605 dispatcher->ShareHandleWithRemote(platform_file, false), |
| 606 byte_count); |
| 604 #endif // defined(OS_NACL) | 607 #endif // defined(OS_NACL) |
| 605 } | 608 } |
| 606 | 609 |
| 607 void PPB_ImageData_Proxy::OnPluginMsgNotifyUnusedImageData( | 610 void PPB_ImageData_Proxy::OnPluginMsgNotifyUnusedImageData( |
| 608 const HostResource& old_image_data) { | 611 const HostResource& old_image_data) { |
| 609 PluginGlobals* plugin_globals = PluginGlobals::Get(); | 612 PluginGlobals* plugin_globals = PluginGlobals::Get(); |
| 610 if (!plugin_globals) | 613 if (!plugin_globals) |
| 611 return; // This may happen if the plugin is maliciously sending this | 614 return; // This may happen if the plugin is maliciously sending this |
| 612 // message to the renderer. | 615 // message to the renderer. |
| 613 | 616 |
| 614 EnterPluginFromHostResource<PPB_ImageData_API> enter(old_image_data); | 617 EnterPluginFromHostResource<PPB_ImageData_API> enter(old_image_data); |
| 615 if (enter.succeeded()) { | 618 if (enter.succeeded()) { |
| 616 ImageData* image_data = static_cast<ImageData*>(enter.object()); | 619 ImageData* image_data = static_cast<ImageData*>(enter.object()); |
| 617 ImageDataCache::GetInstance()->ImageDataUsable(image_data); | 620 ImageDataCache::GetInstance()->ImageDataUsable(image_data); |
| 618 } | 621 } |
| 619 | 622 |
| 620 // The renderer sent us a reference with the message. If the image data was | 623 // The renderer sent us a reference with the message. If the image data was |
| 621 // still cached in our process, the proxy still holds a reference so we can | 624 // still cached in our process, the proxy still holds a reference so we can |
| 622 // remove the one the renderer just sent is. If the proxy no longer holds a | 625 // remove the one the renderer just sent is. If the proxy no longer holds a |
| 623 // reference, we released everything and we should also release the one the | 626 // reference, we released everything and we should also release the one the |
| 624 // renderer just sent us. | 627 // renderer just sent us. |
| 625 dispatcher()->Send(new PpapiHostMsg_PPBCore_ReleaseResource( | 628 dispatcher()->Send(new PpapiHostMsg_PPBCore_ReleaseResource( |
| 626 API_ID_PPB_CORE, old_image_data)); | 629 API_ID_PPB_CORE, old_image_data)); |
| 627 } | 630 } |
| 628 | 631 |
| 629 } // namespace proxy | 632 } // namespace proxy |
| 630 } // namespace ppapi | 633 } // namespace ppapi |
| OLD | NEW |