Merge "Make prior{Linear/Graphic}Allocation own handle" into pi-dev
diff --git a/media/libstagefright/codec2/include/C2Buffer.h b/media/libstagefright/codec2/include/C2Buffer.h
index 4bdd20f..0e35f11 100644
--- a/media/libstagefright/codec2/include/C2Buffer.h
+++ b/media/libstagefright/codec2/include/C2Buffer.h
@@ -655,7 +655,8 @@
      * (Re)creates a 1D allocation from a native |handle|. If successful, the allocation is stored
      * in |allocation|. Otherwise, |allocation| is set to 'nullptr'.
      *
-     * \param handle      the handle for the existing allocation
+     * \param handle      the handle for the existing allocation. On success, the allocation will
+     *                    take ownership of |handle|.
      * \param allocation  pointer to where the allocation shall be stored on success. nullptr
      *                    will be stored here on failure
      *
@@ -712,7 +713,8 @@
      * (Re)creates a 2D allocation from a native handle.  If successful, the allocation is stored
      * in |allocation|. Otherwise, |allocation| is set to 'nullptr'.
      *
-     * \param handle      the handle for the existing allocation
+     * \param handle      the handle for the existing allocation. On success, the allocation will
+     *                    take ownership of |handle|.
      * \param allocation  pointer to where the allocation shall be stored on success. nullptr
      *                    will be stored here on failure
      *
diff --git a/media/libstagefright/codec2/vndk/C2AllocatorGralloc.cpp b/media/libstagefright/codec2/vndk/C2AllocatorGralloc.cpp
index a90e094..96b52a1 100644
--- a/media/libstagefright/codec2/vndk/C2AllocatorGralloc.cpp
+++ b/media/libstagefright/codec2/vndk/C2AllocatorGralloc.cpp
@@ -255,6 +255,7 @@
       mHidlHandle(std::move(hidlHandle)),
       mHandle(handle),
       mBuffer(nullptr),
+      mLockedHandle(nullptr),
       mLocked(false),
       mAllocatorId(allocatorId) {
 }
@@ -269,6 +270,8 @@
         unmap(addr, C2Rect(), nullptr);
     }
     mMapper->freeBuffer(const_cast<native_handle_t *>(mBuffer));
+    native_handle_delete(const_cast<native_handle_t*>(
+            reinterpret_cast<const native_handle_t*>(mHandle)));
 }
 
 c2_status_t C2AllocationGralloc::map(
@@ -608,8 +611,8 @@
         return C2_BAD_VALUE;
     }
 
-    hidl_handle hidlHandle = C2HandleGralloc::UnwrapNativeHandle(grallocHandle);
-
+    hidl_handle hidlHandle;
+    hidlHandle.setTo(C2HandleGralloc::UnwrapNativeHandle(grallocHandle), true);
     allocation->reset(new C2AllocationGralloc(info, mMapper, hidlHandle, grallocHandle, mTraits->id));
     return C2_OK;
 }
diff --git a/media/libstagefright/codec2/vndk/C2AllocatorIon.cpp b/media/libstagefright/codec2/vndk/C2AllocatorIon.cpp
index 664c09e..c5fb8d9 100644
--- a/media/libstagefright/codec2/vndk/C2AllocatorIon.cpp
+++ b/media/libstagefright/codec2/vndk/C2AllocatorIon.cpp
@@ -150,7 +150,6 @@
      * so that we can capture the error.
      *
      * \param ionFd     ion client (ownership transferred to created object)
-     * \param owned     whehter native_handle_t is owned by an allocation or not.
      * \param capacity  size of allocation
      * \param bufferFd  buffer handle (ownership transferred to created object). Must be
      *                  invalid if err is not 0.
@@ -158,9 +157,8 @@
      *                  invalid if err is not 0.
      * \param err       errno during buffer allocation or import
      */
-    Impl(int ionFd, bool owned, size_t capacity, int bufferFd, ion_user_handle_t buffer, C2Allocator::id_t id, int err)
+    Impl(int ionFd, size_t capacity, int bufferFd, ion_user_handle_t buffer, C2Allocator::id_t id, int err)
         : mIonFd(ionFd),
-          mHandleOwned(owned),
           mHandle(bufferFd, capacity),
           mBuffer(buffer),
           mId(id),
@@ -191,7 +189,7 @@
     static Impl *Import(int ionFd, size_t capacity, int bufferFd, C2Allocator::id_t id) {
         ion_user_handle_t buffer = -1;
         int ret = ion_import(ionFd, bufferFd, &buffer);
-        return new Impl(ionFd, false, capacity, bufferFd, buffer, id, ret);
+        return new Impl(ionFd, capacity, bufferFd, buffer, id, ret);
     }
 
     /**
@@ -218,7 +216,7 @@
                 buffer = -1;
             }
         }
-        return new Impl(ionFd, true, size, bufferFd, buffer, id, ret);
+        return new Impl(ionFd, size, bufferFd, buffer, id, ret);
     }
 
     c2_status_t map(size_t offset, size_t size, C2MemoryUsage usage, C2Fence *fence, void **addr) {
@@ -311,13 +309,11 @@
         }
         if (mInit == C2_OK) {
             (void)ion_free(mIonFd, mBuffer);
+            native_handle_close(&mHandle);
         }
         if (mIonFd >= 0) {
             close(mIonFd);
         }
-        if (mHandleOwned) {
-            native_handle_close(&mHandle);
-        }
     }
 
     c2_status_t status() const {
@@ -338,7 +334,6 @@
 
 private:
     int mIonFd;
-    bool mHandleOwned;
     C2HandleIon mHandle;
     ion_user_handle_t mBuffer;
     C2Allocator::id_t mId;
@@ -481,6 +476,8 @@
     c2_status_t ret = alloc->status();
     if (ret == C2_OK) {
         *allocation = alloc;
+        native_handle_delete(const_cast<native_handle_t*>(
+                reinterpret_cast<const native_handle_t*>(handle)));
     }
     return ret;
 }
diff --git a/media/libstagefright/codec2/vndk/bufferpool/BufferPoolClient.cpp b/media/libstagefright/codec2/vndk/bufferpool/BufferPoolClient.cpp
index 7cb4ba9..dda8e39 100644
--- a/media/libstagefright/codec2/vndk/bufferpool/BufferPoolClient.cpp
+++ b/media/libstagefright/codec2/vndk/bufferpool/BufferPoolClient.cpp
@@ -135,7 +135,8 @@
     bool mInvalidated; // TODO: implement
     int64_t mExpireUs;
     bool mHasCache;
-    _C2BlockPoolData mBuffer;
+    BufferId mId;
+    native_handle_t *mHandle;
     std::weak_ptr<_C2BlockPoolData> mCache;
 
     void updateExpire() {
@@ -144,11 +145,18 @@
 
 public:
     ClientBuffer(BufferId id, native_handle_t *handle)
-            : mInvalidated(false), mHasCache(false), mBuffer(id, handle) {
+            : mInvalidated(false), mHasCache(false), mId(id), mHandle(handle) {
         (void)mInvalidated;
         mExpireUs = getTimestampNow() + kCacheTtlUs;
     }
 
+    ~ClientBuffer() {
+        if (mHandle) {
+            native_handle_close(mHandle);
+            native_handle_delete(mHandle);
+        }
+    }
+
     bool expire() const {
         int64_t now = getTimestampNow();
         return now >= mExpireUs;
@@ -175,7 +183,7 @@
             // Allocates a raw ptr in order to avoid sending #postBufferRelease
             // from deleter, in case of native_handle_clone failure.
             _C2BlockPoolData *ptr = new _C2BlockPoolData(
-                    mBuffer.mId, native_handle_clone(mBuffer.mHandle));
+                    mId, native_handle_clone(mHandle));
             if (ptr && ptr->mHandle != NULL) {
                 std::shared_ptr<_C2BlockPoolData>
                         cache(ptr, BlockPoolDataDtor(impl));
diff --git a/media/libstagefright/codec2/vndk/bufferpool/include/BufferPoolTypes.h b/media/libstagefright/codec2/vndk/bufferpool/include/BufferPoolTypes.h
index 0cf023c..7f4223c 100644
--- a/media/libstagefright/codec2/vndk/bufferpool/include/BufferPoolTypes.h
+++ b/media/libstagefright/codec2/vndk/bufferpool/include/BufferPoolTypes.h
@@ -25,6 +25,7 @@
 
 struct __attribute__((visibility("hidden"))) _C2BlockPoolData {
     uint32_t mId; //BufferId
+    // Handle should be copied to somewhere else, and should be managed there.
     native_handle_t *mHandle;
 
     _C2BlockPoolData() : mId(0), mHandle(NULL) {}
@@ -33,10 +34,6 @@
             : mId(id), mHandle(handle) {}
 
     ~_C2BlockPoolData() {
-        if (mHandle != NULL) {
-            native_handle_close(mHandle);
-            native_handle_delete(mHandle);
-        }
     }
 };