diff options
Diffstat (limited to 'mojo/edk/embedder/platform_shared_buffer.cc')
-rw-r--r-- | mojo/edk/embedder/platform_shared_buffer.cc | 325 |
1 files changed, 0 insertions, 325 deletions
diff --git a/mojo/edk/embedder/platform_shared_buffer.cc b/mojo/edk/embedder/platform_shared_buffer.cc deleted file mode 100644 index 58af44d..0000000 --- a/mojo/edk/embedder/platform_shared_buffer.cc +++ /dev/null @@ -1,325 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "mojo/edk/embedder/platform_shared_buffer.h" - -#include <stddef.h> - -#include <utility> - -#include "base/logging.h" -#include "base/memory/ptr_util.h" -#include "base/memory/shared_memory.h" -#include "base/process/process_handle.h" -#include "base/sys_info.h" -#include "mojo/edk/embedder/platform_handle_utils.h" - -#if defined(OS_NACL) -// For getpagesize() on NaCl. -#include <unistd.h> -#endif - -namespace mojo { -namespace edk { - -namespace { - -// Takes ownership of |memory_handle|. -ScopedPlatformHandle SharedMemoryToPlatformHandle( - base::SharedMemoryHandle memory_handle) { -#if defined(OS_POSIX) && !(defined(OS_MACOSX) && !defined(OS_IOS)) - return ScopedPlatformHandle(PlatformHandle(memory_handle.fd)); -#elif defined(OS_WIN) - return ScopedPlatformHandle(PlatformHandle(memory_handle.GetHandle())); -#else - return ScopedPlatformHandle(PlatformHandle(memory_handle.GetMemoryObject())); -#endif -} - -} // namespace - -// static -PlatformSharedBuffer* PlatformSharedBuffer::Create(size_t num_bytes) { - DCHECK_GT(num_bytes, 0u); - - PlatformSharedBuffer* rv = new PlatformSharedBuffer(num_bytes, false); - if (!rv->Init()) { - // We can't just delete it directly, due to the "in destructor" (debug) - // check. - scoped_refptr<PlatformSharedBuffer> deleter(rv); - return nullptr; - } - - return rv; -} - -// static -PlatformSharedBuffer* PlatformSharedBuffer::CreateFromPlatformHandle( - size_t num_bytes, - bool read_only, - ScopedPlatformHandle platform_handle) { - DCHECK_GT(num_bytes, 0u); - - PlatformSharedBuffer* rv = new PlatformSharedBuffer(num_bytes, read_only); - if (!rv->InitFromPlatformHandle(std::move(platform_handle))) { - // We can't just delete it directly, due to the "in destructor" (debug) - // check. - scoped_refptr<PlatformSharedBuffer> deleter(rv); - return nullptr; - } - - return rv; -} - -// static -PlatformSharedBuffer* PlatformSharedBuffer::CreateFromPlatformHandlePair( - size_t num_bytes, - ScopedPlatformHandle rw_platform_handle, - ScopedPlatformHandle ro_platform_handle) { - DCHECK_GT(num_bytes, 0u); - DCHECK(rw_platform_handle.is_valid()); - DCHECK(ro_platform_handle.is_valid()); - - PlatformSharedBuffer* rv = new PlatformSharedBuffer(num_bytes, false); - if (!rv->InitFromPlatformHandlePair(std::move(rw_platform_handle), - std::move(ro_platform_handle))) { - // We can't just delete it directly, due to the "in destructor" (debug) - // check. - scoped_refptr<PlatformSharedBuffer> deleter(rv); - return nullptr; - } - - return rv; -} - -// static -PlatformSharedBuffer* PlatformSharedBuffer::CreateFromSharedMemoryHandle( - size_t num_bytes, - bool read_only, - base::SharedMemoryHandle handle) { - DCHECK_GT(num_bytes, 0u); - - PlatformSharedBuffer* rv = new PlatformSharedBuffer(num_bytes, read_only); - rv->InitFromSharedMemoryHandle(handle); - - return rv; -} - -size_t PlatformSharedBuffer::GetNumBytes() const { - return num_bytes_; -} - -bool PlatformSharedBuffer::IsReadOnly() const { - return read_only_; -} - -std::unique_ptr<PlatformSharedBufferMapping> PlatformSharedBuffer::Map( - size_t offset, - size_t length) { - if (!IsValidMap(offset, length)) - return nullptr; - - return MapNoCheck(offset, length); -} - -bool PlatformSharedBuffer::IsValidMap(size_t offset, size_t length) { - if (offset > num_bytes_ || length == 0) - return false; - - // Note: This is an overflow-safe check of |offset + length > num_bytes_| - // (that |num_bytes >= offset| is verified above). - if (length > num_bytes_ - offset) - return false; - - return true; -} - -std::unique_ptr<PlatformSharedBufferMapping> PlatformSharedBuffer::MapNoCheck( - size_t offset, - size_t length) { - DCHECK(IsValidMap(offset, length)); - DCHECK(shared_memory_); - base::SharedMemoryHandle handle; - { - base::AutoLock locker(lock_); - handle = base::SharedMemory::DuplicateHandle(shared_memory_->handle()); - } - if (handle == base::SharedMemory::NULLHandle()) - return nullptr; - - std::unique_ptr<PlatformSharedBufferMapping> mapping( - new PlatformSharedBufferMapping(handle, read_only_, offset, length)); - if (mapping->Map()) - return base::WrapUnique(mapping.release()); - - return nullptr; -} - -ScopedPlatformHandle PlatformSharedBuffer::DuplicatePlatformHandle() { - DCHECK(shared_memory_); - base::SharedMemoryHandle handle; - { - base::AutoLock locker(lock_); - handle = base::SharedMemory::DuplicateHandle(shared_memory_->handle()); - } - if (handle == base::SharedMemory::NULLHandle()) - return ScopedPlatformHandle(); - - return SharedMemoryToPlatformHandle(handle); -} - -ScopedPlatformHandle PlatformSharedBuffer::PassPlatformHandle() { - DCHECK(HasOneRef()); - - // The only way to pass a handle from base::SharedMemory is to duplicate it - // and close the original. - ScopedPlatformHandle handle = DuplicatePlatformHandle(); - - base::AutoLock locker(lock_); - shared_memory_->Close(); - return handle; -} - -base::SharedMemoryHandle PlatformSharedBuffer::DuplicateSharedMemoryHandle() { - DCHECK(shared_memory_); - - base::AutoLock locker(lock_); - return base::SharedMemory::DuplicateHandle(shared_memory_->handle()); -} - -PlatformSharedBuffer* PlatformSharedBuffer::CreateReadOnlyDuplicate() { - DCHECK(shared_memory_); - - if (ro_shared_memory_) { - base::AutoLock locker(lock_); - base::SharedMemoryHandle handle; - handle = base::SharedMemory::DuplicateHandle(ro_shared_memory_->handle()); - if (handle == base::SharedMemory::NULLHandle()) - return nullptr; - return CreateFromSharedMemoryHandle(num_bytes_, true, handle); - } - - base::SharedMemoryHandle handle; - bool success; - { - base::AutoLock locker(lock_); - success = shared_memory_->ShareReadOnlyToProcess( - base::GetCurrentProcessHandle(), &handle); - } - if (!success || handle == base::SharedMemory::NULLHandle()) - return nullptr; - - return CreateFromSharedMemoryHandle(num_bytes_, true, handle); -} - -PlatformSharedBuffer::PlatformSharedBuffer(size_t num_bytes, bool read_only) - : num_bytes_(num_bytes), read_only_(read_only) {} - -PlatformSharedBuffer::~PlatformSharedBuffer() {} - -bool PlatformSharedBuffer::Init() { - DCHECK(!shared_memory_); - DCHECK(!read_only_); - - base::SharedMemoryCreateOptions options; - options.size = num_bytes_; - // By default, we can share as read-only. - options.share_read_only = true; - - shared_memory_.reset(new base::SharedMemory); - return shared_memory_->Create(options); -} - -bool PlatformSharedBuffer::InitFromPlatformHandle( - ScopedPlatformHandle platform_handle) { - DCHECK(!shared_memory_); - -#if defined(OS_WIN) - base::SharedMemoryHandle handle(platform_handle.release().handle, - base::GetCurrentProcId()); -#elif defined(OS_MACOSX) && !defined(OS_IOS) - base::SharedMemoryHandle handle; - handle = base::SharedMemoryHandle(platform_handle.release().port, num_bytes_, - base::GetCurrentProcId()); -#else - base::SharedMemoryHandle handle(platform_handle.release().handle, false); -#endif - - shared_memory_.reset(new base::SharedMemory(handle, read_only_)); - return true; -} - -bool PlatformSharedBuffer::InitFromPlatformHandlePair( - ScopedPlatformHandle rw_platform_handle, - ScopedPlatformHandle ro_platform_handle) { -#if defined(OS_MACOSX) - NOTREACHED(); - return false; -#else // defined(OS_MACOSX) - -#if defined(OS_WIN) - base::SharedMemoryHandle handle(rw_platform_handle.release().handle, - base::GetCurrentProcId()); - base::SharedMemoryHandle ro_handle(ro_platform_handle.release().handle, - base::GetCurrentProcId()); -#else // defined(OS_WIN) - base::SharedMemoryHandle handle(rw_platform_handle.release().handle, false); - base::SharedMemoryHandle ro_handle(ro_platform_handle.release().handle, - false); -#endif // defined(OS_WIN) - - DCHECK(!shared_memory_); - shared_memory_.reset(new base::SharedMemory(handle, false)); - ro_shared_memory_.reset(new base::SharedMemory(ro_handle, true)); - return true; - -#endif // defined(OS_MACOSX) -} - -void PlatformSharedBuffer::InitFromSharedMemoryHandle( - base::SharedMemoryHandle handle) { - DCHECK(!shared_memory_); - - shared_memory_.reset(new base::SharedMemory(handle, read_only_)); -} - -PlatformSharedBufferMapping::~PlatformSharedBufferMapping() { - Unmap(); -} - -void* PlatformSharedBufferMapping::GetBase() const { - return base_; -} - -size_t PlatformSharedBufferMapping::GetLength() const { - return length_; -} - -bool PlatformSharedBufferMapping::Map() { - // Mojo shared buffers can be mapped at any offset. However, - // base::SharedMemory must be mapped at a page boundary. So calculate what the - // nearest whole page offset is, and build a mapping that's offset from that. -#if defined(OS_NACL) - // base::SysInfo isn't available under NaCl. - size_t page_size = getpagesize(); -#else - size_t page_size = base::SysInfo::VMAllocationGranularity(); -#endif - size_t offset_rounding = offset_ % page_size; - size_t real_offset = offset_ - offset_rounding; - size_t real_length = length_ + offset_rounding; - - if (!shared_memory_.MapAt(static_cast<off_t>(real_offset), real_length)) - return false; - - base_ = static_cast<char*>(shared_memory_.memory()) + offset_rounding; - return true; -} - -void PlatformSharedBufferMapping::Unmap() { - shared_memory_.Unmap(); -} - -} // namespace edk -} // namespace mojo |