Report data from aaudio mmap path to audio flinger.

Report data from aaudio mmap path to audio flinger for sound dose
computation. A shared memory is allocated for read and write counter.
The client will shared the write counter with the aaudio service. The
command thread will wake up every 5 burst time to report the data to
audio flinger.

Test: atest AAudioTests
Test: test_marshalling
Test: dump wav file in audio flinger and play
Bug: 264254430
Change-Id: Ib732442c5afc9169fe891212cf77b458c41a87f1
diff --git a/media/libaaudio/src/binding/AudioEndpointParcelable.cpp b/media/libaaudio/src/binding/AudioEndpointParcelable.cpp
index b1262df..d15d2fa 100644
--- a/media/libaaudio/src/binding/AudioEndpointParcelable.cpp
+++ b/media/libaaudio/src/binding/AudioEndpointParcelable.cpp
@@ -18,6 +18,7 @@
 //#define LOG_NDEBUG 0
 #include <utils/Log.h>
 
+#include <map>
 #include <stdint.h>
 
 #include <binder/Parcel.h>
@@ -37,8 +38,7 @@
         : mUpMessageQueueParcelable(parcelable.upMessageQueueParcelable),
           mDownMessageQueueParcelable(parcelable.downMessageQueueParcelable),
           mUpDataQueueParcelable(parcelable.upDataQueueParcelable),
-          mDownDataQueueParcelable(parcelable.downDataQueueParcelable),
-          mNumSharedMemories(parcelable.sharedMemories.size()) {
+          mDownDataQueueParcelable(parcelable.downDataQueueParcelable) {
     for (size_t i = 0; i < parcelable.sharedMemories.size() && i < MAX_SHARED_MEMORIES; ++i) {
         // Re-construct.
         mSharedMemories[i].~SharedMemoryParcelable();
@@ -52,15 +52,48 @@
     return *this;
 }
 
+namespace {
+
+void updateSharedMemoryIndex(SharedRegion* sharedRegion, int oldIndex, int newIndex) {
+    if (sharedRegion->sharedMemoryIndex == oldIndex) {
+        sharedRegion->sharedMemoryIndex = newIndex;
+    }
+}
+
+void updateSharedMemoryIndex(RingBuffer* ringBuffer, int oldIndex, int newIndex) {
+    updateSharedMemoryIndex(&ringBuffer->readCounterParcelable, oldIndex, newIndex);
+    updateSharedMemoryIndex(&ringBuffer->writeCounterParcelable, oldIndex, newIndex);
+    updateSharedMemoryIndex(&ringBuffer->dataParcelable, oldIndex, newIndex);
+}
+
+void updateSharedMemoryIndex(Endpoint* endpoint, int oldIndex, int newIndex) {
+    updateSharedMemoryIndex(&endpoint->upMessageQueueParcelable, oldIndex, newIndex);
+    updateSharedMemoryIndex(&endpoint->downMessageQueueParcelable, oldIndex, newIndex);
+    updateSharedMemoryIndex(&endpoint->upDataQueueParcelable, oldIndex, newIndex);
+    updateSharedMemoryIndex(&endpoint->downDataQueueParcelable, oldIndex, newIndex);
+}
+
+} // namespace
+
 Endpoint AudioEndpointParcelable::parcelable()&& {
     Endpoint result;
     result.upMessageQueueParcelable = mUpMessageQueueParcelable.parcelable();
     result.downMessageQueueParcelable = mDownMessageQueueParcelable.parcelable();
     result.upDataQueueParcelable = mUpDataQueueParcelable.parcelable();
     result.downDataQueueParcelable = mDownDataQueueParcelable.parcelable();
-    result.sharedMemories.reserve(std::min(mNumSharedMemories, MAX_SHARED_MEMORIES));
-    for (size_t i = 0; i < mNumSharedMemories && i < MAX_SHARED_MEMORIES; ++i) {
-        result.sharedMemories.emplace_back(std::move(mSharedMemories[i]).parcelable());
+    // To transfer through binder, only valid/in-use shared memory is allowed. By design, the
+    // shared memories that are currently in-use may not be placed continuously from position 0.
+    // However, when marshalling the shared memories into Endpoint, the shared memories will be
+    // re-indexed from 0. In that case, when placing a shared memory, it is needed to update the
+    // corresponding cached indexes.
+    for (int i = 0; i < MAX_SHARED_MEMORIES; ++i) {
+        if (mSharedMemories[i].isInUse()) {
+            const int index = result.sharedMemories.size();
+            result.sharedMemories.emplace_back(std::move(mSharedMemories[i]).parcelable());
+            // Updating all the SharedRegion that is using `i` as shared memory index with the
+            // new shared memory index as `result.sharedMemories.size() - 1`.
+            updateSharedMemoryIndex(&result, i, index);
+        }
     }
     return result;
 }
@@ -71,28 +104,50 @@
  */
 int32_t AudioEndpointParcelable::addFileDescriptor(const unique_fd& fd,
                                                    int32_t sizeInBytes) {
-    if (mNumSharedMemories >= MAX_SHARED_MEMORIES) {
+    const int32_t index = getNextAvailableSharedMemoryPosition();
+    if (index < 0) {
         return AAUDIO_ERROR_OUT_OF_RANGE;
     }
-    int32_t index = mNumSharedMemories++;
     mSharedMemories[index].setup(fd, sizeInBytes);
     return index;
 }
 
 void AudioEndpointParcelable::closeDataFileDescriptor() {
-    const int32_t curDataMemoryIndex = mDownDataQueueParcelable.getSharedMemoryIndex();
-    mSharedMemories[curDataMemoryIndex].closeAndReleaseFd();
+    for (const int32_t memoryIndex : std::set{mDownDataQueueParcelable.getDataSharedMemoryIndex(),
+                                mDownDataQueueParcelable.getReadCounterSharedMemoryIndex(),
+                                mDownDataQueueParcelable.getWriteCounterSharedMemoryIndex()}) {
+        mSharedMemories[memoryIndex].closeAndReleaseFd();
+    }
 }
 
-void AudioEndpointParcelable::updateDataFileDescriptor(
+aaudio_result_t AudioEndpointParcelable::updateDataFileDescriptor(
         AudioEndpointParcelable* endpointParcelable) {
-    const int32_t curDataMemoryIndex = mDownDataQueueParcelable.getSharedMemoryIndex();
-    const int32_t newDataMemoryIndex =
-            endpointParcelable->mDownDataQueueParcelable.getSharedMemoryIndex();
-    mSharedMemories[curDataMemoryIndex].close();
-    mSharedMemories[curDataMemoryIndex].setup(
-            endpointParcelable->mSharedMemories[newDataMemoryIndex]);
-    mDownDataQueueParcelable.updateMemory(endpointParcelable->mDownDataQueueParcelable);
+    // Before updating data file descriptor, close the old shared memories.
+    closeDataFileDescriptor();
+    // The given endpoint parcelable and this one are two different objects, the indexes in
+    // `mSharedMemories` for `mDownDataQueueParcelable` can be different. In that case, an index
+    // map, which maps from the index in given endpoint parcelable to the index in this endpoint
+    // parcelable, is required when updating shared memory.
+    std::map<int32_t, int32_t> memoryIndexMap;
+    auto& downDataQueueParcelable = endpointParcelable->mDownDataQueueParcelable;
+    for (const int32_t memoryIndex : {downDataQueueParcelable.getDataSharedMemoryIndex(),
+                                      downDataQueueParcelable.getReadCounterSharedMemoryIndex(),
+                                      downDataQueueParcelable.getWriteCounterSharedMemoryIndex()}) {
+        if (memoryIndexMap.find(memoryIndex) != memoryIndexMap.end()) {
+            // This shared memory has been set up in this endpoint parcelable.
+            continue;
+        }
+        // Set up the memory in the next available shared memory position.
+        const int index = getNextAvailableSharedMemoryPosition();
+        if (index < 0) {
+            return AAUDIO_ERROR_OUT_OF_RANGE;
+        }
+        mSharedMemories[index].setup(endpointParcelable->mSharedMemories[memoryIndex]);
+        memoryIndexMap.emplace(memoryIndex, index);
+    }
+    mDownDataQueueParcelable.updateMemory(
+            endpointParcelable->mDownDataQueueParcelable, memoryIndexMap);
+    return AAUDIO_OK;
 }
 
 aaudio_result_t AudioEndpointParcelable::resolve(EndpointDescriptor *descriptor) {
@@ -114,26 +169,29 @@
 
 aaudio_result_t AudioEndpointParcelable::close() {
     int err = 0;
-    for (int i = 0; i < mNumSharedMemories; i++) {
-        int lastErr = mSharedMemories[i].close();
+    for (auto& sharedMemory : mSharedMemories) {
+        const int lastErr = sharedMemory.close();
         if (lastErr < 0) err = lastErr;
     }
     return AAudioConvert_androidToAAudioResult(err);
 }
 
-aaudio_result_t AudioEndpointParcelable::validate() const {
-    if (mNumSharedMemories < 0 || mNumSharedMemories >= MAX_SHARED_MEMORIES) {
-        ALOGE("invalid mNumSharedMemories = %d", mNumSharedMemories);
-        return AAUDIO_ERROR_INTERNAL;
+int32_t AudioEndpointParcelable::getNextAvailableSharedMemoryPosition() const {
+    for (int i = 0; i < MAX_SHARED_MEMORIES; ++i) {
+        if (!mSharedMemories[i].isInUse()) {
+            return i;
+        }
     }
-    return AAUDIO_OK;
+    return -1;
 }
 
 void AudioEndpointParcelable::dump() {
     ALOGD("======================================= BEGIN");
-    ALOGD("mNumSharedMemories = %d", mNumSharedMemories);
-    for (int i = 0; i < mNumSharedMemories; i++) {
-        mSharedMemories[i].dump();
+    for (int i = 0; i < MAX_SHARED_MEMORIES; ++i) {
+        if (mSharedMemories[i].isInUse()) {
+            ALOGD("Shared memory index=%d", i);
+            mSharedMemories[i].dump();
+        }
     }
     ALOGD("mUpMessageQueueParcelable =========");
     mUpMessageQueueParcelable.dump();
diff --git a/media/libaaudio/src/binding/AudioEndpointParcelable.h b/media/libaaudio/src/binding/AudioEndpointParcelable.h
index 5d2c38f..722dd14 100644
--- a/media/libaaudio/src/binding/AudioEndpointParcelable.h
+++ b/media/libaaudio/src/binding/AudioEndpointParcelable.h
@@ -61,8 +61,10 @@
      * Update current data file descriptor with given endpoint parcelable.
      * @param endpointParcelable an endpoint parcelable that contains new data file
      *                           descriptor information
+     * @return AAUDIO_OK if the data file descriptor updates successfully.
+     *         AAUDIO_ERROR_OUT_OF_RANGE if there is not enough space for the shared memory.
      */
-    void updateDataFileDescriptor(AudioEndpointParcelable* endpointParcelable);
+    aaudio_result_t updateDataFileDescriptor(AudioEndpointParcelable* endpointParcelable);
 
     aaudio_result_t resolve(EndpointDescriptor *descriptor);
     aaudio_result_t resolveDataQueue(RingBufferDescriptor *descriptor);
@@ -84,9 +86,10 @@
     RingBufferParcelable    mDownDataQueueParcelable;    // eg. playback
 
 private:
-    aaudio_result_t         validate() const;
+    // Return the first available shared memory position. Return -1 if all shared memories are
+    // in use.
+    int32_t getNextAvailableSharedMemoryPosition() const;
 
-    int32_t                 mNumSharedMemories = 0;
     SharedMemoryParcelable  mSharedMemories[MAX_SHARED_MEMORIES];
 };
 
diff --git a/media/libaaudio/src/binding/RingBufferParcelable.cpp b/media/libaaudio/src/binding/RingBufferParcelable.cpp
index 3bc51d0..f8d748e 100644
--- a/media/libaaudio/src/binding/RingBufferParcelable.cpp
+++ b/media/libaaudio/src/binding/RingBufferParcelable.cpp
@@ -33,7 +33,6 @@
         : mReadCounterParcelable(parcelable.readCounterParcelable),
           mWriteCounterParcelable(parcelable.writeCounterParcelable),
           mDataParcelable(parcelable.dataParcelable),
-          mSharedMemoryIndex(parcelable.sharedMemoryIndex),
           mBytesPerFrame(parcelable.bytesPerFrame),
           mFramesPerBurst(parcelable.framesPerBurst),
           mCapacityInFrames(parcelable.capacityInFrames),
@@ -46,7 +45,6 @@
     result.readCounterParcelable = mReadCounterParcelable.parcelable();
     result.writeCounterParcelable = mWriteCounterParcelable.parcelable();
     result.dataParcelable = mDataParcelable.parcelable();
-    result.sharedMemoryIndex = mSharedMemoryIndex;
     result.bytesPerFrame = mBytesPerFrame;
     result.framesPerBurst = mFramesPerBurst;
     result.capacityInFrames = mCapacityInFrames;
@@ -62,19 +60,26 @@
                  int32_t readCounterOffset,
                  int32_t writeCounterOffset,
                  int32_t counterSizeBytes) {
-    mSharedMemoryIndex = sharedMemoryIndex;
-    mReadCounterParcelable.setup(sharedMemoryIndex, readCounterOffset, counterSizeBytes);
-    mWriteCounterParcelable.setup(sharedMemoryIndex, writeCounterOffset, counterSizeBytes);
-    mDataParcelable.setup(sharedMemoryIndex, dataMemoryOffset, dataSizeInBytes);
+    mReadCounterParcelable.setup({sharedMemoryIndex, readCounterOffset, counterSizeBytes});
+    mWriteCounterParcelable.setup({sharedMemoryIndex, writeCounterOffset, counterSizeBytes});
+    mDataParcelable.setup({sharedMemoryIndex, dataMemoryOffset, dataSizeInBytes});
 }
 
 void RingBufferParcelable::setupMemory(int32_t sharedMemoryIndex,
                  int32_t dataMemoryOffset,
                  int32_t dataSizeInBytes) {
-    mSharedMemoryIndex = sharedMemoryIndex;
-    mReadCounterParcelable.setup(sharedMemoryIndex, 0, 0);
-    mWriteCounterParcelable.setup(sharedMemoryIndex, 0, 0);
-    mDataParcelable.setup(sharedMemoryIndex, dataMemoryOffset, dataSizeInBytes);
+    mReadCounterParcelable.setup({sharedMemoryIndex, 0, 0});
+    mWriteCounterParcelable.setup({sharedMemoryIndex, 0, 0});
+    mDataParcelable.setup({sharedMemoryIndex, dataMemoryOffset, dataSizeInBytes});
+}
+
+void RingBufferParcelable::setupMemory(
+        const SharedRegionParcelable::MemoryInfoTuple& dataMemoryInfo,
+        const SharedRegionParcelable::MemoryInfoTuple& readCounterInfo,
+        const SharedRegionParcelable::MemoryInfoTuple& writeCounterInfo) {
+    mReadCounterParcelable.setup(readCounterInfo);
+    mWriteCounterParcelable.setup(writeCounterInfo);
+    mDataParcelable.setup(dataMemoryInfo);
 }
 
 int32_t RingBufferParcelable::getBytesPerFrame() const {
@@ -128,9 +133,11 @@
     return AAUDIO_OK;
 }
 
-void RingBufferParcelable::updateMemory(const RingBufferParcelable& parcelable) {
-    setupMemory(mSharedMemoryIndex, 0,
-                parcelable.getCapacityInFrames() * parcelable.getBytesPerFrame());
+void RingBufferParcelable::updateMemory(const RingBufferParcelable& parcelable,
+                                        const std::map<int32_t, int32_t>& memoryIndexMap) {
+    setupMemory(parcelable.mDataParcelable.getMemoryInfo(&memoryIndexMap),
+                parcelable.mReadCounterParcelable.getMemoryInfo(&memoryIndexMap),
+                parcelable.mWriteCounterParcelable.getMemoryInfo(&memoryIndexMap));
     setBytesPerFrame(parcelable.getBytesPerFrame());
     setFramesPerBurst(parcelable.getFramesPerBurst());
     setCapacityInFrames(parcelable.getCapacityInFrames());
@@ -152,7 +159,6 @@
     return AAUDIO_OK;
 }
 
-
 void RingBufferParcelable::dump() {
     ALOGD("mCapacityInFrames = %d ---------", mCapacityInFrames);
     if (mCapacityInFrames > 0) {
diff --git a/media/libaaudio/src/binding/RingBufferParcelable.h b/media/libaaudio/src/binding/RingBufferParcelable.h
index 29d0d86..4363191 100644
--- a/media/libaaudio/src/binding/RingBufferParcelable.h
+++ b/media/libaaudio/src/binding/RingBufferParcelable.h
@@ -17,6 +17,7 @@
 #ifndef ANDROID_AAUDIO_RINGBUFFER_PARCELABLE_H
 #define ANDROID_AAUDIO_RINGBUFFER_PARCELABLE_H
 
+#include <map>
 #include <stdint.h>
 
 #include <aaudio/RingBuffer.h>
@@ -46,6 +47,22 @@
                      int32_t dataMemoryOffset,
                      int32_t dataSizeInBytes);
 
+    /**
+     * Set up memory for the RingBufferParcelable.
+     *
+     * This function will take three MemoryInfoTuple as parameters to set up memory. The
+     * MemoryInfoTuple contains the shared memory index, offset in the shared memory and size
+     * of the object. This will allow setting up the read counter, write counter and data memory
+     * that are located in different shared memory blocks.
+     *
+     * @param dataMemoryInfo
+     * @param readCounterInfo
+     * @param writeCounterInfo
+     */
+    void setupMemory(const SharedRegionParcelable::MemoryInfoTuple& dataMemoryInfo,
+                     const SharedRegionParcelable::MemoryInfoTuple& readCounterInfo,
+                     const SharedRegionParcelable::MemoryInfoTuple& writeCounterInfo);
+
     int32_t getBytesPerFrame() const;
 
     void setBytesPerFrame(int32_t bytesPerFrame);
@@ -62,10 +79,24 @@
 
     aaudio_result_t resolve(SharedMemoryParcelable *memoryParcels, RingBufferDescriptor *descriptor);
 
-    void updateMemory(const RingBufferParcelable& parcelable);
+    /**
+     * Update this ring buffer with the given ring buffer.
+     *
+     * @param parcelable the ring buffer to be used to update this ring buffer.
+     * @param memoryIndexMap a map from the shared memory indexes used by the given ring buffer
+     *                       to the shared memory indexes used by this ring buffer.
+     */
+    void updateMemory(const RingBufferParcelable& parcelable,
+                      const std::map<int32_t, int32_t>& memoryIndexMap);
 
-    int32_t getSharedMemoryIndex() const {
-        return mSharedMemoryIndex;
+    int32_t getReadCounterSharedMemoryIndex() const {
+        return mReadCounterParcelable.getSharedMemoryIndex();
+    }
+    int32_t getWriteCounterSharedMemoryIndex() const {
+        return mWriteCounterParcelable.getSharedMemoryIndex();
+    }
+    int32_t getDataSharedMemoryIndex() const {
+        return mDataParcelable.getSharedMemoryIndex();
     }
 
     void dump();
@@ -77,7 +108,6 @@
     SharedRegionParcelable  mReadCounterParcelable;
     SharedRegionParcelable  mWriteCounterParcelable;
     SharedRegionParcelable  mDataParcelable;
-    int32_t                 mSharedMemoryIndex = -1;
     int32_t                 mBytesPerFrame = 0;     // index is in frames
     int32_t                 mFramesPerBurst = 0;    // for ISOCHRONOUS queues
     int32_t                 mCapacityInFrames = 0;  // zero if unused
diff --git a/media/libaaudio/src/binding/SharedMemoryParcelable.cpp b/media/libaaudio/src/binding/SharedMemoryParcelable.cpp
index 741aefc..c360a1f 100644
--- a/media/libaaudio/src/binding/SharedMemoryParcelable.cpp
+++ b/media/libaaudio/src/binding/SharedMemoryParcelable.cpp
@@ -146,7 +146,7 @@
     return AAUDIO_OK;
 }
 
-void SharedMemoryParcelable::dump() {
+void SharedMemoryParcelable::dump() const {
     ALOGD("mFd = %d", mFd.get());
     ALOGD("mSizeInBytes = %" PRId64, mSizeInBytes);
 }
diff --git a/media/libaaudio/src/binding/SharedMemoryParcelable.h b/media/libaaudio/src/binding/SharedMemoryParcelable.h
index 7762fef..909f3a6 100644
--- a/media/libaaudio/src/binding/SharedMemoryParcelable.h
+++ b/media/libaaudio/src/binding/SharedMemoryParcelable.h
@@ -64,7 +64,9 @@
 
     int32_t getSizeInBytes();
 
-    void dump();
+    bool isInUse() const { return mFd.get() != -1; }
+
+    void dump() const;
 
     // Extract a parcelable representation of this object.
     // Since we own a unique FD, move semantics are provided to avoid the need to dupe.
diff --git a/media/libaaudio/src/binding/SharedRegionParcelable.cpp b/media/libaaudio/src/binding/SharedRegionParcelable.cpp
index 6fa109b..fd69ef1 100644
--- a/media/libaaudio/src/binding/SharedRegionParcelable.cpp
+++ b/media/libaaudio/src/binding/SharedRegionParcelable.cpp
@@ -46,12 +46,17 @@
     return result;
 }
 
-void SharedRegionParcelable::setup(int32_t sharedMemoryIndex,
-                                   int32_t offsetInBytes,
-                                   int32_t sizeInBytes) {
-    mSharedMemoryIndex = sharedMemoryIndex;
-    mOffsetInBytes = offsetInBytes;
-    mSizeInBytes = sizeInBytes;
+void SharedRegionParcelable::setup(MemoryInfoTuple memoryInfoTuple) {
+    mSharedMemoryIndex = std::get<MEMORY_INDEX>(memoryInfoTuple);
+    mOffsetInBytes = std::get<OFFSET>(memoryInfoTuple);
+    mSizeInBytes = std::get<SIZE>(memoryInfoTuple);
+}
+
+SharedRegionParcelable::MemoryInfoTuple SharedRegionParcelable::getMemoryInfo(
+        const std::map<int32_t, int32_t>* memoryIndexMap) const {
+    return {memoryIndexMap == nullptr ? mSharedMemoryIndex : memoryIndexMap->at(mSharedMemoryIndex),
+            mOffsetInBytes,
+            mSizeInBytes};
 }
 
 aaudio_result_t SharedRegionParcelable::resolve(SharedMemoryParcelable *memoryParcels,
diff --git a/media/libaaudio/src/binding/SharedRegionParcelable.h b/media/libaaudio/src/binding/SharedRegionParcelable.h
index c15fc30..74ea75d 100644
--- a/media/libaaudio/src/binding/SharedRegionParcelable.h
+++ b/media/libaaudio/src/binding/SharedRegionParcelable.h
@@ -37,12 +37,36 @@
     // Construct based on a parcelable representation.
     explicit SharedRegionParcelable(const SharedRegion& parcelable);
 
-    void setup(int32_t sharedMemoryIndex, int32_t offsetInBytes, int32_t sizeInBytes);
+    // A tuple that contains information for setting up shared memory.
+    // The information in the tuple is <shared memory index, offset, size in byte>.
+    using MemoryInfoTuple = std::tuple<int, int, int>;
+    // Enums to use as index to query from MemoryInfoTuple
+    enum {
+        MEMORY_INDEX = 0,
+        OFFSET = 1,
+        SIZE = 2,
+    };
+    void setup(MemoryInfoTuple memoryInfoTuple);
 
     aaudio_result_t resolve(SharedMemoryParcelable *memoryParcels, void **regionAddressPtr);
 
     bool isFileDescriptorSafe(SharedMemoryParcelable *memoryParcels);
 
+    int32_t getSharedMemoryIndex() const { return mSharedMemoryIndex; }
+
+    /**
+     * Get the memory information of this SharedRegionParcelable.
+     *
+     * If the `memoryIndexMap` is not null, it indicates the caller has a different indexing for
+     * the shared memory. In that case, the `memoryIndexMap` must contains information from the
+     * shared memory indexes used by this object to the caller's shared memory indexes.
+     *
+     * @param memoryIndexMap a pointer to a map of memory index, which map the current shared
+     *                       memory index to a new shared memory index.
+     * @return
+     */
+    MemoryInfoTuple getMemoryInfo(const std::map<int32_t, int32_t>* memoryIndexMap) const;
+
     void dump();
 
     // Extract a parcelable representation of this object.
diff --git a/media/libaaudio/src/binding/aidl/aaudio/RingBuffer.aidl b/media/libaaudio/src/binding/aidl/aaudio/RingBuffer.aidl
index dd64493..998fc66 100644
--- a/media/libaaudio/src/binding/aidl/aaudio/RingBuffer.aidl
+++ b/media/libaaudio/src/binding/aidl/aaudio/RingBuffer.aidl
@@ -26,5 +26,4 @@
     int                 framesPerBurst;    // for ISOCHRONOUS queues
     int                 capacityInFrames;  // zero if unused
     int /* RingbufferFlags */ flags;  // = RingbufferFlags::NONE;
-    int                 sharedMemoryIndex;
-}
\ No newline at end of file
+}
diff --git a/media/libaaudio/src/client/AudioStreamInternal.cpp b/media/libaaudio/src/client/AudioStreamInternal.cpp
index 8fe8569..525ebb4 100644
--- a/media/libaaudio/src/client/AudioStreamInternal.cpp
+++ b/media/libaaudio/src/client/AudioStreamInternal.cpp
@@ -384,7 +384,11 @@
         goto exit;
     }
     // Reconstruct data queue descriptor using new shared file descriptor.
-    mEndPointParcelable.updateDataFileDescriptor(&endpointParcelable);
+    result = mEndPointParcelable.updateDataFileDescriptor(&endpointParcelable);
+    if (result != AAUDIO_OK) {
+        ALOGE("%s failed to update data file descriptor, error=%d", __func__, result);
+        goto exit;
+    }
     result = mEndPointParcelable.resolveDataQueue(&mEndpointDescriptor.dataQueueDescriptor);
     if (result != AAUDIO_OK) {
         ALOGE("Failed to resolve data queue after exiting standby, error=%d", result);