From f011974db73540fd1c9713007ca60035fbf5990b Mon Sep 17 00:00:00 2001 From: "qinmin@chromium.org" Date: Sat, 7 Sep 2013 02:04:31 +0000 Subject: [PATCH] capture a top java exception on certain Samsung devices This is one of the top crasher on some samsung devices https://crash.corp.google.com/search?query=android.media.MediaCodec.flush Capture some exceptions while we are trying to look into the problem BUG=278464 Review URL: https://chromiumcodereview.appspot.com/23321004 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@221858 0039d316-1c4b-4281-b951-d872f2087c98 --- .../src/org/chromium/media/MediaCodecBridge.java | 16 +++++++++++----- media/base/android/media_codec_bridge.cc | 5 +++-- media/base/android/media_codec_bridge.h | 4 +++- media/base/android/media_decoder_job.cc | 6 +++++- 4 files changed, 22 insertions(+), 9 deletions(-) diff --git a/media/base/android/java/src/org/chromium/media/MediaCodecBridge.java b/media/base/android/java/src/org/chromium/media/MediaCodecBridge.java index 7025a1de6f19aa..3ed617bb34c240 100644 --- a/media/base/android/java/src/org/chromium/media/MediaCodecBridge.java +++ b/media/base/android/java/src/org/chromium/media/MediaCodecBridge.java @@ -193,12 +193,18 @@ private DequeueInputResult dequeueInputBuffer(long timeoutUs) { } @CalledByNative - private void flush() { - mMediaCodec.flush(); - mFlushed = true; - if (mAudioTrack != null) { - mAudioTrack.flush(); + private int flush() { + try { + mFlushed = true; + if (mAudioTrack != null) { + mAudioTrack.flush(); + } + mMediaCodec.flush(); + } catch(IllegalStateException e) { + Log.e(TAG, "Failed to flush MediaCodec " + e.toString()); + return MEDIA_CODEC_ERROR; } + return MEDIA_CODEC_OK; } @CalledByNative diff --git a/media/base/android/media_codec_bridge.cc b/media/base/android/media_codec_bridge.cc index f5c73a0a75c215..c61ed9abfe30d5 100644 --- a/media/base/android/media_codec_bridge.cc +++ b/media/base/android/media_codec_bridge.cc @@ -111,9 +111,10 @@ void MediaCodecBridge::StartInternal() { GetOutputBuffers(); } -void MediaCodecBridge::Reset() { +MediaCodecStatus MediaCodecBridge::Reset() { JNIEnv* env = AttachCurrentThread(); - Java_MediaCodecBridge_flush(env, j_media_codec_.obj()); + return static_cast( + Java_MediaCodecBridge_flush(env, j_media_codec_.obj())); } void MediaCodecBridge::Stop() { diff --git a/media/base/android/media_codec_bridge.h b/media/base/android/media_codec_bridge.h index 9f855beb6098cf..7c3615a5f3a7d2 100644 --- a/media/base/android/media_codec_bridge.h +++ b/media/base/android/media_codec_bridge.h @@ -54,7 +54,9 @@ class MEDIA_EXPORT MediaCodecBridge { // DequeueInputBuffer() and DequeueOutputBuffer() become invalid. // Please note that this clears all the inputs in the media codec. In other // words, there will be no outputs until new input is provided. - void Reset(); + // Returns MEDIA_CODEC_ERROR if an unexpected error happens, or Media_CODEC_OK + // otherwise. + MediaCodecStatus Reset(); // Finishes the decode/encode session. The instance remains active // and ready to be StartAudio/Video()ed again. HOWEVER, due to the buggy diff --git a/media/base/android/media_decoder_job.cc b/media/base/android/media_decoder_job.cc index 4370c7e340954f..c5b6cbc57a0bc6 100644 --- a/media/base/android/media_decoder_job.cc +++ b/media/base/android/media_decoder_job.cc @@ -231,7 +231,11 @@ void MediaDecoderJob::DecodeInternal( if (needs_flush) { DVLOG(1) << "DecodeInternal needs flush."; input_eos_encountered_ = false; - media_codec_bridge_->Reset(); + MediaCodecStatus reset_status = media_codec_bridge_->Reset(); + if (MEDIA_CODEC_OK != reset_status) { + callback.Run(reset_status, start_presentation_timestamp, 0); + return; + } } MediaCodecStatus input_status = MEDIA_CODEC_INPUT_END_OF_STREAM;