Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 3e904467 authored by Haynes Mathew George's avatar Haynes Mathew George Committed by Aalique Grahame
Browse files

libstagefright: omx: Prevent assertion due to state mismatches

Instead handle them a bit better. Since the assertions dealt
with in this patchset can only happen if the OMX IL client died
while de-init'ing the component, it is impossible to deal with
all possible cases gracefully. Hence take an aggressive approach
by moving state of the component to OMX_StateInvalid. This looks
okay as per the spec, but might not be the best approach.

CRs-Fixed: 1077558
Change-Id: Id240a23f2c16e89f41f9156277f4dcbe0969f954
parent bb813629
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -140,6 +140,7 @@ private:
    void onPortFlush(OMX_U32 portIndex, bool sendFlushComplete);

    void checkTransitions();
    void onTransitionError();

    DISALLOW_EVIL_CONSTRUCTORS(SimpleSoftOMXComponent);
};
+40 −4
Original line number Diff line number Diff line
@@ -425,16 +425,43 @@ void SimpleSoftOMXComponent::onSendCommand(
    }
}

void SimpleSoftOMXComponent::onTransitionError() {
    mState = OMX_StateInvalid;
    mTargetState = OMX_StateInvalid;
    notify(OMX_EventError, OMX_CommandStateSet, OMX_StateInvalid, 0);
}

void SimpleSoftOMXComponent::onChangeState(OMX_STATETYPE state) {
    bool skipTransitions = false;

    // We shouldn't be in a state transition already.
    CHECK_EQ((int)mState, (int)mTargetState);
    if (mState != mTargetState) {
        // Workaround to prevent assertion
        // XXX CHECK_EQ((int)mState, (int)mTargetState);
        ALOGW("mState %d != mTargetState %d", mState, mTargetState);
        skipTransitions = true;
        onTransitionError();
    }

    switch (mState) {
        case OMX_StateLoaded:
            CHECK_EQ((int)state, (int)OMX_StateIdle);
            if (state != OMX_StateIdle) {
                // Workaround to prevent assertion
                // XXX CHECK_EQ((int)state, (int)OMX_StateIdle);
                ALOGW("In OMX_StateLoaded, state %d != OMX_StateIdle", state);
                skipTransitions = true;
                onTransitionError();
            }
            break;
        case OMX_StateIdle:
            CHECK(state == OMX_StateLoaded || state == OMX_StateExecuting);
            if (!(state == OMX_StateLoaded || state == OMX_StateExecuting)) {
                // Workaround to prevent assertion
                // XXX CHECK(state == OMX_StateLoaded || state == OMX_StateExecuting);
                ALOGW("In OMX_StateIdle, state %d != OMX_StateLoaded||OMX_StateExecuting",
                      state);
                skipTransitions = true;
                onTransitionError();
            }
            break;
        case OMX_StateExecuting:
        {
@@ -448,11 +475,20 @@ void SimpleSoftOMXComponent::onChangeState(OMX_STATETYPE state) {
            notify(OMX_EventCmdComplete, OMX_CommandStateSet, state, NULL);
            break;
        }

        case OMX_StateInvalid: {
            ALOGW("In OMX_StateInvalid, ignore state transition to %d", state);
            skipTransitions = true;
            onTransitionError();
            break;
        }
        default:
            TRESPASS();
    }

    if (skipTransitions) {
        return;
    }

    mTargetState = state;

    checkTransitions();