int32_t OMXImplWVClassic::HandlePrepareDecodeBuffer(
    OMX_BUFFERHEADERTYPE *buffer, buffer_retain_t *retain, VideoDecodeBuffer *p)
{
    if (buffer == NULL || p == NULL)
    {
        return OMXDRM_ERROR_INV_ARG ;
    }

    IMRDataBuffer *imrBuffer = (IMRDataBuffer *)buffer->pBuffer;

    if (imrBuffer->magic != IMR_DATA_BUFFER_MAGIC)
    {
        LOGE("HandlePrepareDecodeBuffer: IMR buffer has wrong magic: 0x%08x", imrBuffer->magic) ;
        return OMXDRM_ERROR_HW ;
    }

    if (imrBuffer->isClear)
    {
        p->data = imrBuffer->data + buffer->nOffset;
        p->size = buffer->nFilledLen;
    }
    else
    {
        // Return NALU headers in the clear, use IMRDataBuffer::data for that.

        imrBuffer->size = NALU_BUFFER_SIZE;
        sec_result_t secres = Drm_WV_ReturnNALUHeaders(
            WV_SESSION_ID, imrBuffer->frameStartOffset, buffer->nFilledLen, imrBuffer->data, &(imrBuffer->size));
        if (secres == DRM_FAIL_FW_SESSION)
        {
            LOGW("HandlePrepareDecodeBuffer: Drm_WV_ReturnNALUHeaders failed (DRM_FAIL_FW_SESSION). Session is disabled.");
            return OMXDRM_ERROR_NOT_READY;
        }
        else if (secres != 0)
        {
            LOGE("HandlePrepareDecodeBuffer: Drm_WV_ReturnNALUHeaders failed. Error = %#x, IMR offset = %u, len = %lu",
                secres, imrBuffer->frameStartOffset, buffer->nFilledLen);
            return OMXDRM_ERROR_HW;
        }
        else
        {
            // Success
            p->data = imrBuffer->data;
            p->size = imrBuffer->size;
            p->flag |= IS_SECURE_DATA;
        }
    }

    return OMXDRM_SUCCESS ;
}
OMX_ERRORTYPE OMXVideoDecoderAVCSecure::PrepareDecodeBuffer(OMX_BUFFERHEADERTYPE *buffer, buffer_retain_t *retain, VideoDecodeBuffer *p) {
    OMX_ERRORTYPE ret;
    ret = OMXVideoDecoderBase::PrepareDecodeBuffer(buffer, retain, p);
    CHECK_RETURN_VALUE("OMXVideoDecoderBase::PrepareDecodeBuffer");

    if (buffer->nFilledLen == 0) {
        return OMX_ErrorNone;
    }
    // OMX_BUFFERFLAG_CODECCONFIG is an optional flag
    // if flag is set, buffer will only contain codec data.
    if (buffer->nFlags & OMX_BUFFERFLAG_CODECCONFIG) {
        LOGV("Received AVC codec data.");
        return ret;
    }
    p->flag |= HAS_COMPLETE_FRAME;

    if (buffer->nOffset != 0) {
        LOGW("buffer offset %d is not zero!!!", buffer->nOffset);
    }

    IMRDataBuffer *imrBuffer = (IMRDataBuffer *)buffer->pBuffer;
    if (imrBuffer->clear) {
        p->data = imrBuffer->data + buffer->nOffset;
        p->size = buffer->nFilledLen;
    } else {
        imrBuffer->size = NALU_BUFFER_SIZE;
        sec_result_t res = Drm_WV_ReturnNALUHeaders(WV_SESSION_ID, imrBuffer->offset, buffer->nFilledLen, imrBuffer->data, (uint32_t *)&(imrBuffer->size));
        if (res == DRM_FAIL_FW_SESSION) {
            LOGW("Drm_WV_ReturnNALUHeaders failed. Session is disabled.");
            mSessionPaused = true;
            ret =  OMX_ErrorNotReady;
        } else if (res != 0) {
            mSessionPaused = false;
            LOGE("Drm_WV_ReturnNALUHeaders failed. Error = %#x, IMR offset = %d, len = %d", res, imrBuffer->offset, buffer->nFilledLen);
            ret = OMX_ErrorHardware;
        } else {
            mSessionPaused = false;
            p->data = imrBuffer->data;
            p->size = imrBuffer->size;
            p->flag |= IS_SECURE_DATA;
        }
    }

    //reset IMR size
    imrBuffer->size = NALU_BUFFER_SIZE;
    return ret;
}