media: keep JMediaCodec::mCodec reference until destruction
Releasing mCodec prematurely at release() sometimes causes double
free on MediaCodec objects.
Bug: 134770912
Test: atest CtsMediaTestCases:MediaCodecTest#testAsyncRelease (20 times)
Change-Id: Ieb265c9c4d74bd6bd3b34f0a713c8fa7dd2dedd1
diff --git a/media/jni/android_media_MediaCodec.cpp b/media/jni/android_media_MediaCodec.cpp
index 150b6f9..8d420e2 100644
--- a/media/jni/android_media_MediaCodec.cpp
+++ b/media/jni/android_media_MediaCodec.cpp
@@ -211,21 +211,22 @@
}
void JMediaCodec::release() {
- if (mCodec != NULL) {
- mCodec->release();
- mCodec.clear();
- mInitStatus = NO_INIT;
- }
+ std::call_once(mReleaseFlag, [this] {
+ if (mCodec != NULL) {
+ mCodec->release();
+ mInitStatus = NO_INIT;
+ }
- if (mLooper != NULL) {
- mLooper->unregisterHandler(id());
- mLooper->stop();
- mLooper.clear();
- }
+ if (mLooper != NULL) {
+ mLooper->unregisterHandler(id());
+ mLooper->stop();
+ mLooper.clear();
+ }
+ });
}
JMediaCodec::~JMediaCodec() {
- if (mCodec != NULL || mLooper != NULL) {
+ if (mLooper != NULL) {
/* MediaCodec and looper should have been released explicitly already
* in setMediaCodec() (see comments in setMediaCodec()).
*
diff --git a/media/jni/android_media_MediaCodec.h b/media/jni/android_media_MediaCodec.h
index de08550..dfe30a3 100644
--- a/media/jni/android_media_MediaCodec.h
+++ b/media/jni/android_media_MediaCodec.h
@@ -17,6 +17,8 @@
#ifndef _ANDROID_MEDIA_MEDIACODEC_H_
#define _ANDROID_MEDIA_MEDIACODEC_H_
+#include <mutex>
+
#include "jni.h"
#include <media/MediaAnalyticsItem.h>
@@ -156,6 +158,7 @@
sp<ALooper> mLooper;
sp<MediaCodec> mCodec;
AString mNameAtCreation;
+ std::once_flag mReleaseFlag;
sp<AMessage> mCallbackNotification;
sp<AMessage> mOnFrameRenderedNotification;