Home | History | Annotate | Download | only in android
      1 // Copyright 2018 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 "base/android/scoped_hardware_buffer_handle.h"
      6 
      7 #include "base/android/android_hardware_buffer_compat.h"
      8 #include "base/logging.h"
      9 #include "base/posix/unix_domain_socket.h"
     10 
     11 namespace base {
     12 namespace android {
     13 
     14 ScopedHardwareBufferHandle::ScopedHardwareBufferHandle() = default;
     15 
     16 ScopedHardwareBufferHandle::ScopedHardwareBufferHandle(
     17     ScopedHardwareBufferHandle&& other) {
     18   *this = std::move(other);
     19 }
     20 
     21 ScopedHardwareBufferHandle::~ScopedHardwareBufferHandle() {
     22   reset();
     23 }
     24 
     25 // static
     26 ScopedHardwareBufferHandle ScopedHardwareBufferHandle::Adopt(
     27     AHardwareBuffer* buffer) {
     28   return ScopedHardwareBufferHandle(buffer);
     29 }
     30 
     31 ScopedHardwareBufferHandle& ScopedHardwareBufferHandle::operator=(
     32     ScopedHardwareBufferHandle&& other) {
     33   reset();
     34   std::swap(buffer_, other.buffer_);
     35   return *this;
     36 }
     37 
     38 bool ScopedHardwareBufferHandle::is_valid() const {
     39   return buffer_ != nullptr;
     40 }
     41 
     42 AHardwareBuffer* ScopedHardwareBufferHandle::get() const {
     43   return buffer_;
     44 }
     45 
     46 void ScopedHardwareBufferHandle::reset() {
     47   if (buffer_) {
     48     AndroidHardwareBufferCompat::GetInstance().Release(buffer_);
     49     buffer_ = nullptr;
     50   }
     51 }
     52 
     53 AHardwareBuffer* ScopedHardwareBufferHandle::Take() {
     54   AHardwareBuffer* buffer = nullptr;
     55   std::swap(buffer, buffer_);
     56   return buffer;
     57 }
     58 
     59 ScopedHardwareBufferHandle ScopedHardwareBufferHandle::Clone() const {
     60   DCHECK(buffer_);
     61   AndroidHardwareBufferCompat::GetInstance().Acquire(buffer_);
     62   return ScopedHardwareBufferHandle(buffer_);
     63 }
     64 
     65 ScopedFD ScopedHardwareBufferHandle::SerializeAsFileDescriptor() const {
     66   DCHECK(is_valid());
     67 
     68   ScopedFD reader, writer;
     69   if (!CreateSocketPair(&reader, &writer)) {
     70     PLOG(ERROR) << "socketpair";
     71     return ScopedFD();
     72   }
     73 
     74   // NOTE: SendHandleToUnixSocket does NOT acquire or retain a reference to the
     75   // buffer object. The caller is therefore responsible for ensuring that the
     76   // buffer remains alive through the lifetime of this file descriptor.
     77   int result =
     78       AndroidHardwareBufferCompat::GetInstance().SendHandleToUnixSocket(
     79           buffer_, writer.get());
     80   if (result < 0) {
     81     PLOG(ERROR) << "send";
     82     return ScopedFD();
     83   }
     84 
     85   return reader;
     86 }
     87 
     88 // static
     89 ScopedHardwareBufferHandle
     90 ScopedHardwareBufferHandle::DeserializeFromFileDescriptor(ScopedFD fd) {
     91   DCHECK(fd.is_valid());
     92   DCHECK(AndroidHardwareBufferCompat::IsSupportAvailable());
     93   AHardwareBuffer* buffer = nullptr;
     94 
     95   // NOTE: Upon success, RecvHandleFromUnixSocket acquires a new reference to
     96   // the AHardwareBuffer.
     97   int result =
     98       AndroidHardwareBufferCompat::GetInstance().RecvHandleFromUnixSocket(
     99           fd.get(), &buffer);
    100   if (result < 0) {
    101     PLOG(ERROR) << "recv";
    102     return ScopedHardwareBufferHandle();
    103   }
    104 
    105   return ScopedHardwareBufferHandle(buffer);
    106 }
    107 
    108 ScopedHardwareBufferHandle::ScopedHardwareBufferHandle(AHardwareBuffer* buffer)
    109     : buffer_(buffer) {
    110   DCHECK(AndroidHardwareBufferCompat::IsSupportAvailable());
    111 }
    112 
    113 }  // namespace android
    114 }  // namespace base
    115