#include "Exynos_OMX_Basecomponent.h"
#include "Exynos_OMX_Baseport.h"
#include "Exynos_OMX_Vdec.h"
+#include "Exynos_OMX_VdecControl.h"
#include "Exynos_OSAL_ETC.h"
#include "Exynos_OSAL_Semaphore.h"
#include "Exynos_OSAL_Thread.h"
{OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel41},
{OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel42}};
-static OMX_ERRORTYPE GetCodecInputPrivateData(OMX_PTR codecBuffer, void *pVirtAddr, OMX_U32 *dataSize)
+OMX_ERRORTYPE H264CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent);
+
+static OMX_ERRORTYPE GetCodecInputPrivateData(OMX_PTR codecBuffer, OMX_PTR *pVirtAddr, OMX_U32 *dataSize)
{
OMX_ERRORTYPE ret = OMX_ErrorNone;
return ret;
}
-static OMX_ERRORTYPE GetCodecOutputPrivateData(OMX_PTR codecBuffer, void *addr[], int size[])
+static OMX_ERRORTYPE GetCodecOutputPrivateData(OMX_PTR codecBuffer, OMX_PTR addr[], OMX_U32 size[])
{
OMX_ERRORTYPE ret = OMX_ErrorNone;
ExynosVideoBuffer *pCodecBuffer;
pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
- if ((nPortIndex == INPUT_PORT_INDEX) && (pInbufOps != NULL))
+ if ((nPortIndex == INPUT_PORT_INDEX) && (pInbufOps != NULL)) {
pInbufOps->Stop(hMFCHandle);
- else if ((nPortIndex == OUTPUT_PORT_INDEX) && (pOutbufOps != NULL))
+ } else if ((nPortIndex == OUTPUT_PORT_INDEX) && (pOutbufOps != NULL)) {
+ EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
pOutbufOps->Stop(hMFCHandle);
-
+ if (pExynosOutputPort->bufferProcessType == BUFFER_SHARE) {
+ pOutbufOps->Clear_RegisteredBuffer(hMFCHandle);
+ }
+ }
ret = OMX_ErrorNone;
EXIT:
return ret;
}
+OMX_ERRORTYPE H264CodecRegistCodecBuffers(
+ OMX_COMPONENTTYPE *pOMXComponent,
+ OMX_U32 nPortIndex,
+ OMX_U32 nBufferCnt)
+{
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+ EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
+ void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
+ CODEC_DEC_BUFFER **ppCodecBuffer = NULL;
+ ExynosVideoDecBufferOps *pBufOps = NULL;
+ ExynosVideoPlane *pPlanes = NULL;
+
+ OMX_U32 nPlaneCnt = 0;
+ uint32_t i, j;
+
+ FunctionIn();
+
+ if (nPortIndex == INPUT_PORT_INDEX) {
+ ppCodecBuffer = &(pVideoDec->pMFCDecInputBuffer[0]);
+ pBufOps = pH264Dec->hMFCH264Handle.pInbufOps;
+ } else {
+ ppCodecBuffer = &(pVideoDec->pMFCDecOutputBuffer[0]);
+ pBufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
+ }
+ nPlaneCnt = pExynosComponent->pExynosPort[nPortIndex].nPlaneCnt;
+
+ pPlanes = (ExynosVideoPlane *)Exynos_OSAL_Malloc(sizeof(ExynosVideoPlane) * nPlaneCnt);
+ if (pPlanes == NULL) {
+ ret = OMX_ErrorInsufficientResources;
+ goto EXIT;
+ }
+
+ /* Register buffer */
+ for (i = 0; i < nBufferCnt; i++) {
+ for (j = 0; j < nPlaneCnt; j++) {
+ pPlanes[j].addr = ppCodecBuffer[i]->pVirAddr[j];
+ pPlanes[j].fd = ppCodecBuffer[i]->fd[j];
+ pPlanes[j].allocSize = ppCodecBuffer[i]->bufferSize[j];
+ }
+
+ if (pBufOps->Register(hMFCHandle, pPlanes, nPlaneCnt) != VIDEO_ERROR_NONE) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "PORT[%d]: Failed to Register buffer", nPortIndex);
+ ret = OMX_ErrorInsufficientResources;
+ Exynos_OSAL_Free(pPlanes);
+ goto EXIT;
+ }
+ }
+
+ Exynos_OSAL_Free(pPlanes);
+
+ ret = OMX_ErrorNone;
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
+OMX_ERRORTYPE H264CodecReconfigAllBuffers(
+ OMX_COMPONENTTYPE *pOMXComponent,
+ OMX_U32 nPortIndex)
+{
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+ EXYNOS_OMX_BASEPORT *pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
+ EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
+ void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
+ ExynosVideoDecBufferOps *pBufferOps = NULL;
+
+ FunctionIn();
+
+ if ((nPortIndex == INPUT_PORT_INDEX) &&
+ (pH264Dec->bSourceStart == OMX_TRUE)) {
+ ret = OMX_ErrorNotImplemented;
+ goto EXIT;
+ } else if ((nPortIndex == OUTPUT_PORT_INDEX) &&
+ (pH264Dec->bDestinationStart == OMX_TRUE)) {
+ pBufferOps = pH264Dec->hMFCH264Handle.pOutbufOps;
+
+ if (pExynosPort->bufferProcessType & BUFFER_COPY) {
+ /**********************************/
+ /* Codec Buffer Free & Unregister */
+ /**********************************/
+ Exynos_Free_CodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX);
+ Exynos_CodecBufferReset(pExynosComponent, OUTPUT_PORT_INDEX);
+ pBufferOps->Clear_RegisteredBuffer(hMFCHandle);
+ pBufferOps->Cleanup_Buffer(hMFCHandle);
+
+ } else if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
+ /**********************************/
+ /* Codec Buffer Unregister */
+ /**********************************/
+ pBufferOps->Clear_RegisteredBuffer(hMFCHandle);
+ pBufferOps->Cleanup_Buffer(hMFCHandle);
+ }
+ /******************************************************/
+ /* V4L2 Destnation Setup for DPB Buffer Number Change */
+ /******************************************************/
+ H264CodecDstSetup(pOMXComponent);
+ pVideoDec->bReconfigDPB = OMX_FALSE;
+
+ Exynos_ResolutionUpdate(pOMXComponent);
+ } else {
+ ret = OMX_ErrorBadParameter;
+ goto EXIT;
+ }
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
OMX_ERRORTYPE H264CodecEnQueueAllBuffer(OMX_COMPONENTTYPE *pOMXComponent, OMX_U32 nPortIndex)
{
OMX_ERRORTYPE ret = OMX_ErrorNone;
void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
- int i, nOutbufs;
+ uint32_t i, nOutbufs;
ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
pInbufOps->Clear_Queue(hMFCHandle);
} else if ((nPortIndex == OUTPUT_PORT_INDEX) &&
(pH264Dec->bDestinationStart == OMX_TRUE)) {
- OMX_U32 dataLen[MFC_OUTPUT_BUFFER_PLANE] = {0, 0};
- ExynosVideoBuffer *pBuffer = NULL;
-
Exynos_CodecBufferReset(pExynosComponent, OUTPUT_PORT_INDEX);
- nOutbufs = pDecOps->Get_ActualBufferCount(hMFCHandle);
- nOutbufs += EXTRA_DPB_NUM;
- for (i = 0; i < nOutbufs; i++) {
- pOutbufOps->Get_Buffer(hMFCHandle, i, &pBuffer);
- Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, (OMX_PTR)pBuffer);
+ for (i = 0; i < pH264Dec->hMFCH264Handle.maxDPBNum; i++) {
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecOutputBuffer[%d]: 0x%x", i, pVideoDec->pMFCDecOutputBuffer[i]);
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecOutputBuffer[%d]->pVirAddr[0]: 0x%x", i, pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0]);
+
+ Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, pVideoDec->pMFCDecOutputBuffer[i]);
}
pOutbufOps->Clear_Queue(hMFCHandle);
}
pH264Dec->hMFCH264Handle.S3DFPArgmtType = (EXYNOS_OMX_FPARGMT_TYPE) framePacking.arrangement_type;
/** Send Port Settings changed call back - output color format change */
- (*(pExynosComponent->pCallbacks->EventHandler))
+ (*(pExynosComponent->pCallbacks->EventHandler))
(pOMXComponent,
pExynosComponent->callbackData,
- OMX_EventPortSettingsChanged, /* The command was completed */
- OMX_DirOutput, /* This is the port index */
- 0,
+ OMX_EventS3DInformation, /* The command was completed */
+ OMX_TRUE, /* S3D is enabled */
+ (OMX_S32)pH264Dec->hMFCH264Handle.S3DFPArgmtType, /* S3D FPArgmtType */
NULL);
Exynos_OSAL_SleepMillisec(0);
- ret = OMX_TRUE;
+ } else {
+ pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_NONE;
}
+ ret = OMX_TRUE;
+
EXIT:
return ret;
}
#endif
+OMX_ERRORTYPE H264CodecCheckResolutionChange(OMX_COMPONENTTYPE *pOMXComponent)
+{
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+ EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
+ void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
+ EXYNOS_OMX_BASEPORT *pInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
+ EXYNOS_OMX_BASEPORT *pOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
+ ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
+ ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
+
+ OMX_CONFIG_RECTTYPE *pCropRectangle = NULL;
+ OMX_PARAM_PORTDEFINITIONTYPE *pInputPortDefinition = NULL;
+ OMX_PARAM_PORTDEFINITIONTYPE *pOutputPortDefinition = NULL;
+
+ FunctionIn();
+ /* get geometry for output */
+ Exynos_OSAL_Memset(&pH264Dec->hMFCH264Handle.codecOutbufConf, 0, sizeof(ExynosVideoGeometry));
+ if (pOutbufOps->Get_Geometry(hMFCHandle, &pH264Dec->hMFCH264Handle.codecOutbufConf) != VIDEO_ERROR_NONE) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to get geometry for parsed header info");
+ ret = OMX_ErrorInsufficientResources;
+ goto EXIT;
+ }
+
+ /* get dpb count */
+ pH264Dec->hMFCH264Handle.maxDPBNum = pDecOps->Get_ActualBufferCount(hMFCHandle);
+ if (pVideoDec->bThumbnailMode == OMX_FALSE) {
+ pH264Dec->hMFCH264Handle.maxDPBNum += EXTRA_DPB_NUM;
+ }
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "H264CodecSetup nOutbufs: %d", pH264Dec->hMFCH264Handle.maxDPBNum);
+
+ pH264Dec->hMFCH264Handle.bConfiguredMFCSrc = OMX_TRUE;
+
+ if (pVideoDec->bReconfigDPB != OMX_TRUE) {
+ pCropRectangle = &(pOutputPort->cropRectangle);
+ pInputPortDefinition = &(pInputPort->portDefinition);
+ pOutputPortDefinition = &(pOutputPort->portDefinition);
+ } else {
+ pCropRectangle = &(pOutputPort->newCropRectangle);
+ pInputPortDefinition = &(pInputPort->newPortDefinition);
+ pOutputPortDefinition = &(pOutputPort->newPortDefinition);
+ }
+
+ pCropRectangle->nTop = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nTop;
+ pCropRectangle->nLeft = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nLeft;
+ pCropRectangle->nWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nWidth;
+ pCropRectangle->nHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nHeight;
+
+ if (pOutputPort->bufferProcessType & BUFFER_COPY) {
+ if ((pVideoDec->bReconfigDPB) ||
+ (pInputPort->portDefinition.format.video.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth) ||
+ (pInputPort->portDefinition.format.video.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight)) {
+ pOutputPort->exceptionFlag = NEED_PORT_DISABLE;
+
+ pInputPortDefinition->format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
+ pInputPortDefinition->format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
+ pInputPortDefinition->format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
+ pInputPortDefinition->format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
+ pOutputPortDefinition->nBufferCountActual = pOutputPort->portDefinition.nBufferCountActual;
+ pOutputPortDefinition->nBufferCountMin = pOutputPort->portDefinition.nBufferCountMin;
+ if (pVideoDec->bReconfigDPB != OMX_TRUE) {
+ Exynos_UpdateFrameSize(pOMXComponent);
+ }
+
+ /** Send Port Settings changed call back **/
+ (*(pExynosComponent->pCallbacks->EventHandler))
+ (pOMXComponent,
+ pExynosComponent->callbackData,
+ OMX_EventPortSettingsChanged, /* The command was completed */
+ OMX_DirOutput, /* This is the port index */
+ 0,
+ NULL);
+ }
+ } else if (pOutputPort->bufferProcessType & BUFFER_SHARE) {
+ if ((pVideoDec->bReconfigDPB) ||
+ (pInputPort->portDefinition.format.video.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth) ||
+ (pInputPort->portDefinition.format.video.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight) ||
+ (pOutputPort->portDefinition.nBufferCountActual != pH264Dec->hMFCH264Handle.maxDPBNum)) {
+
+ pInputPortDefinition->format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
+ pInputPortDefinition->format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
+ pInputPortDefinition->format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
+ pInputPortDefinition->format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
+
+ pOutputPortDefinition->nBufferCountActual = pH264Dec->hMFCH264Handle.maxDPBNum;
+ pOutputPortDefinition->nBufferCountMin = pH264Dec->hMFCH264Handle.maxDPBNum;
+ if (pVideoDec->bReconfigDPB != OMX_TRUE) {
+ Exynos_UpdateFrameSize(pOMXComponent);
+ }
+ pOutputPort->exceptionFlag = NEED_PORT_DISABLE;
+
+ /** Send Port Settings changed call back **/
+ (*(pExynosComponent->pCallbacks->EventHandler))
+ (pOMXComponent,
+ pExynosComponent->callbackData,
+ OMX_EventPortSettingsChanged, /* The command was completed */
+ OMX_DirOutput, /* This is the port index */
+ 0,
+ NULL);
+ }
+ }
+ if ((pVideoDec->bReconfigDPB == OMX_TRUE) ||
+ (pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nWidth) ||
+ (pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nHeight)) {
+ /* Check Crop */
+ pInputPortDefinition->format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
+ pInputPortDefinition->format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
+ pInputPortDefinition->format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
+ pInputPortDefinition->format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
+ if (pVideoDec->bReconfigDPB != OMX_TRUE) {
+ Exynos_UpdateFrameSize(pOMXComponent);
+ }
+
+ /** Send crop info call back **/
+ (*(pExynosComponent->pCallbacks->EventHandler))
+ (pOMXComponent,
+ pExynosComponent->callbackData,
+ OMX_EventPortSettingsChanged, /* The command was completed */
+ OMX_DirOutput, /* This is the port index */
+ OMX_IndexConfigCommonOutputCrop,
+ NULL);
+ }
+
+ ret = OMX_ErrorNone;
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
OMX_ERRORTYPE H264CodecSrcSetup(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcInputData)
{
OMX_ERRORTYPE ret = OMX_ErrorNone;
FunctionIn();
if ((oneFrameSize <= 0) && (pSrcInputData->nFlags & OMX_BUFFERFLAG_EOS)) {
- OMX_BUFFERHEADERTYPE *OMXBuffer = NULL;
- OMXBuffer = Exynos_OutputBufferGetQueue_Direct(pExynosComponent);
- if (OMXBuffer == NULL) {
- ret = OMX_ErrorUndefined;
+ BYPASS_BUFFER_INFO *pBufferInfo = (BYPASS_BUFFER_INFO *)Exynos_OSAL_Malloc(sizeof(BYPASS_BUFFER_INFO));
+ if (pBufferInfo == NULL) {
+ ret = OMX_ErrorInsufficientResources;
goto EXIT;
}
- OMXBuffer->nTimeStamp = pSrcInputData->timeStamp;
- OMXBuffer->nFlags = pSrcInputData->nFlags;
- Exynos_OMX_OutputBufferReturn(pOMXComponent, OMXBuffer);
+ pBufferInfo->nFlags = pSrcInputData->nFlags;
+ pBufferInfo->timeStamp = pSrcInputData->timeStamp;
+ ret = Exynos_OSAL_Queue(&pH264Dec->bypassBufferInfoQ, (void *)pBufferInfo);
+ Exynos_OSAL_SignalSet(pH264Dec->hDestinationStartEvent);
ret = OMX_ErrorNone;
goto EXIT;
}
- if (pVideoDec->bThumbnailMode == OMX_TRUE)
- pDecOps->Set_DisplayDelay(hMFCHandle, 0);
+ if (pVideoDec->bThumbnailMode == OMX_TRUE) {
+ pDecOps->Set_IFrameDecoding(hMFCHandle);
+ }
+
+ if ((pDecOps->Enable_DTSMode != NULL) &&
+ (pVideoDec->bDTSMode == OMX_TRUE))
+ pDecOps->Enable_DTSMode(hMFCHandle);
/* input buffer info */
Exynos_OSAL_Memset(&bufferConf, 0, sizeof(bufferConf));
if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
bufferConf.nSizeImage = pExynosInputPort->portDefinition.format.video.nFrameWidth
* pExynosInputPort->portDefinition.format.video.nFrameHeight * 3 / 2;
- inputBufferNumber = MAX_VIDEO_INPUTBUFFER_NUM;
} else if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
bufferConf.nSizeImage = DEFAULT_MFC_INPUT_BUFFER_SIZE;
- inputBufferNumber = MFC_INPUT_BUFFER_NUM_MAX;
}
+ bufferConf.nPlaneCnt = pExynosInputPort->nPlaneCnt;
+ inputBufferNumber = MAX_INPUTBUFFER_NUM_DYNAMIC;
/* should be done before prepare input buffer */
if (pInbufOps->Enable_Cacheable(hMFCHandle) != VIDEO_ERROR_NONE) {
goto EXIT;
}
- if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
- /* Register input buffer */
- for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) {
- ExynosVideoPlane plane;
- plane.addr = pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[0];
- plane.allocSize = pVideoDec->pMFCDecInputBuffer[i]->bufferSize[0];
- plane.fd = pVideoDec->pMFCDecInputBuffer[i]->fd[0];
- if (pInbufOps->Register(hMFCHandle, &plane, MFC_INPUT_BUFFER_PLANE) != VIDEO_ERROR_NONE) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Register input buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
- }
- } else if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
- /* Register input buffer */
- for (i = 0; i < pExynosInputPort->portDefinition.nBufferCountActual; i++) {
- ExynosVideoPlane plane;
- if (pVideoDec->bDRMPlayerMode == OMX_TRUE) {
- plane.addr = Exynos_OSAL_SharedMemory_IONToVirt(pVideoDec->hSharedMemory, pExynosInputPort->extendBufferHeader[i].OMXBufferHeader->pBuffer);
- } else {
- plane.addr = pExynosInputPort->extendBufferHeader[i].OMXBufferHeader->pBuffer;
- }
- plane.allocSize = pExynosInputPort->extendBufferHeader[i].OMXBufferHeader->nAllocLen;
- plane.fd = pExynosInputPort->extendBufferHeader[i].buf_fd[0];
- if (pInbufOps->Register(hMFCHandle, &plane, MFC_INPUT_BUFFER_PLANE) != VIDEO_ERROR_NONE) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Register input buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
- }
- }
-
/* set output geometry */
Exynos_OSAL_Memset(&bufferConf, 0, sizeof(bufferConf));
+
+#ifdef USE_DUALDPB_MODE
+ switch (pExynosOutputPort->portDefinition.format.video.eColorFormat) {
+ case OMX_COLOR_FormatYUV420SemiPlanar:
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12;
+ break;
+ case OMX_COLOR_FormatYUV420Planar:
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_I420;
+ break;
+ case OMX_SEC_COLOR_FormatYVU420Planar:
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_YV12;
+ break;
+ case OMX_SEC_COLOR_FormatNV21Linear:
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV21;
+ break;
+ case OMX_SEC_COLOR_FormatNV12Tiled:
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
+ break;
+ default:
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
+ break;
+ }
+
+ if (bufferConf.eColorFormat != VIDEO_COLORFORMAT_NV12_TILED) {
+ if ((pDecOps->Enable_DualDPBMode != NULL) &&
+ (pDecOps->Enable_DualDPBMode(hMFCHandle) == VIDEO_ERROR_NONE)) {
+ pVideoDec->bDualDPBMode = OMX_TRUE;
+ pExynosOutputPort->nPlaneCnt = Exynos_OSAL_GetPlaneCount(pExynosOutputPort->portDefinition.format.video.eColorFormat);
+ } else {
+ bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
+ pExynosOutputPort->nPlaneCnt = MFC_DEFAULT_OUTPUT_BUFFER_PLANE;
+ }
+ }
+ pH264Dec->hMFCH264Handle.MFCOutputColorType = bufferConf.eColorFormat;
+#else
pH264Dec->hMFCH264Handle.MFCOutputColorType = bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
+#endif
+ bufferConf.nPlaneCnt = pExynosOutputPort->nPlaneCnt;
if (pOutbufOps->Set_Geometry(hMFCHandle, &bufferConf) != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to set geometry for output buffer");
ret = OMX_ErrorInsufficientResources;
/* input buffer enqueue for header parsing */
Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "oneFrameSize: %d", oneFrameSize);
- if (pInbufOps->Enqueue(hMFCHandle, (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.dataBuffer,
- (unsigned int *)&oneFrameSize, MFC_INPUT_BUFFER_PLANE, pSrcInputData->bufferHeader) != VIDEO_ERROR_NONE) {
+ OMX_U32 nAllocLen[MAX_BUFFER_PLANE] = {pSrcInputData->bufferHeader->nAllocLen, 0, 0};
+ if (pInbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.dataBuffer,
+ (unsigned int **)&pSrcInputData->buffer.singlePlaneBuffer.fd,
+ (unsigned int *)nAllocLen, (unsigned int *)&oneFrameSize,
+ pExynosInputPort->nPlaneCnt, pSrcInputData->bufferHeader) != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to enqueue input buffer for header parsing");
// ret = OMX_ErrorInsufficientResources;
ret = (OMX_ERRORTYPE)OMX_ErrorCodecInit;
goto EXIT;
}
- /* get geometry for output */
- Exynos_OSAL_Memset(&pH264Dec->hMFCH264Handle.codecOutbufConf, 0, sizeof(ExynosVideoGeometry));
- if (pOutbufOps->Get_Geometry(hMFCHandle, &pH264Dec->hMFCH264Handle.codecOutbufConf) != VIDEO_ERROR_NONE) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to get geometry for parsed header info");
- ret = OMX_ErrorInsufficientResources;
+ ret = H264CodecCheckResolutionChange(pOMXComponent);
+ if (ret != OMX_ErrorNone) {
+ H264CodecStop(pOMXComponent, INPUT_PORT_INDEX);
+ pInbufOps->Cleanup_Buffer(hMFCHandle);
goto EXIT;
}
- /* get dpb count */
- pH264Dec->hMFCH264Handle.maxDPBNum = pDecOps->Get_ActualBufferCount(hMFCHandle);
- if (pVideoDec->bThumbnailMode == OMX_FALSE)
- pH264Dec->hMFCH264Handle.maxDPBNum += EXTRA_DPB_NUM;
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "H264CodecSetup nOutbufs: %d", pH264Dec->hMFCH264Handle.maxDPBNum);
-
- pH264Dec->hMFCH264Handle.bConfiguredMFCSrc = OMX_TRUE;
-
- pExynosOutputPort->cropRectangle.nTop = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nTop;
- pExynosOutputPort->cropRectangle.nLeft = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nLeft;
- pExynosOutputPort->cropRectangle.nWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nWidth;
- pExynosOutputPort->cropRectangle.nHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nHeight;
-
- if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
- if ((pExynosInputPort->portDefinition.format.video.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth) ||
- (pExynosInputPort->portDefinition.format.video.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight)) {
- pExynosInputPort->portDefinition.format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
- pExynosInputPort->portDefinition.format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
- pExynosInputPort->portDefinition.format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
- pExynosInputPort->portDefinition.format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
-
- Exynos_UpdateFrameSize(pOMXComponent);
- pExynosOutputPort->exceptionFlag = NEED_PORT_DISABLE;
-
- /** Send Port Settings changed call back **/
- (*(pExynosComponent->pCallbacks->EventHandler))
- (pOMXComponent,
- pExynosComponent->callbackData,
- OMX_EventPortSettingsChanged, /* The command was completed */
- OMX_DirOutput, /* This is the port index */
- 0,
- NULL);
- }
- } else if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
- if ((pExynosInputPort->portDefinition.format.video.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth) ||
- (pExynosInputPort->portDefinition.format.video.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight) ||
- (pExynosOutputPort->portDefinition.nBufferCountActual != pH264Dec->hMFCH264Handle.maxDPBNum)) {
- pExynosInputPort->portDefinition.format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
- pExynosInputPort->portDefinition.format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
- pExynosInputPort->portDefinition.format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
- pExynosInputPort->portDefinition.format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
-
- pExynosOutputPort->portDefinition.nBufferCountActual = pH264Dec->hMFCH264Handle.maxDPBNum - 2;
- pExynosOutputPort->portDefinition.nBufferCountMin = pH264Dec->hMFCH264Handle.maxDPBNum - 2;
-
- Exynos_UpdateFrameSize(pOMXComponent);
- pExynosOutputPort->exceptionFlag = NEED_PORT_DISABLE;
-
- /** Send Port Settings changed call back **/
- (*(pExynosComponent->pCallbacks->EventHandler))
- (pOMXComponent,
- pExynosComponent->callbackData,
- OMX_EventPortSettingsChanged, /* The command was completed */
- OMX_DirOutput, /* This is the port index */
- 0,
- NULL);
- }
- }
- if ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nWidth) ||
- (pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nHeight)) {
- /* Check Crop */
- pExynosInputPort->portDefinition.format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
- pExynosInputPort->portDefinition.format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
- pExynosInputPort->portDefinition.format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
- pExynosInputPort->portDefinition.format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
- Exynos_UpdateFrameSize(pOMXComponent);
-
- /** Send crop info call back **/
- (*(pExynosComponent->pCallbacks->EventHandler))
- (pOMXComponent,
- pExynosComponent->callbackData,
- OMX_EventPortSettingsChanged, /* The command was completed */
- OMX_DirOutput, /* This is the port index */
- OMX_IndexConfigCommonOutputCrop,
- NULL);
- }
-
Exynos_OSAL_SleepMillisec(0);
ret = OMX_ErrorInputDataDecodeYet;
H264CodecStop(pOMXComponent, INPUT_PORT_INDEX);
ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
- int i, nOutbufs;
+ uint32_t i, nOutbufs;
+
+ OMX_U32 nAllocLen[MAX_BUFFER_PLANE] = {0, 0, 0};
+ OMX_U32 dataLen[MAX_BUFFER_PLANE] = {0, 0, 0};
FunctionIn();
- /* get dpb count */
- nOutbufs = pH264Dec->hMFCH264Handle.maxDPBNum;
+ for (i = 0; i < pExynosOutputPort->nPlaneCnt; i++)
+ nAllocLen[i] = pH264Dec->hMFCH264Handle.codecOutbufConf.nAlignPlaneSize[i];
+
+ pOutbufOps->Set_Shareable(hMFCHandle);
if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
/* should be done before prepare output buffer */
ret = OMX_ErrorInsufficientResources;
goto EXIT;
}
- }
-
- pOutbufOps->Set_Shareable(hMFCHandle);
- if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
- ExynosVideoPlane planes[MFC_OUTPUT_BUFFER_PLANE];
- OMX_U32 nAllocLen[MFC_OUTPUT_BUFFER_PLANE] = {0, 0};
- OMX_U32 dataLen[MFC_OUTPUT_BUFFER_PLANE] = {0, 0};
- int plane;
+ /* get dpb count */
+ nOutbufs = pH264Dec->hMFCH264Handle.maxDPBNum;
+ if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
+ ret = OMX_ErrorInsufficientResources;
+ goto EXIT;
+ }
- nAllocLen[0] = calc_plane(pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth,
- pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight);
- nAllocLen[1] = calc_plane(pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth,
- pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight >> 1);
+ ret = Exynos_Allocate_CodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX, nOutbufs, nAllocLen);
+ if (ret != OMX_ErrorNone)
+ goto EXIT;
- if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
- MEMORY_TYPE memoryType;
- if (pVideoDec->bDRMPlayerMode == OMX_TRUE)
- memoryType = SECURE_MEMORY;
- else
- memoryType = NORMAL_MEMORY;
+ ret = H264CodecRegistCodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX, nOutbufs);
+ if (ret != OMX_ErrorNone)
+ goto EXIT;
- /* Register output buffer */
+ /* Enqueue output buffer */
for (i = 0; i < nOutbufs; i++) {
- pVideoDec->pMFCDecOutputBuffer[i] = (CODEC_DEC_BUFFER *)Exynos_OSAL_Malloc(sizeof(CODEC_DEC_BUFFER));
- Exynos_OSAL_Memset(pVideoDec->pMFCDecOutputBuffer[i], 0, sizeof(CODEC_DEC_BUFFER));
-
- for (plane = 0; plane < MFC_OUTPUT_BUFFER_PLANE; plane++) {
- pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[plane] =
- (void *)Exynos_OSAL_SharedMemory_Alloc(pVideoDec->hSharedMemory, nAllocLen[plane], memoryType);
- if (pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[plane] == NULL) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Alloc output buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
- pVideoDec->pMFCDecOutputBuffer[i]->fd[plane] =
- Exynos_OSAL_SharedMemory_VirtToION(pVideoDec->hSharedMemory,
- pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[plane]);
- pVideoDec->pMFCDecOutputBuffer[i]->bufferSize[plane] = nAllocLen[plane];
-
- planes[plane].addr = pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[plane];
- planes[plane].fd = pVideoDec->pMFCDecOutputBuffer[i]->fd[plane];
- planes[plane].allocSize = pVideoDec->pMFCDecOutputBuffer[i]->bufferSize[plane];
- }
-
- if (pOutbufOps->Register(hMFCHandle, planes, MFC_OUTPUT_BUFFER_PLANE) != VIDEO_ERROR_NONE) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Register output buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr,
- (unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, NULL);
+ (unsigned int *)dataLen, pExynosOutputPort->nPlaneCnt, NULL);
+ }
+
+ if (pOutbufOps->Run(hMFCHandle) != VIDEO_ERROR_NONE) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to run output buffer");
+ ret = OMX_ErrorInsufficientResources;
+ goto EXIT;
}
} else if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
+ ExynosVideoPlane planes[MAX_BUFFER_PLANE] = {{0}, {0}, {0}};
+ int plane;
+
+ /* get dpb count */
+ nOutbufs = pExynosOutputPort->portDefinition.nBufferCountActual;
+ if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
+ ret = OMX_ErrorInsufficientResources;
+ goto EXIT;
+ }
+
/* Register output buffer */
/*************/
/* TBD */
#ifdef USE_ANB
if (pExynosOutputPort->bIsANBEnabled == OMX_TRUE) {
for (i = 0; i < pExynosOutputPort->assignedBufferNum; i++) {
- for (plane = 0; plane < MFC_OUTPUT_BUFFER_PLANE; plane++) {
+ for (plane = 0; plane < pExynosOutputPort->nPlaneCnt; plane++) {
planes[plane].fd = pExynosOutputPort->extendBufferHeader[i].buf_fd[plane];
planes[plane].addr = pExynosOutputPort->extendBufferHeader[i].pYUVBuf[plane];
planes[plane].allocSize = nAllocLen[plane];
}
- if (pOutbufOps->Register(hMFCHandle, planes, MFC_OUTPUT_BUFFER_PLANE) != VIDEO_ERROR_NONE) {
+ if (pOutbufOps->Register(hMFCHandle, planes, pExynosOutputPort->nPlaneCnt) != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Register output buffer");
ret = OMX_ErrorInsufficientResources;
goto EXIT;
}
pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pExynosOutputPort->extendBufferHeader[i].pYUVBuf,
- (unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, NULL);
+ (unsigned int *)dataLen, pExynosOutputPort->nPlaneCnt, NULL);
+ }
+
+ if (pOutbufOps->Apply_RegisteredBuffer(hMFCHandle) != VIDEO_ERROR_NONE) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Apply output buffer");
+ ret = OMX_ErrorHardware;
+ goto EXIT;
}
} else {
ret = OMX_ErrorNotImplemented;
#endif
}
- if (pOutbufOps->Run(hMFCHandle) != VIDEO_ERROR_NONE) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to run output buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
-
- if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
- H264CodecStop(pOMXComponent, OUTPUT_PORT_INDEX);
- }
pH264Dec->hMFCH264Handle.bConfiguredMFCDst = OMX_TRUE;
ret = OMX_ErrorNone;
goto EXIT;
}
- if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_ENABLE_THUMBNAIL) == 0) {
- EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
- *pIndexType = OMX_IndexVendorThumbnailMode;
- ret = OMX_ErrorNone;
- }
#ifdef USE_S3D_SUPPORT
- else if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_GET_S3D) == 0) {
+ if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_GET_S3D) == 0) {
*pIndexType = OMX_IndexVendorS3DMode;
ret = OMX_ErrorNone;
+ goto EXIT;
}
#endif
- else {
- ret = Exynos_OMX_VideoDecodeGetExtensionIndex(hComponent, cParameterName, pIndexType);
- }
+
+ ret = Exynos_OMX_VideoDecodeGetExtensionIndex(hComponent, cParameterName, pIndexType);
EXIT:
FunctionOut();
pH264Dec->hMFCH264Handle.bConfiguredMFCDst = OMX_FALSE;
pExynosComponent->bUseFlagEOF = OMX_TRUE;
pExynosComponent->bSaveFlagEOS = OMX_FALSE;
+ pExynosComponent->bBehaviorEOS = OMX_FALSE;
/* H.264 Codec Open */
ret = H264CodecOpen(pH264Dec);
pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
+ pExynosInputPort->nPlaneCnt = MFC_DEFAULT_INPUT_BUFFER_PLANE;
if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
+ OMX_U32 nPlaneSize[MAX_BUFFER_PLANE] = {DEFAULT_MFC_INPUT_BUFFER_SIZE, 0, 0};
Exynos_OSAL_SemaphoreCreate(&pExynosInputPort->codecSemID);
Exynos_OSAL_QueueCreate(&pExynosInputPort->codecBufferQ, MAX_QUEUE_ELEMENTS);
- for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) {
- pVideoDec->pMFCDecInputBuffer[i] = Exynos_OSAL_Malloc(sizeof(CODEC_DEC_BUFFER));
- Exynos_OSAL_Memset(pVideoDec->pMFCDecInputBuffer[i], 0, sizeof(CODEC_DEC_BUFFER));
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecInputBuffer[%d]: 0x%x", i, pVideoDec->pMFCDecInputBuffer[i]);
-
- for (plane = 0; plane < MFC_INPUT_BUFFER_PLANE; plane++) {
- /* Use ION Allocator */
- pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[plane] = (void *)Exynos_OSAL_SharedMemory_Alloc(pVideoDec->hSharedMemory, DEFAULT_MFC_INPUT_BUFFER_SIZE, NORMAL_MEMORY);
- pVideoDec->pMFCDecInputBuffer[i]->fd[plane] = Exynos_OSAL_SharedMemory_VirtToION(pVideoDec->hSharedMemory, pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[plane]);
- pVideoDec->pMFCDecInputBuffer[i]->bufferSize[plane] = DEFAULT_MFC_INPUT_BUFFER_SIZE;
- pVideoDec->pMFCDecInputBuffer[i]->dataSize = 0;
- if (pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[plane] == NULL) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Fail input buffer");
- ret = OMX_ErrorInsufficientResources;
- goto EXIT;
- }
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecInputBuffer[%d]->pVirAddr[%d]: 0x%x", i, plane, pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[plane]);
- }
+ ret = Exynos_Allocate_CodecBuffers(pOMXComponent, INPUT_PORT_INDEX, MFC_INPUT_BUFFER_NUM_MAX, nPlaneSize);
+ if (ret != OMX_ErrorNone)
+ goto EXIT;
+ for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++)
Exynos_CodecBufferEnQueue(pExynosComponent, INPUT_PORT_INDEX, pVideoDec->pMFCDecInputBuffer[i]);
- }
} else if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
/*************/
/* TBD */
/* Does not require any actions. */
}
+ pExynosOutputPort->nPlaneCnt = MFC_DEFAULT_OUTPUT_BUFFER_PLANE;
if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
Exynos_OSAL_SemaphoreCreate(&pExynosOutputPort->codecSemID);
Exynos_OSAL_QueueCreate(&pExynosOutputPort->codecBufferQ, MAX_QUEUE_ELEMENTS);
pExynosComponent->getAllDelayBuffer = OMX_FALSE;
-#if 0//defined(USE_CSC_GSCALER)
- csc_method = CSC_METHOD_HW; //in case of Use ION buffer.
+ Exynos_OSAL_QueueCreate(&pH264Dec->bypassBufferInfoQ, QUEUE_ELEMENTS);
+
+#ifdef USE_CSC_HW
+ csc_method = CSC_METHOD_HW;
#endif
if (pVideoDec->bDRMPlayerMode == OMX_TRUE) {
pVideoDec->csc_handle = csc_init(CSC_METHOD_HW);
pVideoDec->csc_handle = NULL;
}
+ Exynos_OSAL_QueueTerminate(&pH264Dec->bypassBufferInfoQ);
+
Exynos_OSAL_SignalTerminate(pH264Dec->hDestinationStartEvent);
pH264Dec->hDestinationStartEvent = NULL;
pH264Dec->bDestinationStart = OMX_FALSE;
pH264Dec->bSourceStart = OMX_FALSE;
if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
- for (i = 0; i < MFC_OUTPUT_BUFFER_NUM_MAX; i++) {
- if (pVideoDec->pMFCDecOutputBuffer[i] != NULL) {
- for (plane = 0; plane < MFC_OUTPUT_BUFFER_PLANE; plane++) {
- if (pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[plane] != NULL)
- Exynos_OSAL_SharedMemory_Free(pVideoDec->hSharedMemory, pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[plane]);
- }
-
- Exynos_OSAL_Free(pVideoDec->pMFCDecOutputBuffer[i]);
- pVideoDec->pMFCDecOutputBuffer[i] = NULL;
- }
- }
-
+ Exynos_Free_CodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX);
Exynos_OSAL_QueueTerminate(&pExynosOutputPort->codecBufferQ);
Exynos_OSAL_SemaphoreTerminate(pExynosOutputPort->codecSemID);
} else if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
}
if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
- for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) {
- if (pVideoDec->pMFCDecInputBuffer[i] != NULL) {
- for (plane = 0; plane < MFC_INPUT_BUFFER_PLANE; plane++) {
- if (pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[plane] != NULL)
- Exynos_OSAL_SharedMemory_Free(pVideoDec->hSharedMemory, pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[plane]);
- }
- Exynos_OSAL_Free(pVideoDec->pMFCDecInputBuffer[i]);
- pVideoDec->pMFCDecInputBuffer[i] = NULL;
- }
- }
-
+ Exynos_Free_CodecBuffers(pOMXComponent, INPUT_PORT_INDEX);
Exynos_OSAL_QueueTerminate(&pExynosInputPort->codecBufferQ);
Exynos_OSAL_SemaphoreTerminate(pExynosInputPort->codecSemID);
} else if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
}
H264CodecClose(pH264Dec);
+ Exynos_ResetAllPortConfig(pOMXComponent);
+
EXIT:
FunctionOut();
OMX_ERRORTYPE Exynos_H264Dec_SrcIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcInputData)
{
- OMX_ERRORTYPE ret = OMX_ErrorNone;
- EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
- EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
- EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
- void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
- EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
- EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+ EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
+ void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
+ EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
+ EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
+
+ OMX_BUFFERHEADERTYPE tempBufferHeader;
+ void *pPrivate = NULL;
+
OMX_U32 oneFrameSize = pSrcInputData->dataLen;
OMX_BOOL bInStartCode = OMX_FALSE;
- ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
- ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
- ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
- ExynosVideoErrorType codecReturn = VIDEO_ERROR_NONE;
+
+ ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
+ ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
+ ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
+ ExynosVideoErrorType codecReturn = VIDEO_ERROR_NONE;
+
int i;
FunctionIn();
pDecOps->Set_FrameTag(hMFCHandle, pH264Dec->hMFCH264Handle.indexTimestamp);
pH264Dec->hMFCH264Handle.indexTimestamp++;
pH264Dec->hMFCH264Handle.indexTimestamp %= MAX_TIMESTAMP;
-
+#ifdef USE_QOS_CTRL
+ if ((pVideoDec->bQosChanged == OMX_TRUE) &&
+ (pDecOps->Set_QosRatio != NULL)) {
+ pDecOps->Set_QosRatio(hMFCHandle, pVideoDec->nQosRatio);
+ pVideoDec->bQosChanged = OMX_FALSE;
+ }
+#endif
/* queue work for input buffer */
Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "oneFrameSize: %d, bufferHeader: 0x%x, dataBuffer: 0x%x", oneFrameSize, pSrcInputData->bufferHeader, pSrcInputData->buffer.singlePlaneBuffer.dataBuffer);
- codecReturn = pInbufOps->Enqueue(hMFCHandle, (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.dataBuffer,
- (unsigned int *)&oneFrameSize, MFC_INPUT_BUFFER_PLANE, pSrcInputData->bufferHeader);
+ OMX_U32 nAllocLen[MAX_BUFFER_PLANE] = {pSrcInputData->bufferHeader->nAllocLen, 0, 0};
+
+ if (pExynosInputPort->bufferProcessType == BUFFER_COPY) {
+ tempBufferHeader.nFlags = pSrcInputData->nFlags;
+ tempBufferHeader.nTimeStamp = pSrcInputData->timeStamp;
+ pPrivate = (void *)&tempBufferHeader;
+ } else {
+ pPrivate = (void *)pSrcInputData->bufferHeader;
+ }
+ codecReturn = pInbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.dataBuffer,
+ (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.fd,
+ (unsigned int *)nAllocLen, (unsigned int *)&oneFrameSize,
+ pExynosInputPort->nPlaneCnt, pPrivate);
if (codecReturn != VIDEO_ERROR_NONE) {
ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
ExynosVideoBuffer *pVideoBuffer;
+ ExynosVideoBuffer videoBuffer;
FunctionIn();
- pVideoBuffer = pInbufOps->Dequeue(hMFCHandle);
+ if (pInbufOps->ExtensionDequeue(hMFCHandle, &videoBuffer) == VIDEO_ERROR_NONE)
+ pVideoBuffer = &videoBuffer;
+ else
+ pVideoBuffer = NULL;
pSrcOutputData->dataLen = 0;
pSrcOutputData->usedDataLen = 0;
pSrcOutputData->remainDataLen = 0;
- pSrcOutputData->nFlags = 0;
- pSrcOutputData->timeStamp = 0;
+ pSrcOutputData->nFlags = 0;
+ pSrcOutputData->timeStamp = 0;
+ pSrcOutputData->bufferHeader = NULL;
if (pVideoBuffer == NULL) {
pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer = NULL;
pSrcOutputData->allocSize = 0;
pSrcOutputData->pPrivate = NULL;
- pSrcOutputData->bufferHeader = NULL;
} else {
pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer = pVideoBuffer->planes[0].addr;
pSrcOutputData->buffer.singlePlaneBuffer.fd = pVideoBuffer->planes[0].fd;
pSrcOutputData->allocSize = pVideoBuffer->planes[0].allocSize;
if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
- int i = 0;
- while (pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer != pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[0]) {
- if (i >= MFC_INPUT_BUFFER_NUM_MAX) {
- Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Can not find buffer");
- ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
- goto EXIT;
+ int i;
+ for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) {
+ if (pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer ==
+ pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[0]) {
+ pVideoDec->pMFCDecInputBuffer[i]->dataSize = 0;
+ pSrcOutputData->pPrivate = pVideoDec->pMFCDecInputBuffer[i];
+ break;
}
- i++;
}
- pVideoDec->pMFCDecInputBuffer[i]->dataSize = 0;
- pSrcOutputData->pPrivate = pVideoDec->pMFCDecInputBuffer[i];
+
+ if (i >= MFC_INPUT_BUFFER_NUM_MAX) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Can not find buffer");
+ ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
+ goto EXIT;
+ }
}
/* For Share Buffer */
- pSrcOutputData->bufferHeader = (OMX_BUFFERHEADERTYPE*)pVideoBuffer->pPrivate;
+ if (pExynosInputPort->bufferProcessType == BUFFER_SHARE)
+ pSrcOutputData->bufferHeader = (OMX_BUFFERHEADERTYPE*)pVideoBuffer->pPrivate;
}
ret = OMX_ErrorNone;
OMX_ERRORTYPE Exynos_H264Dec_DstIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pDstInputData)
{
- OMX_ERRORTYPE ret = OMX_ErrorNone;
- EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
- EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
- EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
- void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
- EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
- ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
- ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
- OMX_U32 dataLen[MFC_OUTPUT_BUFFER_PLANE] = {0,};
- ExynosVideoErrorType codecReturn = VIDEO_ERROR_NONE;
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+ EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
+ void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
+ EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
+
+ ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
+ ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
+ ExynosVideoErrorType codecReturn = VIDEO_ERROR_NONE;
+
+ OMX_U32 dataLen[MAX_BUFFER_PLANE] = {0, 0, 0};
+ uint32_t i;
FunctionIn();
goto EXIT;
}
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x", __FUNCTION__, __LINE__,
- pDstInputData->buffer.multiPlaneBuffer.dataBuffer[0],
- pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1]);
+ for (i = 0; i < pExynosOutputPort->nPlaneCnt; i++) {
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[%d]: 0x%x", __FUNCTION__, __LINE__, i,
+ pDstInputData->buffer.multiPlaneBuffer.dataBuffer[i]);
+ }
codecReturn = pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
- (unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
+ (unsigned int *)dataLen, pExynosOutputPort->nPlaneCnt, pDstInputData->bufferHeader);
if (codecReturn != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
}
while (1) {
- if ((pVideoBuffer = pOutbufOps->Dequeue(hMFCHandle)) == NULL) {
+ pVideoBuffer = pOutbufOps->Dequeue(hMFCHandle);
+ if (pVideoBuffer == (ExynosVideoBuffer *)VIDEO_ERROR_DQBUF_EIO) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "HW is not available");
+ ret = OMX_ErrorHardware;
+ goto EXIT;
+ }
+
+ if (pVideoBuffer == NULL) {
ret = OMX_ErrorNone;
goto EXIT;
}
if ((displayStatus == VIDEO_FRAME_STATUS_DISPLAY_DECODING) ||
(displayStatus == VIDEO_FRAME_STATUS_DISPLAY_ONLY) ||
(displayStatus == VIDEO_FRAME_STATUS_CHANGE_RESOL) ||
+ (displayStatus == VIDEO_FRAME_STATUS_DECODING_FINISHED) ||
+ (displayStatus == VIDEO_FRAME_STATUS_ENABLED_S3D) ||
(CHECK_PORT_BEING_FLUSHED(pExynosOutputPort))) {
ret = OMX_ErrorNone;
break;
}
}
+
+#ifdef USE_S3D_SUPPORT
+ /* Check Whether frame packing information is available */
+ if ((pH264Dec->hMFCH264Handle.S3DFPArgmtType == OMX_SEC_FPARGMT_INVALID) &&
+ (pVideoDec->bThumbnailMode == OMX_FALSE) &&
+ ((displayStatus == VIDEO_FRAME_STATUS_DISPLAY_ONLY) ||
+ (displayStatus == VIDEO_FRAME_STATUS_DISPLAY_DECODING) ||
+ (displayStatus == VIDEO_FRAME_STATUS_ENABLED_S3D))) {
+ if (H264CodecCheckFramePacking(pOMXComponent) != OMX_TRUE) {
+ ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
+ goto EXIT;
+ }
+ }
+#endif
+
+ if ((pVideoDec->bThumbnailMode == OMX_FALSE) &&
+ ((displayStatus == VIDEO_FRAME_STATUS_CHANGE_RESOL) ||
+ (displayStatus == VIDEO_FRAME_STATUS_ENABLED_S3D))) {
+ if (pVideoDec->bReconfigDPB != OMX_TRUE) {
+ pExynosOutputPort->exceptionFlag = NEED_PORT_FLUSH;
+ pVideoDec->bReconfigDPB = OMX_TRUE;
+ H264CodecCheckResolutionChange(pOMXComponent);
+ pVideoDec->csc_set_format = OMX_FALSE;
+#ifdef USE_S3D_SUPPORT
+ pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_INVALID;
+#endif
+ }
+ ret = OMX_ErrorNone;
+ goto EXIT;
+ }
+
pH264Dec->hMFCH264Handle.outputIndexTimestamp++;
pH264Dec->hMFCH264Handle.outputIndexTimestamp %= MAX_TIMESTAMP;
pDstOutputData->allocSize = pDstOutputData->dataLen = 0;
- for (plane = 0; plane < MFC_OUTPUT_BUFFER_PLANE; plane++) {
+ for (plane = 0; plane < pExynosOutputPort->nPlaneCnt; plane++) {
pDstOutputData->buffer.multiPlaneBuffer.dataBuffer[plane] = pVideoBuffer->planes[plane].addr;
pDstOutputData->buffer.multiPlaneBuffer.fd[plane] = pVideoBuffer->planes[plane].fd;
pDstOutputData->allocSize += pVideoBuffer->planes[plane].allocSize;
}
pDstOutputData->usedDataLen = 0;
pDstOutputData->pPrivate = pVideoBuffer;
+ if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
+ int i = 0;
+ pDstOutputData->pPrivate = NULL;
+ for (i = 0; i < MFC_OUTPUT_BUFFER_NUM_MAX; i++) {
+ if (pDstOutputData->buffer.multiPlaneBuffer.dataBuffer[0] ==
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0]) {
+ pDstOutputData->pPrivate = pVideoDec->pMFCDecOutputBuffer[i];
+ break;
+ }
+ }
+
+ if (pDstOutputData->pPrivate == NULL) {
+ Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Can not find buffer");
+ ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
+ goto EXIT;
+ }
+ }
+
/* For Share Buffer */
pDstOutputData->bufferHeader = (OMX_BUFFERHEADERTYPE *)pVideoBuffer->pPrivate;
case VIDEO_COLORFORMAT_NV12:
pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420SemiPlanar;
break;
+#ifdef USE_DUALDPB_MODE
+ case VIDEO_COLORFORMAT_I420:
+ pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420Planar;
+ break;
+ case VIDEO_COLORFORMAT_YV12:
+ pBufferInfo->ColorFormat = OMX_SEC_COLOR_FormatYVU420Planar;
+ break;
+ case VIDEO_COLORFORMAT_NV21:
+ pBufferInfo->ColorFormat = OMX_SEC_COLOR_FormatNV21Linear;
+ break;
+#endif
case VIDEO_COLORFORMAT_NV12_TILED:
default:
pBufferInfo->ColorFormat = OMX_SEC_COLOR_FormatNV12Tiled;
break;
}
-#ifdef USE_S3D_SUPPORT
- /* Check Whether frame packing information is available */
- if (pExynosOutputPort->bufferProcessType & BUFFER_COPY &&
- pVideoDec->bThumbnailMode == OMX_FALSE &&
- pH264Dec->hMFCH264Handle.S3DFPArgmtType == OMX_SEC_FPARGMT_NONE) {
- H264CodecCheckFramePacking(pOMXComponent);
- }
-#endif
-
indexTimestamp = pDecOps->Get_FrameTag(hMFCHandle);
Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "out indexTimestamp: %d", indexTimestamp);
if ((indexTimestamp < 0) || (indexTimestamp >= MAX_TIMESTAMP)) {
if ((pExynosComponent->checkTimeStamp.needSetStartTimeStamp != OMX_TRUE) &&
(pExynosComponent->checkTimeStamp.needCheckStartTimeStamp != OMX_TRUE)) {
- pDstOutputData->timeStamp = pExynosComponent->timeStamp[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
- pDstOutputData->nFlags = pExynosComponent->nFlags[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "missing out indexTimestamp: %d", indexTimestamp);
+ if (indexTimestamp == INDEX_AFTER_EOS) {
+ pDstOutputData->timeStamp = 0x00;
+ pDstOutputData->nFlags = 0x00;
+ } else {
+ pDstOutputData->timeStamp = pExynosComponent->timeStamp[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
+ pDstOutputData->nFlags = pExynosComponent->nFlags[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
+ pExynosComponent->nFlags[pH264Dec->hMFCH264Handle.outputIndexTimestamp] = 0x00;
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "missing out indexTimestamp: %d", indexTimestamp);
+ }
} else {
pDstOutputData->timeStamp = 0x00;
pDstOutputData->nFlags = 0x00;
} else {
/* For timestamp correction. if mfc support frametype detect */
Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "disp_pic_frame_type: %d", pVideoBuffer->frameType);
-#ifdef NEED_TIMESTAMP_REORDER
- if ((pVideoBuffer->frameType == VIDEO_FRAME_I)) {
- pDstOutputData->timeStamp = pExynosComponent->timeStamp[indexTimestamp];
- pDstOutputData->nFlags = pExynosComponent->nFlags[indexTimestamp];
- pH264Dec->hMFCH264Handle.outputIndexTimestamp = indexTimestamp;
- } else {
- pDstOutputData->timeStamp = pExynosComponent->timeStamp[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
- pDstOutputData->nFlags = pExynosComponent->nFlags[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
+
+ /* NEED TIMESTAMP REORDER */
+ if (pVideoDec->bDTSMode == OMX_TRUE) {
+ if ((pVideoBuffer->frameType == VIDEO_FRAME_I) ||
+ ((pVideoBuffer->frameType == VIDEO_FRAME_OTHERS) &&
+ ((pExynosComponent->nFlags[indexTimestamp] & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS)) ||
+ (pExynosComponent->checkTimeStamp.needCheckStartTimeStamp == OMX_TRUE))
+ pH264Dec->hMFCH264Handle.outputIndexTimestamp = indexTimestamp;
+ else
+ indexTimestamp = pH264Dec->hMFCH264Handle.outputIndexTimestamp;
}
-#else
+
pDstOutputData->timeStamp = pExynosComponent->timeStamp[indexTimestamp];
pDstOutputData->nFlags = pExynosComponent->nFlags[indexTimestamp];
-#endif
+ pExynosComponent->nFlags[indexTimestamp] = 0x00;
+
Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "timestamp %lld us (%.2f secs), indexTimestamp: %d, nFlags: 0x%x", pDstOutputData->timeStamp, pDstOutputData->timeStamp / 1E6, indexTimestamp, pDstOutputData->nFlags);
}
- if ((displayStatus == VIDEO_FRAME_STATUS_CHANGE_RESOL) ||
+ if ((displayStatus == VIDEO_FRAME_STATUS_DECODING_FINISHED) ||
((pDstOutputData->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS)) {
Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "displayStatus:%d, nFlags0x%x", displayStatus, pDstOutputData->nFlags);
pDstOutputData->remainDataLen = 0;
+
+ if (((pDstOutputData->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) &&
+ (pExynosComponent->bBehaviorEOS == OMX_TRUE)) {
+ pDstOutputData->remainDataLen = bufferGeometry->nFrameWidth * bufferGeometry->nFrameHeight * 3 / 2;
+ pExynosComponent->bBehaviorEOS = OMX_FALSE;
+ }
} else {
pDstOutputData->remainDataLen = bufferGeometry->nFrameWidth * bufferGeometry->nFrameHeight * 3 / 2;
}
Exynos_OSAL_SignalWait(pH264Dec->hDestinationStartEvent, DEF_MAX_WAIT_TIME);
Exynos_OSAL_SignalReset(pH264Dec->hDestinationStartEvent);
}
+ if (Exynos_OSAL_GetElemNum(&pH264Dec->bypassBufferInfoQ) > 0) {
+ BYPASS_BUFFER_INFO *pBufferInfo = (BYPASS_BUFFER_INFO *)Exynos_OSAL_Dequeue(&pH264Dec->bypassBufferInfoQ);
+ if (pBufferInfo == NULL) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
+
+ pDstInputData->bufferHeader->nFlags = pBufferInfo->nFlags;
+ pDstInputData->bufferHeader->nTimeStamp = pBufferInfo->timeStamp;
+ Exynos_OMX_OutputBufferReturn(pOMXComponent, pDstInputData->bufferHeader);
+ Exynos_OSAL_Free(pBufferInfo);
+
+ ret = OMX_ErrorNone;
+ goto EXIT;
+ }
}
if (pH264Dec->hMFCH264Handle.bConfiguredMFCDst == OMX_TRUE) {
ret = Exynos_H264Dec_DstIn(pOMXComponent, pDstInputData);
Exynos_OSAL_SignalWait(pH264Dec->hDestinationStartEvent, DEF_MAX_WAIT_TIME);
Exynos_OSAL_SignalReset(pH264Dec->hDestinationStartEvent);
}
+
+ if (Exynos_OSAL_GetElemNum(&pH264Dec->bypassBufferInfoQ) > 0) {
+ EXYNOS_OMX_DATABUFFER *dstOutputUseBuffer = &pExynosOutputPort->way.port2WayDataBuffer.outputDataBuffer;
+ OMX_BUFFERHEADERTYPE *pOMXBuffer = NULL;
+ BYPASS_BUFFER_INFO *pBufferInfo = NULL;
+
+ if (dstOutputUseBuffer->dataValid == OMX_FALSE) {
+ pOMXBuffer = Exynos_OutputBufferGetQueue_Direct(pExynosComponent);
+ if (pOMXBuffer == NULL) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
+ } else {
+ pOMXBuffer = dstOutputUseBuffer->bufferHeader;
+ }
+
+ pBufferInfo = Exynos_OSAL_Dequeue(&pH264Dec->bypassBufferInfoQ);
+ if (pBufferInfo == NULL) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
+
+ pOMXBuffer->nFlags = pBufferInfo->nFlags;
+ pOMXBuffer->nTimeStamp = pBufferInfo->timeStamp;
+ Exynos_OMX_OutputBufferReturn(pOMXComponent, pOMXBuffer);
+ Exynos_OSAL_Free(pBufferInfo);
+
+ dstOutputUseBuffer->dataValid = OMX_FALSE;
+
+ ret = OMX_ErrorNone;
+ goto EXIT;
+ }
}
ret = Exynos_H264Dec_DstOut(pOMXComponent, pDstOutputData);
if ((ret != OMX_ErrorNone) && (pExynosComponent->currentState == OMX_StateExecuting)) {
pVideoDec->bDRMPlayerMode = bDRMPlayerMode;
#ifdef USE_S3D_SUPPORT
- pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_NONE;
+ pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_INVALID;
#endif
/* Set componentVersion */
pVideoDec->exynos_checkInputFrame = &Check_H264_Frame;
pVideoDec->exynos_codec_getCodecInputPrivateData = &GetCodecInputPrivateData;
pVideoDec->exynos_codec_getCodecOutputPrivateData = &GetCodecOutputPrivateData;
+ pVideoDec->exynos_codec_reconfigAllBuffers = &H264CodecReconfigAllBuffers;
pVideoDec->hSharedMemory = Exynos_OSAL_SharedMemory_Open();
if (pVideoDec->hSharedMemory == NULL) {