Home | History | Annotate | Download | only in system
      1 // Copyright 2014 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 "mojo/edk/system/platform_handle_dispatcher.h"
      6 
      7 #include "base/synchronization/lock.h"
      8 #include "mojo/edk/embedder/platform_handle_vector.h"
      9 
     10 namespace mojo {
     11 namespace edk {
     12 
     13 // static
     14 scoped_refptr<PlatformHandleDispatcher> PlatformHandleDispatcher::Create(
     15     ScopedPlatformHandle platform_handle) {
     16   return new PlatformHandleDispatcher(std::move(platform_handle));
     17 }
     18 
     19 ScopedPlatformHandle PlatformHandleDispatcher::PassPlatformHandle() {
     20   return std::move(platform_handle_);
     21 }
     22 
     23 Dispatcher::Type PlatformHandleDispatcher::GetType() const {
     24   return Type::PLATFORM_HANDLE;
     25 }
     26 
     27 MojoResult PlatformHandleDispatcher::Close() {
     28   base::AutoLock lock(lock_);
     29   if (is_closed_ || in_transit_)
     30     return MOJO_RESULT_INVALID_ARGUMENT;
     31   is_closed_ = true;
     32   platform_handle_.reset();
     33   return MOJO_RESULT_OK;
     34 }
     35 
     36 void PlatformHandleDispatcher::StartSerialize(uint32_t* num_bytes,
     37                                               uint32_t* num_ports,
     38                                               uint32_t* num_handles) {
     39   *num_bytes = 0;
     40   *num_ports = 0;
     41   *num_handles = 1;
     42 }
     43 
     44 bool PlatformHandleDispatcher::EndSerialize(void* destination,
     45                                             ports::PortName* ports,
     46                                             PlatformHandle* handles) {
     47   base::AutoLock lock(lock_);
     48   if (is_closed_)
     49     return false;
     50   handles[0] = platform_handle_.get();
     51   return true;
     52 }
     53 
     54 bool PlatformHandleDispatcher::BeginTransit() {
     55   base::AutoLock lock(lock_);
     56   if (in_transit_)
     57     return false;
     58   in_transit_ = !is_closed_;
     59   return in_transit_;
     60 }
     61 
     62 void PlatformHandleDispatcher::CompleteTransitAndClose() {
     63   base::AutoLock lock(lock_);
     64 
     65   in_transit_ = false;
     66   is_closed_ = true;
     67 
     68   // The system has taken ownership of our handle.
     69   ignore_result(platform_handle_.release());
     70 }
     71 
     72 void PlatformHandleDispatcher::CancelTransit() {
     73   base::AutoLock lock(lock_);
     74   in_transit_ = false;
     75 }
     76 
     77 // static
     78 scoped_refptr<PlatformHandleDispatcher> PlatformHandleDispatcher::Deserialize(
     79     const void* bytes,
     80     size_t num_bytes,
     81     const ports::PortName* ports,
     82     size_t num_ports,
     83     PlatformHandle* handles,
     84     size_t num_handles) {
     85   if (num_bytes || num_ports || num_handles != 1)
     86     return nullptr;
     87 
     88   PlatformHandle handle;
     89   std::swap(handle, handles[0]);
     90 
     91   return PlatformHandleDispatcher::Create(ScopedPlatformHandle(handle));
     92 }
     93 
     94 PlatformHandleDispatcher::PlatformHandleDispatcher(
     95     ScopedPlatformHandle platform_handle)
     96     : platform_handle_(std::move(platform_handle)) {}
     97 
     98 PlatformHandleDispatcher::~PlatformHandleDispatcher() {
     99   DCHECK(is_closed_ && !in_transit_);
    100   DCHECK(!platform_handle_.is_valid());
    101 }
    102 
    103 }  // namespace edk
    104 }  // namespace mojo
    105