summaryrefslogtreecommitdiffstats
path: root/media
diff options
context:
space:
mode:
authorJamie Gennis <jgennis@google.com>2010-11-01 16:04:31 -0700
committerJamie Gennis <jgennis@google.com>2010-11-03 16:15:10 -0700
commitf0c5c1e8ce765c66d24bc9d00904fd350b99d16a (patch)
treeb820acdc100c17af51177694d45eee3a578f3390 /media
parentde04e5242ad7d95c392070e1a4f7acdf3809b91a (diff)
downloadframeworks_base-f0c5c1e8ce765c66d24bc9d00904fd350b99d16a.zip
frameworks_base-f0c5c1e8ce765c66d24bc9d00904fd350b99d16a.tar.gz
frameworks_base-f0c5c1e8ce765c66d24bc9d00904fd350b99d16a.tar.bz2
Fix a MediaBuffer leak in Stagefright.
Change-Id: I548e60b07cf1676476874b156cfbc4ffefdfa2b9
Diffstat (limited to 'media')
-rw-r--r--media/libstagefright/OMXCodec.cpp63
1 files changed, 29 insertions, 34 deletions
diff --git a/media/libstagefright/OMXCodec.cpp b/media/libstagefright/OMXCodec.cpp
index 3c3bd93..e1c06a6 100644
--- a/media/libstagefright/OMXCodec.cpp
+++ b/media/libstagefright/OMXCodec.cpp
@@ -1901,11 +1901,8 @@ void OMXCodec::on_message(const omx_message &msg) {
if (mPortStatus[kPortIndexInput] == DISABLING) {
CODEC_LOGV("Port is disabled, freeing buffer %p", buffer);
- status_t err =
- mOMX->freeBuffer(mNode, kPortIndexInput, buffer);
+ status_t err = freeBuffer(kPortIndexInput, i);
CHECK_EQ(err, OK);
-
- buffers->removeAt(i);
} else if (mState != ERROR
&& mPortStatus[kPortIndexInput] != SHUTTING_DOWN) {
CHECK_EQ(mPortStatus[kPortIndexInput], ENABLED);
@@ -1945,20 +1942,9 @@ void OMXCodec::on_message(const omx_message &msg) {
if (mPortStatus[kPortIndexOutput] == DISABLING) {
CODEC_LOGV("Port is disabled, freeing buffer %p", buffer);
- status_t err =
- mOMX->freeBuffer(mNode, kPortIndexOutput, buffer);
+ status_t err = freeBuffer(kPortIndexOutput, i);
CHECK_EQ(err, OK);
- // Cancel the buffer if it belongs to an ANativeWindow.
- if (info->mMediaBuffer != NULL) {
- sp<GraphicBuffer> graphicBuffer = info->mMediaBuffer->graphicBuffer();
- if (!info->mOwnedByNativeWindow && graphicBuffer != 0) {
- cancelBufferToNativeWindow(info);
- // Ignore any errors
- }
- }
-
- buffers->removeAt(i);
#if 0
} else if (mPortStatus[kPortIndexOutput] == ENABLED
&& (flags & OMX_BUFFERFLAG_EOS)) {
@@ -2436,37 +2422,46 @@ status_t OMXCodec::freeBuffersOnPort(
CODEC_LOGV("freeing buffer %p on port %ld", info->mBuffer, portIndex);
- status_t err =
- mOMX->freeBuffer(mNode, portIndex, info->mBuffer);
+ status_t err = freeBuffer(portIndex, i);
if (err != OK) {
stickyErr = err;
}
- if (info->mMediaBuffer != NULL) {
- info->mMediaBuffer->setObserver(NULL);
+ }
- // Make sure nobody but us owns this buffer at this point.
- CHECK_EQ(info->mMediaBuffer->refcount(), 0);
+ CHECK(onlyThoseWeOwn || buffers->isEmpty());
- // Cancel the buffer if it belongs to an ANativeWindow.
- sp<GraphicBuffer> graphicBuffer = info->mMediaBuffer->graphicBuffer();
- if (!info->mOwnedByNativeWindow && graphicBuffer != 0) {
- status_t err = cancelBufferToNativeWindow(info);
- if (err != OK) {
- stickyErr = err;
- }
- }
+ return stickyErr;
+}
+
+status_t OMXCodec::freeBuffer(OMX_U32 portIndex, size_t bufIndex) {
+ Vector<BufferInfo> *buffers = &mPortBuffers[portIndex];
+
+ BufferInfo *info = &buffers->editItemAt(bufIndex);
+
+ status_t err = mOMX->freeBuffer(mNode, portIndex, info->mBuffer);
+
+ if (err == OK && info->mMediaBuffer != NULL) {
+ info->mMediaBuffer->setObserver(NULL);
- info->mMediaBuffer->release();
+ // Make sure nobody but us owns this buffer at this point.
+ CHECK_EQ(info->mMediaBuffer->refcount(), 0);
+
+ // Cancel the buffer if it belongs to an ANativeWindow.
+ sp<GraphicBuffer> graphicBuffer = info->mMediaBuffer->graphicBuffer();
+ if (!info->mOwnedByNativeWindow && graphicBuffer != 0) {
+ err = cancelBufferToNativeWindow(info);
}
- buffers->removeAt(i);
+ info->mMediaBuffer->release();
}
- CHECK(onlyThoseWeOwn || buffers->isEmpty());
+ if (err == OK) {
+ buffers->removeAt(bufIndex);
+ }
- return stickyErr;
+ return err;
}
void OMXCodec::onPortSettingsChanged(OMX_U32 portIndex) {