Search code examples
android-mediacodec

Why does MediaCodec.reset() generate java.lang.IllegalStateException


The official document says: "Call reset() to make the codec usable again. You can call it from any state to move the codec back to the Uninitialized state."

However, the following code occasionally throws java.lang.IllegalStateException:

if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
    //do nothing
} else {
    try {
        mediaCodec.reset();
    } catch (Exception ex) {
          //occasionally throws java.lang.IllegalStateException
    }
}

Exception:

Class: java.lang.IllegalStateException
 Stack trace: java.lang.IllegalStateException
    at android.media.MediaCodec.native_reset(Native Method)
    at android.media.MediaCodec.reset(MediaCodec.java:1794)

Solution

  • you are right, the documentation is a bit misleading here because there are two possible states a MediaCodec instance can be in that are not resettable.

    If the MediaCodec instance is released, Released state, it is obviously not resettable thus resulting in an IllegalStateException.

    If the MediaCodec instance is in Error state because it could not be created it is also not resettable, but this time resulting in a MediaCodec.CodecException. For example if you create to many instances.

    A comment in the libstagefright sourcecode describes what a reset call is basically doing.

        /* When external-facing MediaCodec object is created,
           it is already initialized.  Thus, reset is essentially
           release() followed by init(), plus clearing the state */
    

    If you check out the code you'll see that when release is called on an already released MediaCodec instance it'll result in an INVALID_OPERATION err, which leads to the codec not being reinitialized and ultimately in an IllegalStateException.

    I hope this clarified your question

    Best regards

    Chris