summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorWei Jia <wjia@google.com>2015-04-28 18:22:36 -0700
committerWei Jia <wjia@google.com>2015-04-30 09:53:14 -0700
commitbac588208fadec78e3fa205c238089df277d3817 (patch)
tree3feebbd56bf126f282d96583f2a60f17fdfabdfe
parentc0239eca6d022b498d21cc467f83f715f7e7ed89 (diff)
downloadframeworks_av-bac588208fadec78e3fa205c238089df277d3817.zip
frameworks_av-bac588208fadec78e3fa205c238089df277d3817.tar.gz
frameworks_av-bac588208fadec78e3fa205c238089df277d3817.tar.bz2
MediaSync: map returned output buffers to previously received input buffers.
Bug: 19666434 Change-Id: I81e9cb8e73d950b3be5d29cf010c6793894ad802
-rw-r--r--include/media/stagefright/MediaSync.h8
-rw-r--r--media/libstagefright/MediaSync.cpp23
2 files changed, 29 insertions, 2 deletions
diff --git a/include/media/stagefright/MediaSync.h b/include/media/stagefright/MediaSync.h
index 8ad74a4..e071b65 100644
--- a/include/media/stagefright/MediaSync.h
+++ b/include/media/stagefright/MediaSync.h
@@ -23,6 +23,7 @@
#include <media/stagefright/foundation/AHandler.h>
#include <utils/Condition.h>
+#include <utils/KeyedVector.h>
#include <utils/Mutex.h>
namespace android {
@@ -190,6 +191,13 @@ private:
int64_t mNextBufferItemMediaUs;
List<BufferItem> mBufferItems;
+
+ // Keep track of buffers received from |mInput|. This is needed because
+ // it's possible the consumer of |mOutput| could return a different
+ // GraphicBuffer::handle (e.g., due to passing buffers through IPC),
+ // and that could cause problem if the producer of |mInput| only
+ // supports pre-registered buffers.
+ KeyedVector<uint64_t, sp<GraphicBuffer> > mBuffersFromInput;
sp<ALooper> mLooper;
float mPlaybackRate;
diff --git a/media/libstagefright/MediaSync.cpp b/media/libstagefright/MediaSync.cpp
index 8030a36..4350b59 100644
--- a/media/libstagefright/MediaSync.cpp
+++ b/media/libstagefright/MediaSync.cpp
@@ -430,7 +430,16 @@ void MediaSync::onFrameAvailableFromInput() {
return;
}
+ if (mBuffersFromInput.indexOfKey(bufferItem.mGraphicBuffer->getId()) >= 0) {
+ // Something is wrong since this buffer should be at our hands, bail.
+ mInput->consumerDisconnect();
+ onAbandoned_l(true /* isInput */);
+ return;
+ }
+ mBuffersFromInput.add(bufferItem.mGraphicBuffer->getId(), bufferItem.mGraphicBuffer);
+
mBufferItems.push_back(bufferItem);
+
if (mBufferItems.size() == 1) {
onDrainVideo_l();
}
@@ -497,9 +506,19 @@ void MediaSync::onBufferReleasedByOutput() {
void MediaSync::returnBufferToInput_l(
const sp<GraphicBuffer> &buffer, const sp<Fence> &fence) {
+ ssize_t ix = mBuffersFromInput.indexOfKey(buffer->getId());
+ if (ix < 0) {
+ // The buffer is unknown, something is wrong, bail.
+ mOutput->disconnect(NATIVE_WINDOW_API_MEDIA);
+ onAbandoned_l(false /* isInput */);
+ return;
+ }
+ sp<GraphicBuffer> oldBuffer = mBuffersFromInput.valueAt(ix);
+ mBuffersFromInput.removeItemsAt(ix);
+
// Attach and release the buffer back to the input.
int consumerSlot;
- status_t status = mInput->attachBuffer(&consumerSlot, buffer);
+ status_t status = mInput->attachBuffer(&consumerSlot, oldBuffer);
ALOGE_IF(status != NO_ERROR, "attaching buffer to input failed (%d)", status);
if (status == NO_ERROR) {
status = mInput->releaseBuffer(consumerSlot, 0 /* frameNumber */,
@@ -512,7 +531,7 @@ void MediaSync::returnBufferToInput_l(
return;
}
- ALOGV("released buffer %#llx to input", (long long)buffer->getId());
+ ALOGV("released buffer %#llx to input", (long long)oldBuffer->getId());
// Notify any waiting onFrameAvailable calls.
--mNumOutstandingBuffers;