summaryrefslogtreecommitdiff
path: root/exynos_omx
diff options
context:
space:
mode:
authorSeungBeom Kim <sbcrux.kim@samsung.com>2013-07-31 13:46:35 +0900
committerjp abgrall <jpa@google.com>2013-08-30 18:34:46 +0000
commit3b1c2e30b8c73bb51c3e2c93504e3571ab851268 (patch)
tree50ca3fba5eea62a4d25f6c8044628c77fed895ca /exynos_omx
parent07ded9cf974a05e16be7797a9932f03b9fe70010 (diff)
downloadexynos5-3b1c2e30b8c73bb51c3e2c93504e3571ab851268.tar.gz
exynos_omx: multi_thread: Add dynamic DPB change scheme.
- Decode output port supported StoreMetaDataBuffer. - Dynamic DPB change supported. Change-Id: If23a5eb5cc6fef3781c4a45fb06fe7eab41b1b5b Signed-off-by: SeungBeom Kim <sbcrux.kim@samsung.com> Bug: 10192533
Diffstat (limited to 'exynos_omx')
-rw-r--r--exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/dec/src/ExynosVideoDecoder.c366
-rw-r--r--exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/enc/src/ExynosVideoEncoder.c46
-rw-r--r--exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoApi.h18
-rw-r--r--exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoDec.h4
-rw-r--r--exynos_omx/openmax/exynos_omx/component/common/Exynos_OMX_Baseport.h2
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/Android.mk4
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.c67
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.h4
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_VdecControl.c54
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/h264/Android.mk3
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/h264/Exynos_OMX_H264dec.c108
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Android.mk3
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Exynos_OMX_Mpeg4dec.c110
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Android.mk3
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Exynos_OMX_Vp8dec.c112
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/enc/Exynos_OMX_Venc.c6
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/enc/h264/Android.mk3
-rw-r--r--exynos_omx/openmax/exynos_omx/component/video/enc/mpeg4/Android.mk3
-rw-r--r--exynos_omx/openmax/exynos_omx/include/exynos/Exynos_OMX_Def.h1
-rw-r--r--exynos_omx/openmax/exynos_omx/osal/Android.mk1
-rw-r--r--exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.cpp302
-rw-r--r--exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.h27
22 files changed, 1042 insertions, 205 deletions
diff --git a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/dec/src/ExynosVideoDecoder.c b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/dec/src/ExynosVideoDecoder.c
index abf7ae7..12275ee 100644
--- a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/dec/src/ExynosVideoDecoder.c
+++ b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/dec/src/ExynosVideoDecoder.c
@@ -38,6 +38,7 @@
#include <sys/poll.h>
+#include "ion.h"
#include "ExynosVideoApi.h"
#include "ExynosVideoDec.h"
#include "OMX_Core.h"
@@ -46,6 +47,8 @@
#define LOG_TAG "ExynosVideoDecoder"
#include <utils/Log.h>
+#define MAX_OUTPUTBUFFER_COUNT 32
+
/*
* [Common] __CodingType_To_V4L2PixelFormat
*/
@@ -161,6 +164,13 @@ static void *MFC_Decoder_Init(int nMemoryType)
}
pCtx->pOutMutex = (void*)pMutex;
+ pCtx->hIONHandle = (void*)ion_client_create();
+ pCtx->nPrivateDataShareFD = ion_alloc((ion_client)pCtx->hIONHandle,
+ sizeof(PrivateDataShareBuffer) * VIDEO_BUFFER_MAX_NUM, 0, ION_HEAP_SYSTEM_MASK, ION_FLAG_CACHED);
+ pCtx->nPrivateDataShareAddress =
+ ion_map(pCtx->nPrivateDataShareFD, sizeof(PrivateDataShareBuffer) * VIDEO_BUFFER_MAX_NUM, 0);
+ memset(pCtx->nPrivateDataShareAddress, -1, sizeof(PrivateDataShareBuffer) * VIDEO_BUFFER_MAX_NUM);
+
return (void *)pCtx;
EXIT_QUERYCAP_FAIL:
@@ -200,6 +210,10 @@ static ExynosVideoErrorType MFC_Decoder_Finalize(void *pHandle)
goto EXIT;
}
+ ion_unmap(pCtx->nPrivateDataShareAddress, sizeof(PrivateDataShareBuffer) * VIDEO_BUFFER_MAX_NUM);
+ ion_free(pCtx->nPrivateDataShareFD);
+ ion_client_destroy((ion_client)pCtx->hIONHandle);
+
if (pCtx->pOutMutex != NULL) {
pMutex = (pthread_mutex_t*)pCtx->pOutMutex;
pthread_mutex_destroy(pMutex);
@@ -955,9 +969,8 @@ static ExynosVideoErrorType MFC_Decoder_Setup_Outbuf(
}
if (nBufferCount == 0) {
- ALOGE("%s: Buffer count must be greater than 0", __func__);
- ret = VIDEO_ERROR_BADPARAM;
- goto EXIT;
+ nBufferCount = MAX_OUTPUTBUFFER_COUNT;
+ ALOGV("%s: Change buffer count %d", __func__, nBufferCount);
}
ALOGV("%s: setting up outbufs (%d) shared=%s\n", __func__, nBufferCount,
@@ -1025,8 +1038,10 @@ static ExynosVideoErrorType MFC_Decoder_Setup_Outbuf(
}
pCtx->pOutbuf[i].pGeometry = &pCtx->outbufGeometry;
- pCtx->pOutbuf[i].bQueued = VIDEO_FALSE;
- pCtx->pOutbuf[i].bRegistered = VIDEO_TRUE;
+ pCtx->pOutbuf[i].bQueued = VIDEO_FALSE;
+ pCtx->pOutbuf[i].bSlotUsed = VIDEO_FALSE;
+ pCtx->pOutbuf[i].nIndexUseCnt = 0;
+ pCtx->pOutbuf[i].bRegistered = VIDEO_TRUE;
}
}
@@ -1165,7 +1180,9 @@ static ExynosVideoErrorType MFC_Decoder_Stop_Outbuf(void *pHandle)
}
for (i = 0; i < pCtx->nOutbufs; i++) {
- pCtx->pOutbuf[i].bQueued = VIDEO_FALSE;
+ pCtx->pOutbuf[i].bQueued = VIDEO_FALSE;
+ pCtx->pOutbuf[i].bSlotUsed = VIDEO_FALSE;
+ pCtx->pOutbuf[i].nIndexUseCnt = 0;
}
EXIT:
@@ -1442,7 +1459,6 @@ static ExynosVideoErrorType MFC_Decoder_Enqueue_Inbuf(
buf.index = index;
pCtx->pInbuf[buf.index].bQueued = VIDEO_TRUE;
- pthread_mutex_unlock(pMutex);
if (pCtx->bShareInbuf == VIDEO_TRUE) {
buf.memory = pCtx->nMemoryType;
@@ -1472,15 +1488,20 @@ static ExynosVideoErrorType MFC_Decoder_Enqueue_Inbuf(
!!(buf.flags & V4L2_BUF_FLAG_LAST_FRAME));
}
+ pCtx->pInbuf[buf.index].pPrivate = pPrivate;
+
+ pthread_mutex_unlock(pMutex);
+
if (exynos_v4l2_qbuf(pCtx->hDec, &buf) != 0) {
ALOGE("%s: Failed to enqueue input buffer", __func__);
- pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_lock(pMutex);
+ pCtx->pInbuf[buf.index].pPrivate = NULL;
+ pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
ret = VIDEO_ERROR_APIFAIL;
goto EXIT;
}
- pCtx->pInbuf[buf.index].pPrivate = pPrivate;
-
EXIT:
return ret;
}
@@ -1532,7 +1553,6 @@ static ExynosVideoErrorType MFC_Decoder_Enqueue_Outbuf(
}
buf.index = index;
pCtx->pOutbuf[buf.index].bQueued = VIDEO_TRUE;
- pthread_mutex_unlock(pMutex);
if (pCtx->bShareOutbuf == VIDEO_TRUE) {
buf.memory = pCtx->nMemoryType;
@@ -1555,15 +1575,20 @@ static ExynosVideoErrorType MFC_Decoder_Enqueue_Outbuf(
buf.memory = V4L2_MEMORY_MMAP;
}
+ pCtx->pOutbuf[buf.index].pPrivate = pPrivate;
+
+ pthread_mutex_unlock(pMutex);
+
if (exynos_v4l2_qbuf(pCtx->hDec, &buf) != 0) {
ALOGE("%s: Failed to enqueue output buffer", __func__);
- pCtx->pOutbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_lock(pMutex);
+ pCtx->pOutbuf[buf.index].pPrivate = NULL;
+ pCtx->pOutbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
ret = VIDEO_ERROR_APIFAIL;
goto EXIT;
}
- pCtx->pOutbuf[buf.index].pPrivate = pPrivate;
-
EXIT:
return ret;
}
@@ -1575,6 +1600,7 @@ static ExynosVideoBuffer *MFC_Decoder_Dequeue_Inbuf(void *pHandle)
{
ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
ExynosVideoBuffer *pInbuf = NULL;
+ pthread_mutex_t *pMutex = NULL;
struct v4l2_buffer buf;
@@ -1602,12 +1628,17 @@ static ExynosVideoBuffer *MFC_Decoder_Dequeue_Inbuf(void *pHandle)
goto EXIT;
}
+ pMutex = (pthread_mutex_t*)pCtx->pInMutex;
+ pthread_mutex_lock(pMutex);
+
pInbuf = &pCtx->pInbuf[buf.index];
pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
if (pCtx->bStreamonInbuf == VIDEO_FALSE)
pInbuf = NULL;
+ pthread_mutex_unlock(pMutex);
+
EXIT:
return pInbuf;
}
@@ -1619,6 +1650,7 @@ static ExynosVideoBuffer *MFC_Decoder_Dequeue_Outbuf(void *pHandle)
{
ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
ExynosVideoBuffer *pOutbuf = NULL;
+ pthread_mutex_t *pMutex = NULL;
struct v4l2_buffer buf;
int value;
@@ -1652,6 +1684,9 @@ static ExynosVideoBuffer *MFC_Decoder_Dequeue_Outbuf(void *pHandle)
goto EXIT;
}
+ pMutex = (pthread_mutex_t*)pCtx->pOutMutex;
+ pthread_mutex_lock(pMutex);
+
pOutbuf = &pCtx->pOutbuf[buf.index];
exynos_v4l2_g_ctrl(pCtx->hDec, V4L2_CID_MPEG_MFC51_VIDEO_DISPLAY_STATUS, &value);
@@ -1665,7 +1700,7 @@ static ExynosVideoBuffer *MFC_Decoder_Dequeue_Outbuf(void *pHandle)
break;
case 2:
pOutbuf->displayStatus = VIDEO_FRAME_STATUS_DISPLAY_ONLY;
- break;
+ break;
case 3:
pOutbuf->displayStatus = VIDEO_FRAME_STATUS_CHANGE_RESOL;
break;
@@ -1691,6 +1726,8 @@ static ExynosVideoBuffer *MFC_Decoder_Dequeue_Outbuf(void *pHandle)
pOutbuf->bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
+
EXIT:
return pOutbuf;
}
@@ -1736,6 +1773,302 @@ EXIT:
}
/*
+ * [Decoder Buffer OPS] FindIndex (Output)
+ */
+static int MFC_Decoder_FindEmpty_Outbuf(void *pHandle)
+{
+ ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
+ int nIndex = -1;
+
+ if (pCtx == NULL) {
+ ALOGE("%s: Video context info must be supplied", __func__);
+ goto EXIT;
+ }
+
+ for (nIndex = 0; nIndex < pCtx->nOutbufs; nIndex++) {
+ if ((pCtx->pOutbuf[nIndex].bQueued == VIDEO_FALSE) &&
+ (pCtx->pOutbuf[nIndex].bSlotUsed == VIDEO_FALSE))
+ break;
+ }
+
+ if (nIndex == pCtx->nOutbufs)
+ nIndex = -1;
+
+EXIT:
+ return nIndex;
+}
+
+/*
+ * [Decoder Buffer OPS] BufferIndexFree (Output)
+ */
+void MFC_Decoder_BufferIndexFree_Outbuf(void *pHandle, PrivateDataShareBuffer *pPDSB, int index)
+{
+ ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
+ int i, j;
+
+ ALOGV("De-queue buf.index:%d", index);
+ ALOGV("pOutbuf fd:%d", pCtx->pOutbuf[index].planes[0].fd);
+
+ if (pCtx->pOutbuf[index].nIndexUseCnt == 0) {
+ pCtx->pOutbuf[index].bSlotUsed = VIDEO_FALSE;
+ }
+
+ for (i = 0; pPDSB->dpbFD[i].fd > -1; i++) {
+ ALOGV("pPDSB->dpbFD[%d].fd:%d", i, pPDSB->dpbFD[i].fd);
+ for (j = 0; pCtx->nOutbufs > j; j++)
+ if (pPDSB->dpbFD[i].fd == pCtx->pOutbuf[j].planes[0].fd) {
+ if (pCtx->pOutbuf[j].bQueued == VIDEO_FALSE) {
+ if (pCtx->pOutbuf[j].nIndexUseCnt > 0)
+ pCtx->pOutbuf[j].nIndexUseCnt--;
+ } else if(pCtx->pOutbuf[j].bQueued == VIDEO_TRUE) {
+ if (pCtx->pOutbuf[j].nIndexUseCnt > 1) {
+ /* The buffer being used as the reference buffer came again. */
+ pCtx->pOutbuf[j].nIndexUseCnt--;
+ } else {
+ /* Reference DPB buffer is internally reused. */
+ }
+ }
+ ALOGV("dec FD:%d, pCtx->pOutbuf[%d].nIndexUseCnt:%d", pPDSB->dpbFD[i].fd, j, pCtx->pOutbuf[j].nIndexUseCnt);
+ if ((pCtx->pOutbuf[j].nIndexUseCnt == 0) &&
+ (pCtx->pOutbuf[j].bQueued == VIDEO_FALSE)) {
+ pCtx->pOutbuf[j].bSlotUsed = VIDEO_FALSE;
+ }
+ }
+ }
+ memset((char *)pPDSB, -1, sizeof(PrivateDataShareBuffer));
+
+ return;
+}
+
+/*
+ * [Decoder Buffer OPS] ExtensionEnqueue (Output)
+ */
+static ExynosVideoErrorType MFC_Decoder_ExtensionEnqueue_Outbuf(
+ void *pHandle,
+ unsigned char *pBuffer[],
+ unsigned int *pFd[],
+ unsigned int allocLen[],
+ unsigned int dataSize[],
+ int nPlanes,
+ void *pPrivate)
+{
+ ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
+ ExynosVideoErrorType ret = VIDEO_ERROR_NONE;
+ pthread_mutex_t *pMutex = NULL;
+
+ struct v4l2_plane planes[VIDEO_DECODER_OUTBUF_PLANES];
+ struct v4l2_buffer buf;
+ int index, i;
+
+ if (pCtx == NULL) {
+ ALOGE("%s: Video context info must be supplied", __func__);
+ ret = VIDEO_ERROR_BADPARAM;
+ goto EXIT;
+ }
+
+ if (VIDEO_DECODER_OUTBUF_PLANES < nPlanes) {
+ ALOGE("%s: Number of max planes : %d, nPlanes : %d", __func__,
+ VIDEO_DECODER_OUTBUF_PLANES, nPlanes);
+ ret = VIDEO_ERROR_BADPARAM;
+ goto EXIT;
+ }
+
+ memset(&buf, 0, sizeof(buf));
+ buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
+ buf.m.planes = planes;
+ buf.length = VIDEO_DECODER_OUTBUF_PLANES;
+
+ pMutex = (pthread_mutex_t*)pCtx->pOutMutex;
+ pthread_mutex_lock(pMutex);
+
+ index = MFC_Decoder_Find_Outbuf(pCtx, pBuffer[0]);
+ if (index == -1) {
+ ALOGV("%s: Failed to find index", __func__);
+ index = MFC_Decoder_FindEmpty_Outbuf(pCtx);
+ if (index == -1) {
+ pthread_mutex_unlock(pMutex);
+ ALOGE("%s: Failed to get index", __func__);
+ ret = VIDEO_ERROR_NOBUFFERS;
+ goto EXIT;
+ }
+ }
+
+ buf.index = index;
+ ALOGV("En-queue index:%d pCtx->pOutbuf[buf.index].bQueued:%d, pFd[0]:%d",
+ index, pCtx->pOutbuf[buf.index].bQueued, pFd[0]);
+ pCtx->pOutbuf[buf.index].bQueued = VIDEO_TRUE;
+ pCtx->pOutbuf[buf.index].bSlotUsed = VIDEO_TRUE;
+
+ buf.memory = pCtx->nMemoryType;
+ for (i = 0; i < nPlanes; i++) {
+ /* V4L2_MEMORY_USERPTR */
+ buf.m.planes[i].m.userptr = (unsigned long)pBuffer[i];
+ /* V4L2_MEMORY_DMABUF */
+ buf.m.planes[i].m.fd = pFd[i];
+ buf.m.planes[i].length = allocLen[i];
+ buf.m.planes[i].bytesused = dataSize[i];
+
+ /* Temporary storage for Dequeue */
+ pCtx->pOutbuf[buf.index].planes[i].addr = (unsigned long)pBuffer[i];
+ pCtx->pOutbuf[buf.index].planes[i].fd = (unsigned int)pFd[i];
+ pCtx->pOutbuf[buf.index].planes[i].allocSize = allocLen[i];
+
+ ALOGV("%s: shared outbuf(%d) plane=%d addr=0x%x fd=%d len=%d used=%d\n",
+ __func__, index, i,
+ (void*)buf.m.planes[i].m.userptr, buf.m.planes[i].m.fd,
+ buf.m.planes[i].length, buf.m.planes[i].bytesused);
+ }
+
+ pCtx->pOutbuf[buf.index].pPrivate = pPrivate;
+ pCtx->pOutbuf[buf.index].nIndexUseCnt++;
+
+ pthread_mutex_unlock(pMutex);
+
+ if (exynos_v4l2_qbuf(pCtx->hDec, &buf) != 0) {
+ ALOGE("%s: Failed to enqueue output buffer", __func__);
+ pthread_mutex_lock(pMutex);
+ pCtx->pOutbuf[buf.index].nIndexUseCnt--;
+ pCtx->pOutbuf[buf.index].pPrivate = NULL;
+ pCtx->pOutbuf[buf.index].bQueued = VIDEO_FALSE;
+ if (pCtx->pOutbuf[buf.index].nIndexUseCnt == 0)
+ pCtx->pOutbuf[buf.index].bSlotUsed = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
+ ret = VIDEO_ERROR_APIFAIL;
+ goto EXIT;
+ }
+
+EXIT:
+ return ret;
+}
+
+/*
+ * [Decoder Buffer OPS] ExtensionDequeue (Output)
+ */
+static ExynosVideoErrorType MFC_Decoder_ExtensionDequeue_Outbuf(
+ void *pHandle,
+ ExynosVideoBuffer *pVideoBuffer)
+{
+ ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
+ ExynosVideoErrorType ret = VIDEO_ERROR_NONE;
+ pthread_mutex_t *pMutex = NULL;
+ ExynosVideoBuffer *pOutbuf = NULL;
+ PrivateDataShareBuffer *pPDSB = NULL;
+ struct v4l2_buffer buf;
+ int value, i, j;
+
+ if (pCtx == NULL) {
+ ALOGE("%s: Video context info must be supplied", __func__);
+ ret = VIDEO_ERROR_BADPARAM;
+ goto EXIT;
+ }
+
+ if (pCtx->bStreamonOutbuf == VIDEO_FALSE) {
+ pOutbuf = NULL;
+ ret = VIDEO_ERROR_APIFAIL;
+ goto EXIT;
+ }
+
+ memset(&buf, 0, sizeof(buf));
+ buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
+
+ if (pCtx->bShareOutbuf == VIDEO_TRUE)
+ buf.memory = pCtx->nMemoryType;
+ else
+ buf.memory = V4L2_MEMORY_MMAP;
+
+ /* HACK: pOutbuf return -1 means DECODING_ONLY for almost cases */
+ if (exynos_v4l2_dqbuf(pCtx->hDec, &buf) != 0) {
+ pOutbuf = NULL;
+ ret = VIDEO_ERROR_APIFAIL;
+ goto EXIT;
+ }
+
+ pMutex = (pthread_mutex_t*)pCtx->pOutMutex;
+ pthread_mutex_lock(pMutex);
+
+ pOutbuf = &pCtx->pOutbuf[buf.index];
+ exynos_v4l2_g_ctrl(pCtx->hDec, V4L2_CID_MPEG_MFC51_VIDEO_DISPLAY_STATUS, &value);
+
+ switch (value) {
+ case 0:
+ pOutbuf->displayStatus = VIDEO_FRAME_STATUS_DECODING_ONLY;
+ break;
+ case 1:
+ pOutbuf->displayStatus = VIDEO_FRAME_STATUS_DISPLAY_DECODING;
+ break;
+ case 2:
+ pOutbuf->displayStatus = VIDEO_FRAME_STATUS_DISPLAY_ONLY;
+ break;
+ case 3:
+ pOutbuf->displayStatus = VIDEO_FRAME_STATUS_CHANGE_RESOL;
+ break;
+ default:
+ pOutbuf->displayStatus = VIDEO_FRAME_STATUS_UNKNOWN;
+ break;
+ }
+
+ switch (buf.flags & (0x7 << 3)) {
+ case V4L2_BUF_FLAG_KEYFRAME:
+ pOutbuf->frameType = VIDEO_FRAME_I;
+ break;
+ case V4L2_BUF_FLAG_PFRAME:
+ pOutbuf->frameType = VIDEO_FRAME_P;
+ break;
+ case V4L2_BUF_FLAG_BFRAME:
+ pOutbuf->frameType = VIDEO_FRAME_B;
+ break;
+ default:
+ pOutbuf->frameType = VIDEO_FRAME_OTHERS;
+ break;
+ };
+
+ pPDSB = ((PrivateDataShareBuffer *)pCtx->nPrivateDataShareAddress) + buf.index;
+ if (pCtx->pOutbuf[buf.index].bQueued == VIDEO_TRUE) {
+ memcpy(pVideoBuffer, pOutbuf, sizeof(ExynosVideoBuffer));
+ memcpy((char *)(&(pVideoBuffer->PDSB)), (char *)pPDSB, sizeof(PrivateDataShareBuffer));
+ } else {
+ ret = VIDEO_ERROR_NOBUFFERS;
+ ALOGV("%s :: %d", __FUNCTION__, __LINE__);
+ }
+
+ pCtx->pOutbuf[buf.index].bQueued = VIDEO_FALSE;
+ MFC_Decoder_BufferIndexFree_Outbuf(pHandle, pPDSB, buf.index);
+
+ pthread_mutex_unlock(pMutex);
+
+EXIT:
+ return ret;
+}
+
+/*
+ * [Decoder Buffer OPS] Enable Dynamic DPB
+ */
+static ExynosVideoErrorType MFC_Decoder_Enable_DynamicDPB(void *pHandle)
+{
+ ExynosVideoDecContext *pCtx = (ExynosVideoDecContext *)pHandle;
+ ExynosVideoErrorType ret = VIDEO_ERROR_NONE;
+
+ if (pCtx == NULL) {
+ ALOGE("%s: Video context info must be supplied", __func__);
+ ret = VIDEO_ERROR_BADPARAM;
+ goto EXIT;
+ }
+
+ if (exynos_v4l2_s_ctrl(pCtx->hDec, V4L2_CID_MPEG_MFC_SET_DYNAMIC_DPB_MODE, 1) != 0) {
+ ret = VIDEO_ERROR_APIFAIL;
+ goto EXIT;
+ }
+
+ if (exynos_v4l2_s_ctrl(pCtx->hDec, V4L2_CID_MPEG_MFC_SET_USER_SHARED_HANDLE, pCtx->nPrivateDataShareFD) != 0) {
+ ret = VIDEO_ERROR_APIFAIL;
+ goto EXIT;
+ }
+
+EXIT:
+ return ret;
+}
+
+/*
* [Decoder OPS] Common
*/
static ExynosVideoDecOps defDecOps = {
@@ -1794,6 +2127,9 @@ static ExynosVideoDecBufferOps defOutbufOps = {
.Register = MFC_Decoder_Register_Outbuf,
.Clear_RegisteredBuffer = MFC_Decoder_Clear_RegisteredBuffer_Outbuf,
.Clear_Queue = MFC_Decoder_Clear_Queued_Outbuf,
+ .ExtensionEnqueue = MFC_Decoder_ExtensionEnqueue_Outbuf,
+ .ExtensionDequeue = MFC_Decoder_ExtensionDequeue_Outbuf,
+ .Enable_DynamicDPB = MFC_Decoder_Enable_DynamicDPB,
};
int Exynos_Video_Register_Decoder(
diff --git a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/enc/src/ExynosVideoEncoder.c b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/enc/src/ExynosVideoEncoder.c
index 8d646db..0d3d686 100644
--- a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/enc/src/ExynosVideoEncoder.c
+++ b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/enc/src/ExynosVideoEncoder.c
@@ -1835,7 +1835,6 @@ static ExynosVideoErrorType MFC_Encoder_Enqueue_Inbuf(
buf.index = index;
pCtx->pInbuf[buf.index].bQueued = VIDEO_TRUE;
- pthread_mutex_unlock(pMutex);
if (pCtx->bShareInbuf == VIDEO_TRUE) {
buf.memory = pCtx->nMemoryType;
@@ -1853,15 +1852,20 @@ static ExynosVideoErrorType MFC_Encoder_Enqueue_Inbuf(
buf.m.planes[i].bytesused = dataSize[i];
}
+ pCtx->pInbuf[buf.index].pPrivate = pPrivate;
+
+ pthread_mutex_unlock(pMutex);
+
if (exynos_v4l2_qbuf(pCtx->hEnc, &buf) != 0) {
ALOGE("%s: Failed to enqueue input buffer", __func__);
+ pthread_mutex_lock(pMutex);
+ pCtx->pInbuf[buf.index].pPrivate = NULL;
pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
ret = VIDEO_ERROR_APIFAIL;
goto EXIT;
}
- pCtx->pInbuf[buf.index].pPrivate = pPrivate;
-
EXIT:
return ret;
}
@@ -1913,7 +1917,6 @@ static ExynosVideoErrorType MFC_Encoder_Enqueue_Outbuf(
}
buf.index = index;
pCtx->pOutbuf[buf.index].bQueued = VIDEO_TRUE;
- pthread_mutex_unlock(pMutex);
if (pCtx->bShareOutbuf == VIDEO_TRUE) {
buf.memory = pCtx->nMemoryType;
@@ -1929,15 +1932,20 @@ static ExynosVideoErrorType MFC_Encoder_Enqueue_Outbuf(
buf.memory = V4L2_MEMORY_MMAP;
}
+ pCtx->pOutbuf[buf.index].pPrivate = pPrivate;
+
+ pthread_mutex_unlock(pMutex);
+
if (exynos_v4l2_qbuf(pCtx->hEnc, &buf) != 0) {
ALOGE("%s: Failed to enqueue output buffer", __func__);
+ pthread_mutex_lock(pMutex);
+ pCtx->pOutbuf[buf.index].pPrivate = NULL;
pCtx->pOutbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
ret = VIDEO_ERROR_APIFAIL;
goto EXIT;
}
- pCtx->pOutbuf[buf.index].pPrivate = pPrivate;
-
EXIT:
return ret;
}
@@ -1978,6 +1986,7 @@ static ExynosVideoBuffer *MFC_Encoder_Dequeue_Inbuf(void *pHandle)
{
ExynosVideoEncContext *pCtx = (ExynosVideoEncContext *)pHandle;
ExynosVideoBuffer *pInbuf = NULL;
+ pthread_mutex_t *pMutex = NULL;
struct v4l2_buffer buf;
@@ -2005,9 +2014,14 @@ static ExynosVideoBuffer *MFC_Encoder_Dequeue_Inbuf(void *pHandle)
goto EXIT;
}
+ pMutex = (pthread_mutex_t*)pCtx->pInMutex;
+ pthread_mutex_lock(pMutex);
+
pInbuf = &pCtx->pInbuf[buf.index];
pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
+
EXIT:
return pInbuf;
}
@@ -2019,6 +2033,7 @@ static ExynosVideoBuffer *MFC_Encoder_Dequeue_Outbuf(void *pHandle)
{
ExynosVideoEncContext *pCtx = (ExynosVideoEncContext *)pHandle;
ExynosVideoBuffer *pOutbuf = NULL;
+ pthread_mutex_t *pMutex = NULL;
struct v4l2_buffer buf;
struct v4l2_plane planes[VIDEO_ENCODER_OUTBUF_PLANES];
@@ -2049,6 +2064,9 @@ static ExynosVideoBuffer *MFC_Encoder_Dequeue_Outbuf(void *pHandle)
goto EXIT;
}
+ pMutex = (pthread_mutex_t*)pCtx->pOutMutex;
+ pthread_mutex_lock(pMutex);
+
pOutbuf = &pCtx->pOutbuf[buf.index];
pOutbuf->planes[0].dataSize = buf.m.planes[0].bytesused;
@@ -2070,6 +2088,8 @@ static ExynosVideoBuffer *MFC_Encoder_Dequeue_Outbuf(void *pHandle)
pOutbuf->bQueued = VIDEO_FALSE;
+ pthread_mutex_unlock(pMutex);
+
EXIT:
return pOutbuf;
}
@@ -2191,9 +2211,7 @@ static ExynosVideoErrorType MFC_Encoder_ExtensionEnqueue_Inbuf(
}
buf.index = index;
-
pCtx->pInbuf[buf.index].bQueued = VIDEO_TRUE;
- pthread_mutex_unlock(pMutex);
buf.memory = pCtx->nMemoryType;
for (i = 0; i < nPlanes; i++) {
@@ -2208,17 +2226,20 @@ static ExynosVideoErrorType MFC_Encoder_ExtensionEnqueue_Inbuf(
pCtx->pInbuf[buf.index].planes[i].allocSize = allocLen[i];
}
+ pCtx->pInbuf[buf.index].pPrivate = pPrivate;
+
+ pthread_mutex_unlock(pMutex);
+
if (exynos_v4l2_qbuf(pCtx->hEnc, &buf) != 0) {
ALOGE("%s: Failed to enqueue input buffer", __func__);
pthread_mutex_lock(pMutex);
+ pCtx->pInbuf[buf.index].pPrivate = NULL;
pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
pthread_mutex_unlock(pMutex);
ret = VIDEO_ERROR_APIFAIL;
goto EXIT;
}
- pCtx->pInbuf[buf.index].pPrivate = pPrivate;
-
EXIT:
return ret;
}
@@ -2248,16 +2269,19 @@ static ExynosVideoErrorType MFC_Encoder_ExtensionDequeue_Inbuf(void *pHandle, Ex
memset(&buf, 0, sizeof(buf));
buf.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
buf.memory = pCtx->nMemoryType;
+
if (exynos_v4l2_dqbuf(pCtx->hEnc, &buf) != 0) {
ALOGE("%s: Failed to dequeue input buffer", __func__);
ret = VIDEO_ERROR_APIFAIL;
goto EXIT;
}
- memcpy(pVideoBuffer, &pCtx->pInbuf[buf.index], sizeof(ExynosVideoBuffer));
pMutex = (pthread_mutex_t*)pCtx->pInMutex;
pthread_mutex_lock(pMutex);
+
+ memcpy(pVideoBuffer, &pCtx->pInbuf[buf.index], sizeof(ExynosVideoBuffer));
pCtx->pInbuf[buf.index].bQueued = VIDEO_FALSE;
+
pthread_mutex_unlock(pMutex);
EXIT:
diff --git a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoApi.h b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoApi.h
index 35c0b47..2b9db97 100644
--- a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoApi.h
+++ b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoApi.h
@@ -22,6 +22,7 @@
/* Fixed */
#define VIDEO_BUFFER_MAX_PLANES 3
+#define VIDEO_BUFFER_MAX_NUM 32
typedef enum _ExynosVideoBoolType {
VIDEO_FALSE = 0,
@@ -107,14 +108,28 @@ typedef struct _ExynosVideoPlane {
int fd;
} ExynosVideoPlane;
+typedef struct _ReleaseDPB {
+ int fd;
+ int fd1;
+ int fd2;
+} ReleaseDPB;
+
+typedef struct _PrivateDataShareBuffer {
+ int index;
+ ReleaseDPB dpbFD[VIDEO_BUFFER_MAX_NUM];
+}PrivateDataShareBuffer;
+
typedef struct _ExynosVideoBuffer {
ExynosVideoPlane planes[VIDEO_BUFFER_MAX_PLANES];
ExynosVideoGeometry *pGeometry;
ExynosVideoFrameStatusType displayStatus;
ExynosVideoFrameType frameType;
ExynosVideoBoolType bQueued;
+ ExynosVideoBoolType bSlotUsed;
ExynosVideoBoolType bRegistered;
void *pPrivate;
+ PrivateDataShareBuffer PDSB;
+ int nIndexUseCnt;
} ExynosVideoBuffer;
typedef struct _ExynosVideoFramePacking{
@@ -269,6 +284,9 @@ typedef struct _ExynosVideoDecBufferOps {
ExynosVideoErrorType (*Register)(void *pHandle, ExynosVideoPlane *planes, int nPlanes);
ExynosVideoErrorType (*Clear_RegisteredBuffer)(void *pHandle);
ExynosVideoErrorType (*Clear_Queue)(void *pHandle);
+ ExynosVideoErrorType (*ExtensionEnqueue)(void *pHandle, unsigned char *pBuffer[], unsigned int *pFd[], unsigned int allocLen[], unsigned int dataSize[], int nPlanes, void *pPrivate);
+ ExynosVideoErrorType (*ExtensionDequeue)(void *pHandle, ExynosVideoBuffer *pVideoBuffer);
+ ExynosVideoErrorType (*Enable_DynamicDPB)(void *pHandle);
} ExynosVideoDecBufferOps;
typedef struct _ExynosVideoEncBufferOps {
diff --git a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoDec.h b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoDec.h
index 45287b0..8b56a82 100644
--- a/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoDec.h
+++ b/exynos_omx/codecs/exynos_codecs/video/exynos5/mfc_v4l2/include/ExynosVideoDec.h
@@ -45,6 +45,10 @@ typedef struct _ExynosVideoDecContext {
void *pInMutex;
void *pOutMutex;
int nMemoryType;
+
+ void *hIONHandle;
+ int nPrivateDataShareFD;
+ void *nPrivateDataShareAddress;
} ExynosVideoDecContext;
#endif /* _EXYNOS_VIDEO_DEC_H_ */
diff --git a/exynos_omx/openmax/exynos_omx/component/common/Exynos_OMX_Baseport.h b/exynos_omx/openmax/exynos_omx/component/common/Exynos_OMX_Baseport.h
index 165bbf2..e486555 100644
--- a/exynos_omx/openmax/exynos_omx/component/common/Exynos_OMX_Baseport.h
+++ b/exynos_omx/openmax/exynos_omx/component/common/Exynos_OMX_Baseport.h
@@ -100,7 +100,7 @@ typedef struct _EXYNOS_OMX_DATA
OMX_TICKS timeStamp;
OMX_PTR pPrivate;
CODEC_EXTRA_BUFFERINFO extInfo;
-
+
/* For Share Buffer */
OMX_BUFFERHEADERTYPE* bufferHeader;
} EXYNOS_OMX_DATA;
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/Android.mk b/exynos_omx/openmax/exynos_omx/component/video/dec/Android.mk
index 0d79ec4..816f044 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/Android.mk
@@ -24,4 +24,8 @@ LOCAL_STATIC_LIBRARIES := libExynosOMX_OSAL libcsc_helper
LOCAL_CFLAGS += -DUSE_ANB
endif
+ifeq ($(BOARD_USE_STOREMETADATA), true)
+LOCAL_CFLAGS += -DUSE_STOREMETADATA
+endif
+
include $(BUILD_STATIC_LIBRARY)
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.c b/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.c
index c40221b..1179b1b 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.c
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.c
@@ -192,14 +192,14 @@ OMX_ERRORTYPE Exynos_Output_CodecBufferToData(EXYNOS_OMX_BASECOMPONENT *pExynosC
{
OMX_ERRORTYPE ret = OMX_ErrorNone;
EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
- OMX_PTR pSrcBuf[MAX_BUFFER_PLANE];
- OMX_U32 allocSize[MAX_BUFFER_PLANE];
-
- pVideoDec->exynos_codec_getCodecOutputPrivateData(codecBuffer, pSrcBuf, allocSize);
- pData->buffer.multiPlaneBuffer.dataBuffer[0] = pSrcBuf[0];
- pData->buffer.multiPlaneBuffer.dataBuffer[1] = pSrcBuf[1];
- pData->buffer.multiPlaneBuffer.dataBuffer[2] = pSrcBuf[2];
- pData->allocSize = allocSize[0] + allocSize[1] + allocSize[2];
+ CODEC_DEC_BUFFER *pCodecBuffer = (CODEC_DEC_BUFFER *)codecBuffer;
+ int i = 0;
+
+ for (i = 0; i < MAX_BUFFER_PLANE; i++) {
+ pData->buffer.multiPlaneBuffer.dataBuffer[i] = pCodecBuffer->pVirAddr[i];
+ pData->buffer.multiPlaneBuffer.fd[i] = pCodecBuffer->fd[i];
+ pData->allocSize += pCodecBuffer->bufferSize[i];
+ }
pData->dataLen = 0;
pData->usedDataLen = 0;
pData->remainDataLen = 0;
@@ -284,10 +284,15 @@ OMX_BOOL Exynos_CSC_OutputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA
}
#ifdef USE_ANB
- if (exynosOutputPort->bIsANBEnabled == OMX_TRUE) {
+ if ((exynosOutputPort->bIsANBEnabled == OMX_TRUE) ||
+ (exynosOutputPort->bStoreMetaData == OMX_TRUE)) {
ExynosVideoPlane planes[MAX_BUFFER_PLANE];
OMX_U32 stride;
- Exynos_OSAL_LockANB(pOutputBuf, width, height, exynosOutputPort->portDefinition.format.video.eColorFormat, &stride, planes);
+ if (exynosOutputPort->bIsANBEnabled == OMX_TRUE) {
+ Exynos_OSAL_LockANB(pOutputBuf, width, height, exynosOutputPort->portDefinition.format.video.eColorFormat, &stride, planes);
+ } else if (exynosOutputPort->bStoreMetaData == OMX_TRUE) {
+ Exynos_OSAL_LockMetaData(pOutputBuf, width, height, exynosOutputPort->portDefinition.format.video.eColorFormat, &stride, planes);
+ }
width = stride;
outputUseBuffer->dataLen = sizeof(void *);
@@ -303,6 +308,7 @@ OMX_BOOL Exynos_CSC_OutputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA
}
#endif
if ((exynosOutputPort->bIsANBEnabled == OMX_FALSE) &&
+ (exynosOutputPort->bStoreMetaData == OMX_FALSE) &&
(csc_method == CSC_METHOD_HW)) {
pYUVBuf[0] = Exynos_OSAL_SharedMemory_VirtToION(pVideoDec->hSharedMemory, pOutputBuf);
pYUVBuf[1] = NULL;
@@ -347,6 +353,8 @@ OMX_BOOL Exynos_CSC_OutputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA
#ifdef USE_ANB
if (exynosOutputPort->bIsANBEnabled == OMX_TRUE) {
Exynos_OSAL_UnlockANB(pOutputBuf);
+ } else if (exynosOutputPort->bStoreMetaData == OMX_TRUE) {
+ Exynos_OSAL_UnlockMetaData(pOutputBuf);
}
#endif
@@ -471,7 +479,8 @@ OMX_BOOL Exynos_Postprocess_OutputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_
FunctionIn();
if (exynosOutputPort->bufferProcessType == BUFFER_SHARE) {
- if (exynosOutputPort->bIsANBEnabled == OMX_FALSE) {
+ if ((exynosOutputPort->bIsANBEnabled == OMX_FALSE) &&
+ (exynosOutputPort->bStoreMetaData == OMX_FALSE)) {
if (Exynos_Shared_DataToBuffer(dstOutputData, outputUseBuffer) == OMX_ErrorNone)
outputUseBuffer->dataValid = OMX_TRUE;
} else {
@@ -753,7 +762,8 @@ OMX_ERRORTYPE Exynos_OMX_DstInputBufferProcess(OMX_HANDLETYPE hComponent)
Exynos_OSAL_MutexUnlock(dstInputUseBuffer->bufferMutex);
break;
}
- if (exynosOutputPort->bIsANBEnabled == OMX_FALSE) {
+ if ((exynosOutputPort->bIsANBEnabled == OMX_FALSE) &&
+ (exynosOutputPort->bStoreMetaData == OMX_FALSE)) {
Exynos_Shared_BufferToData(dstInputUseBuffer, &dstInputData, TWO_PLANE);
} else {
ret = Exynos_Shared_ANBBufferToData(dstInputUseBuffer, &dstInputData, exynosOutputPort, TWO_PLANE);
@@ -763,6 +773,7 @@ OMX_ERRORTYPE Exynos_OMX_DstInputBufferProcess(OMX_HANDLETYPE hComponent)
break;
}
}
+ Exynos_OSAL_RefANB_Increase(pVideoDec->hRefHandle, dstInputData.bufferHeader->pBuffer);
Exynos_ResetDataBuffer(dstInputUseBuffer);
}
}
@@ -829,12 +840,24 @@ OMX_ERRORTYPE Exynos_OMX_DstOutputBufferProcess(OMX_HANDLETYPE hComponent)
if (((ret == OMX_ErrorNone) && (dstOutputUseBuffer->dataValid == OMX_TRUE)) ||
(exynosOutputPort->bufferProcessType == BUFFER_SHARE)) {
+ if (exynosOutputPort->bufferProcessType == BUFFER_SHARE) {
+ DECODE_CODEC_EXTRA_BUFFERINFO *pBufferInfo = NULL;
+ int i;
+ pBufferInfo = (DECODE_CODEC_EXTRA_BUFFERINFO *)pDstOutputData->extInfo;
+ for (i = 0; i < VIDEO_BUFFER_MAX_NUM; i++) {
+ if (pBufferInfo->PDSB.dpbFD[i].fd > -1) {
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "decRefCnt-FD:%d", pBufferInfo->PDSB.dpbFD[i].fd);
+ Exynos_OSAL_RefANB_Decrease(pVideoDec->hRefHandle, pBufferInfo->PDSB.dpbFD[i].fd);
+ } else {
+ break;
+ }
+ }
+ }
Exynos_Postprocess_OutputData(pOMXComponent, pDstOutputData);
}
if ((exynosOutputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) {
- OMX_PTR codecBuffer;
- codecBuffer = pDstOutputData->pPrivate;
+ OMX_PTR codecBuffer = pDstOutputData->pPrivate;
if (codecBuffer != NULL) {
Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, codecBuffer);
pDstOutputData->pPrivate = NULL;
@@ -1153,7 +1176,17 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeComponentInit(OMX_IN OMX_HANDLETYPE hCompone
pExynosPort->portDefinition.format.video.pNativeWindow = NULL;
pExynosPort->processData.extInfo = (OMX_PTR)Exynos_OSAL_Malloc(sizeof(DECODE_CODEC_EXTRA_BUFFERINFO));
-
+ Exynos_OSAL_Memset(((char *)pExynosPort->processData.extInfo), 0, sizeof(DECODE_CODEC_EXTRA_BUFFERINFO));
+{
+ int i = 0;
+ DECODE_CODEC_EXTRA_BUFFERINFO *pBufferInfo = NULL;
+ pBufferInfo = (DECODE_CODEC_EXTRA_BUFFERINFO *)(pExynosPort->processData.extInfo);
+ for (i = 0; i < VIDEO_BUFFER_MAX_NUM; i++) {
+ pBufferInfo->PDSB.dpbFD[i].fd = -1;
+ pBufferInfo->PDSB.dpbFD[i].fd1 = -1;
+ pBufferInfo->PDSB.dpbFD[i].fd2 = -1;
+ }
+}
pOMXComponent->UseBuffer = &Exynos_OMX_UseBuffer;
pOMXComponent->AllocateBuffer = &Exynos_OMX_AllocateBuffer;
pOMXComponent->FreeBuffer = &Exynos_OMX_FreeBuffer;
@@ -1165,6 +1198,8 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeComponentInit(OMX_IN OMX_HANDLETYPE hCompone
pExynosComponent->exynos_BufferProcessTerminate = &Exynos_OMX_BufferProcess_Terminate;
pExynosComponent->exynos_BufferFlush = &Exynos_OMX_BufferFlush;
+ pVideoDec->hRefHandle = Exynos_OSAL_RefANB_Create();
+
EXIT:
FunctionOut();
@@ -1200,6 +1235,8 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeComponentDeinit(OMX_IN OMX_HANDLETYPE hCompo
pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+ Exynos_OSAL_RefANB_Terminate(pVideoDec->hRefHandle);
+
Exynos_OSAL_Free(pVideoDec);
pExynosComponent->hComponentHandle = pVideoDec = NULL;
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.h b/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.h
index 7f1be9b..e7bee2d 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.h
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_Vdec.h
@@ -60,6 +60,7 @@
#define MFC_INPUT_BUFFER_PLANE 1
#define MFC_OUTPUT_BUFFER_PLANE 2
+#define MAX_OUTPUTBUFFER_NUM_DYNAMIC 0 /* Dynamic number of metadata buffer */
#define PLATFORM_DISPLAY_BUFFER 1
typedef struct
@@ -82,6 +83,7 @@ typedef struct _DECODE_CODEC_EXTRA_BUFFERINFO
OMX_U32 imageWidth;
OMX_U32 imageHeight;
OMX_COLOR_FORMATTYPE ColorFormat;
+ PrivateDataShareBuffer PDSB;
} DECODE_CODEC_EXTRA_BUFFERINFO;
typedef struct _EXYNOS_OMX_VIDEODEC_COMPONENT
@@ -109,6 +111,8 @@ typedef struct _EXYNOS_OMX_VIDEODEC_COMPONENT
OMX_PTR csc_handle;
OMX_U32 csc_set_format;
+ OMX_HANDLETYPE hRefHandle;
+
OMX_ERRORTYPE (*exynos_codec_srcInputProcess) (OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pInputData);
OMX_ERRORTYPE (*exynos_codec_srcOutputProcess) (OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pInputData);
OMX_ERRORTYPE (*exynos_codec_dstInputProcess) (OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pOutputData);
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_VdecControl.c b/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_VdecControl.c
index ca1ae4d..17c05f2 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_VdecControl.c
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/Exynos_OMX_VdecControl.c
@@ -484,6 +484,20 @@ OMX_ERRORTYPE Exynos_OMX_FlushPort(OMX_COMPONENTTYPE *pOMXComponent, OMX_S32 por
Exynos_ResetCodecData(&pExynosPort->processData);
}
+ if ((pExynosPort->bufferProcessType == BUFFER_SHARE) &&
+ (portIndex == OUTPUT_PORT_INDEX)){
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
+
+ if (pOMXComponent->pComponentPrivate == NULL) {
+ ret = OMX_ErrorBadParameter;
+ goto EXIT;
+ }
+ pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
+ pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
+
+ Exynos_OSAL_RefANB_Reset(pVideoDec->hRefHandle);
+ }
+
while(1) {
OMX_S32 cnt = 0;
Exynos_OSAL_Get_SemaphoreCount(pExynosComponent->pExynosPort[portIndex].bufferSemID, &cnt);
@@ -756,6 +770,9 @@ OMX_ERRORTYPE Exynos_OutputBufferReturn(OMX_COMPONENTTYPE *pOMXComponent)
bufferHeader->nFlags = dataBuffer->nFlags;
bufferHeader->nTimeStamp = dataBuffer->timeStamp;
+ if (exynosOMXOutputPort->bStoreMetaData == OMX_TRUE)
+ bufferHeader->nFilledLen = bufferHeader->nAllocLen;
+
if (pExynosComponent->propagateMarkType.hMarkTargetComponent != NULL) {
bufferHeader->hMarkTargetComponent = pExynosComponent->propagateMarkType.hMarkTargetComponent;
bufferHeader->pMarkData = pExynosComponent->propagateMarkType.pMarkData;
@@ -1099,7 +1116,8 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeGetParameter(
pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
portDefinition = &pExynosPort->portDefinition;
- if (pExynosPort->bIsANBEnabled == OMX_FALSE) {
+ if ((pExynosPort->bIsANBEnabled == OMX_FALSE) &&
+ (pExynosPort->bStoreMetaData == OMX_FALSE)) {
switch (index) {
case supportFormat_0:
portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
@@ -1168,9 +1186,11 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeGetParameter(
* just dereference things directly here
*/
pExynosPort = &pExynosComponent->pExynosPort[portIndex];
- if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
+ if ((pExynosPort->bIsANBEnabled == OMX_TRUE) ||
+ (pExynosPort->bStoreMetaData == OMX_TRUE)){
portDefinition->format.video.eColorFormat =
(OMX_COLOR_FORMATTYPE)Exynos_OSAL_OMX2HalPixelFormat(portDefinition->format.video.eColorFormat);
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "portDefinition->format.video.eColorFormat:0x%x", portDefinition->format.video.eColorFormat);
}
}
break;
@@ -1250,6 +1270,8 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeSetParameter(
portDefinition->format.video.eColorFormat = portFormat->eColorFormat;
portDefinition->format.video.eCompressionFormat = portFormat->eCompressionFormat;
portDefinition->format.video.xFramerate = portFormat->xFramerate;
+
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "portIndex:%d, portFormat->eColorFormat:0x%x", portIndex, portFormat->eColorFormat);
}
}
break;
@@ -1288,7 +1310,8 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeSetParameter(
#ifdef USE_ANB // Modified by Google engineer
/* should not affect the format since in ANB case, the caller
* is providing us a HAL format */
- if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
+ if ((pExynosPort->bIsANBEnabled == OMX_TRUE) ||
+ (pExynosPort->bStoreMetaData == OMX_TRUE)) {
pExynosPort->portDefinition.format.video.eColorFormat =
Exynos_OSAL_Hal2OMXPixelFormat(pExynosPort->portDefinition.format.video.eColorFormat);
}
@@ -1338,6 +1361,7 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeSetParameter(
#ifdef USE_ANB
case OMX_IndexParamEnableAndroidBuffers:
case OMX_IndexParamUseAndroidNativeBuffer:
+ case OMX_IndexParamStoreMetaDataBuffer:
{
ret = Exynos_OSAL_SetANBParameter(hComponent, nIndex, ComponentParameterStructure);
}
@@ -1522,6 +1546,12 @@ OMX_ERRORTYPE Exynos_OMX_VideoDecodeGetExtensionIndex(
*pIndexType = OMX_IndexParamEnableThumbnailMode;
goto EXIT;
}
+#ifdef USE_STOREMETADATA
+ if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_STORE_METADATA_BUFFER) == 0) {
+ *pIndexType = (OMX_INDEXTYPE) OMX_IndexParamStoreMetaDataBuffer;
+ goto EXIT;
+ }
+#endif
ret = Exynos_OMX_GetExtensionIndex(hComponent, cParameterName, pIndexType);
@@ -1536,18 +1566,22 @@ OMX_ERRORTYPE Exynos_Shared_ANBBufferToData(EXYNOS_OMX_DATABUFFER *pUseBuffer, E
{
OMX_ERRORTYPE ret = OMX_ErrorNone;
OMX_U32 width, height;
-// void *pPhys[MAX_BUFFER_PLANE];
ExynosVideoPlane planes[MAX_BUFFER_PLANE];
memset(planes, 0, sizeof(planes));
- if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
- OMX_U32 stride;
+ width = pExynosPort->portDefinition.format.video.nFrameWidth;
+ height = pExynosPort->portDefinition.format.video.nFrameHeight;
- width = pExynosPort->portDefinition.format.video.nFrameWidth;
- height = pExynosPort->portDefinition.format.video.nFrameHeight;
+ if ((pExynosPort->bIsANBEnabled == OMX_TRUE) ||
+ (pExynosPort->bStoreMetaData == OMX_TRUE)) {
+ OMX_U32 stride;
if ((pUseBuffer->bufferHeader != NULL) && (pUseBuffer->bufferHeader->pBuffer != NULL)) {
- Exynos_OSAL_LockANB(pUseBuffer->bufferHeader->pBuffer, width, height, pExynosPort->portDefinition.format.video.eColorFormat, &stride, planes);
+ if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
+ Exynos_OSAL_LockANB(pUseBuffer->bufferHeader->pBuffer, width, height, pExynosPort->portDefinition.format.video.eColorFormat, &stride, planes);
+ } else if (pExynosPort->bStoreMetaData == OMX_TRUE) {
+ Exynos_OSAL_LockMetaData(pUseBuffer->bufferHeader->pBuffer, width, height, pExynosPort->portDefinition.format.video.eColorFormat, &stride, planes);
+ }
pUseBuffer->dataLen = sizeof(void *);
} else {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
@@ -1606,6 +1640,8 @@ OMX_ERRORTYPE Exynos_Shared_DataToANBBuffer(EXYNOS_OMX_DATA *pData, EXYNOS_OMX_D
if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
Exynos_OSAL_UnlockANB(pUseBuffer->bufferHeader->pBuffer);
+ } else if (pExynosPort->bStoreMetaData == OMX_TRUE) {
+ Exynos_OSAL_UnlockMetaData(pUseBuffer->bufferHeader->pBuffer);
} else {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
ret = OMX_ErrorBadParameter;
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Android.mk b/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Android.mk
index 94ced6a..984bd9d 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Android.mk
@@ -30,7 +30,8 @@ LOCAL_ARM_MODE := arm
LOCAL_STATIC_LIBRARIES := libExynosOMX_Vdec libExynosOMX_OSAL libExynosOMX_Basecomponent \
libswconverter libExynosVideoApi
LOCAL_SHARED_LIBRARIES := libc libdl libcutils libutils liblog libui \
- libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos libexynosgscaler
+ libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos libexynosgscaler \
+ libhardware
ifeq ($(BOARD_USES_MFC_FPS),true)
LOCAL_CFLAGS += -DCONFIG_MFC_FPS
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Exynos_OMX_H264dec.c b/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Exynos_OMX_H264dec.c
index 52d17d7..c88bf70 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Exynos_OMX_H264dec.c
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/h264/Exynos_OMX_H264dec.c
@@ -568,8 +568,7 @@ OMX_ERRORTYPE H264CodecEnQueueAllBuffer(OMX_COMPONENTTYPE *pOMXComponent, OMX_U3
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);
+ Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, pVideoDec->pMFCDecOutputBuffer[i]);
}
pOutbufOps->Clear_Queue(hMFCHandle);
} else {
@@ -839,9 +838,13 @@ OMX_ERRORTYPE H264CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
goto EXIT;
}
}
+ if (pOutbufOps->Enable_DynamicDPB(hMFCHandle) != VIDEO_ERROR_NONE) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
pOutbufOps->Set_Shareable(hMFCHandle);
- if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
+ if (pOutbufOps->Setup(hMFCHandle, MAX_OUTPUTBUFFER_NUM_DYNAMIC) != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
ret = OMX_ErrorInsufficientResources;
goto EXIT;
@@ -881,43 +884,27 @@ OMX_ERRORTYPE H264CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
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,
+ /* Enqueue output buffer */
+ pOutbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr,
+ (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->fd,
+ (unsigned int *)pVideoDec->pMFCDecOutputBuffer[i]->bufferSize,
(unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, 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) {
- /* 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++) {
- 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) {
- 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);
- }
- } else {
+ if ((pExynosOutputPort->bIsANBEnabled == OMX_FALSE) &&
+ (pExynosOutputPort->bStoreMetaData == OMX_FALSE)) {
ret = OMX_ErrorNotImplemented;
goto EXIT;
}
@@ -927,15 +914,6 @@ OMX_ERRORTYPE H264CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
#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;
@@ -1767,13 +1745,21 @@ OMX_ERRORTYPE Exynos_H264Dec_DstIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_
goto EXIT;
}
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x", __FUNCTION__, __LINE__,
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x, FD[0]:%d, FD[1]:%d", __FUNCTION__, __LINE__,
pDstInputData->buffer.multiPlaneBuffer.dataBuffer[0],
- pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1]);
-
- codecReturn = pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
- (unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
-
+ pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1],
+ pDstInputData->buffer.multiPlaneBuffer.fd[0],
+ pDstInputData->buffer.multiPlaneBuffer.fd[1]);
+
+ OMX_U32 nAllocLen[VIDEO_BUFFER_MAX_PLANES] = {0, 0, 0};
+ nAllocLen[0] = pExynosOutputPort->portDefinition.format.video.nFrameWidth * pExynosOutputPort->portDefinition.format.video.nFrameHeight;
+ nAllocLen[1] = pExynosOutputPort->portDefinition.format.video.nFrameWidth * pExynosOutputPort->portDefinition.format.video.nFrameHeight / 2;
+
+ codecReturn = pOutbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
+ (unsigned int **)pDstInputData->buffer.multiPlaneBuffer.fd,
+ (unsigned int *)nAllocLen, (unsigned int *)dataLen,
+ MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
if (codecReturn != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
@@ -1801,6 +1787,7 @@ OMX_ERRORTYPE Exynos_H264Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX
ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
ExynosVideoBuffer *pVideoBuffer;
+ ExynosVideoBuffer videoBuffer;
ExynosVideoFrameStatusType displayStatus = VIDEO_FRAME_STATUS_UNKNOWN;
ExynosVideoGeometry *bufferGeometry;
DECODE_CODEC_EXTRA_BUFFERINFO *pBufferInfo = NULL;
@@ -1815,7 +1802,11 @@ OMX_ERRORTYPE Exynos_H264Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX
}
while (1) {
- if ((pVideoBuffer = pOutbufOps->Dequeue(hMFCHandle)) == NULL) {
+ Exynos_OSAL_Memset(&videoBuffer, 0, sizeof(ExynosVideoBuffer));
+ if (pOutbufOps->ExtensionDequeue(hMFCHandle, &videoBuffer) == VIDEO_ERROR_NONE) {
+ pVideoBuffer = &videoBuffer;
+ } else {
+ pVideoBuffer = NULL;
ret = OMX_ErrorNone;
goto EXIT;
}
@@ -1851,6 +1842,28 @@ OMX_ERRORTYPE Exynos_H264Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX
}
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];
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x, FD[0]:%d, FD[1]:%d", __FUNCTION__, __LINE__,
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0],
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[1],
+ pVideoDec->pMFCDecOutputBuffer[i]->fd[0],
+ pVideoDec->pMFCDecOutputBuffer[i]->fd[1]);
+ 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;
@@ -1858,6 +1871,7 @@ OMX_ERRORTYPE Exynos_H264Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX
bufferGeometry = &pH264Dec->hMFCH264Handle.codecOutbufConf;
pBufferInfo->imageWidth = bufferGeometry->nFrameWidth;
pBufferInfo->imageHeight = bufferGeometry->nFrameHeight;
+ Exynos_OSAL_Memcpy(&pBufferInfo->PDSB, &pVideoBuffer->PDSB, sizeof(PrivateDataShareBuffer));
switch (bufferGeometry->eColorFormat) {
case VIDEO_COLORFORMAT_NV12:
pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420SemiPlanar;
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Android.mk b/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Android.mk
index 5f2f98e..d3dec8e 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Android.mk
@@ -26,7 +26,8 @@ LOCAL_ARM_MODE := arm
LOCAL_STATIC_LIBRARIES := libExynosOMX_Vdec libExynosOMX_OSAL libExynosOMX_Basecomponent \
libswconverter libExynosVideoApi
LOCAL_SHARED_LIBRARIES := libc libdl libcutils libutils liblog libui \
- libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos libexynosgscaler
+ libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos libexynosgscaler \
+ libhardware
ifeq ($(BOARD_USES_MFC_FPS),true)
LOCAL_CFLAGS += -DCONFIG_MFC_FPS
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Exynos_OMX_Mpeg4dec.c b/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Exynos_OMX_Mpeg4dec.c
index 0bc6bae..95aa02a 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Exynos_OMX_Mpeg4dec.c
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/mpeg4/Exynos_OMX_Mpeg4dec.c
@@ -672,8 +672,7 @@ OMX_ERRORTYPE Mpeg4CodecEnQueueAllBuffer(OMX_COMPONENTTYPE *pOMXComponent, OMX_U
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);
+ Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, pVideoDec->pMFCDecOutputBuffer[i]);
}
pOutbufOps->Clear_Queue(hMFCHandle);
} else {
@@ -918,8 +917,13 @@ OMX_ERRORTYPE Mpeg4CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
goto EXIT;
}
}
+ if (pOutbufOps->Enable_DynamicDPB(hMFCHandle) != VIDEO_ERROR_NONE) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
+
pOutbufOps->Set_Shareable(hMFCHandle);
- if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
+ if (pOutbufOps->Setup(hMFCHandle, MAX_OUTPUTBUFFER_NUM_DYNAMIC) != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
ret = OMX_ErrorInsufficientResources;
goto EXIT;
@@ -953,43 +957,27 @@ OMX_ERRORTYPE Mpeg4CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
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,
+ /* Enqueue output buffer */
+ pOutbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr,
+ (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->fd,
+ (unsigned int *)pVideoDec->pMFCDecOutputBuffer[i]->bufferSize,
(unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, 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) {
- /* 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++) {
- 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) {
- 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);
- }
- } else {
+ if ((pExynosOutputPort->bIsANBEnabled == OMX_FALSE) &&
+ (pExynosOutputPort->bStoreMetaData == OMX_FALSE)) {
ret = OMX_ErrorNotImplemented;
goto EXIT;
}
@@ -999,15 +987,6 @@ OMX_ERRORTYPE Mpeg4CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
#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) {
- Mpeg4CodecStop(pOMXComponent, OUTPUT_PORT_INDEX);
- }
pMpeg4Dec->hMFCMpeg4Handle.bConfiguredMFCDst = OMX_TRUE;
ret = OMX_ErrorNone;
@@ -1727,7 +1706,6 @@ OMX_ERRORTYPE Exynos_Mpeg4Dec_Terminate(OMX_COMPONENTTYPE *pOMXComponent)
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;
}
@@ -1895,13 +1873,21 @@ OMX_ERRORTYPE Exynos_Mpeg4Dec_DstIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX
goto EXIT;
}
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x", __FUNCTION__, __LINE__,
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x, FD[0]:%d, FD[1]:%d", __FUNCTION__, __LINE__,
pDstInputData->buffer.multiPlaneBuffer.dataBuffer[0],
- pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1]);
-
- codecReturn = pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
- (unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
-
+ pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1],
+ pDstInputData->buffer.multiPlaneBuffer.fd[0],
+ pDstInputData->buffer.multiPlaneBuffer.fd[1]);
+
+ OMX_U32 nAllocLen[VIDEO_BUFFER_MAX_PLANES] = {0, 0, 0};
+ nAllocLen[0] = pExynosOutputPort->portDefinition.format.video.nFrameWidth * pExynosOutputPort->portDefinition.format.video.nFrameHeight;
+ nAllocLen[1] = pExynosOutputPort->portDefinition.format.video.nFrameWidth * pExynosOutputPort->portDefinition.format.video.nFrameHeight / 2;
+
+ codecReturn = pOutbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
+ (unsigned int **)pDstInputData->buffer.multiPlaneBuffer.fd,
+ (unsigned int *)nAllocLen, (unsigned int *)dataLen,
+ MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
if (codecReturn != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
@@ -1929,6 +1915,7 @@ OMX_ERRORTYPE Exynos_Mpeg4Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OM
ExynosVideoDecOps *pDecOps = pMpeg4Dec->hMFCMpeg4Handle.pDecOps;
ExynosVideoDecBufferOps *pOutbufOps = pMpeg4Dec->hMFCMpeg4Handle.pOutbufOps;
ExynosVideoBuffer *pVideoBuffer;
+ ExynosVideoBuffer videoBuffer;
ExynosVideoFrameStatusType displayStatus = VIDEO_FRAME_STATUS_UNKNOWN;
ExynosVideoGeometry *bufferGeometry;
DECODE_CODEC_EXTRA_BUFFERINFO *pBufferInfo = NULL;
@@ -1943,7 +1930,11 @@ OMX_ERRORTYPE Exynos_Mpeg4Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OM
}
while (1) {
- if ((pVideoBuffer = pOutbufOps->Dequeue(hMFCHandle)) == NULL) {
+ Exynos_OSAL_Memset(&videoBuffer, 0, sizeof(ExynosVideoBuffer));
+ if (pOutbufOps->ExtensionDequeue(hMFCHandle, &videoBuffer) == VIDEO_ERROR_NONE) {
+ pVideoBuffer = &videoBuffer;
+ } else {
+ pVideoBuffer = NULL;
ret = OMX_ErrorNone;
goto EXIT;
}
@@ -1979,6 +1970,28 @@ OMX_ERRORTYPE Exynos_Mpeg4Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OM
}
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];
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x, FD[0]:%d, FD[1]:%d", __FUNCTION__, __LINE__,
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0],
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[1],
+ pVideoDec->pMFCDecOutputBuffer[i]->fd[0],
+ pVideoDec->pMFCDecOutputBuffer[i]->fd[1]);
+ 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;
@@ -1986,6 +1999,7 @@ OMX_ERRORTYPE Exynos_Mpeg4Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OM
bufferGeometry = &pMpeg4Dec->hMFCMpeg4Handle.codecOutbufConf;
pBufferInfo->imageWidth = bufferGeometry->nFrameWidth;
pBufferInfo->imageHeight = bufferGeometry->nFrameHeight;
+ Exynos_OSAL_Memcpy(&pBufferInfo->PDSB, &pVideoBuffer->PDSB, sizeof(PrivateDataShareBuffer));
switch (bufferGeometry->eColorFormat) {
case VIDEO_COLORFORMAT_NV12:
pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420SemiPlanar;
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Android.mk b/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Android.mk
index 54caa40..a6f5628 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Android.mk
@@ -26,7 +26,8 @@ LOCAL_ARM_MODE := arm
LOCAL_STATIC_LIBRARIES := libExynosOMX_Vdec libExynosOMX_OSAL libExynosOMX_Basecomponent \
libswconverter libExynosVideoApi
LOCAL_SHARED_LIBRARIES := libc libdl libcutils libutils liblog libui \
- libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos libexynosgscaler
+ libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos libexynosgscaler \
+ libhardware
ifeq ($(BOARD_USES_MFC_FPS),true)
LOCAL_CFLAGS += -DCONFIG_MFC_FPS
diff --git a/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Exynos_OMX_Vp8dec.c b/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Exynos_OMX_Vp8dec.c
index 8a18f15..bb8310d 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Exynos_OMX_Vp8dec.c
+++ b/exynos_omx/openmax/exynos_omx/component/video/dec/vp8/Exynos_OMX_Vp8dec.c
@@ -487,8 +487,7 @@ OMX_ERRORTYPE VP8CodecEnQueueAllBuffer(OMX_COMPONENTTYPE *pOMXComponent, OMX_U32
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);
+ Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, pVideoDec->pMFCDecOutputBuffer[i]);
}
pOutbufOps->Clear_Queue(hMFCHandle);
} else {
@@ -729,9 +728,13 @@ OMX_ERRORTYPE VP8CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
goto EXIT;
}
}
+ if (pOutbufOps->Enable_DynamicDPB(hMFCHandle) != VIDEO_ERROR_NONE) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
pOutbufOps->Set_Shareable(hMFCHandle);
- if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
+ if (pOutbufOps->Setup(hMFCHandle, MAX_OUTPUTBUFFER_NUM_DYNAMIC) != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
ret = OMX_ErrorInsufficientResources;
goto EXIT;
@@ -765,43 +768,27 @@ OMX_ERRORTYPE VP8CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
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,
+ /* Enqueue output buffer */
+ pOutbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr,
+ (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->fd,
+ (unsigned int *)pVideoDec->pMFCDecOutputBuffer[i]->bufferSize,
(unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, 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) {
- /* 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++) {
- 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) {
- 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);
- }
- } else {
+ if ((pExynosOutputPort->bIsANBEnabled == OMX_FALSE) &&
+ (pExynosOutputPort->bStoreMetaData == OMX_FALSE)) {
ret = OMX_ErrorNotImplemented;
goto EXIT;
}
@@ -811,15 +798,6 @@ OMX_ERRORTYPE VP8CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
#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) {
- VP8CodecStop (pOMXComponent, OUTPUT_PORT_INDEX);
- }
pVp8Dec->hMFCVp8Handle.bConfiguredMFCDst = OMX_TRUE;
ret = OMX_ErrorNone;
@@ -1319,7 +1297,6 @@ OMX_ERRORTYPE Exynos_VP8Dec_Terminate(OMX_COMPONENTTYPE *pOMXComponent)
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;
}
@@ -1487,13 +1464,21 @@ OMX_ERRORTYPE Exynos_VP8Dec_DstIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_D
goto EXIT;
}
- Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x", __FUNCTION__, __LINE__,
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x, FD[0]:%d, FD[1]:%d", __FUNCTION__, __LINE__,
pDstInputData->buffer.multiPlaneBuffer.dataBuffer[0],
- pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1]);
-
- codecReturn = pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
- (unsigned int *)dataLen, MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
-
+ pDstInputData->buffer.multiPlaneBuffer.dataBuffer[1],
+ pDstInputData->buffer.multiPlaneBuffer.fd[0],
+ pDstInputData->buffer.multiPlaneBuffer.fd[1]);
+
+ OMX_U32 nAllocLen[VIDEO_BUFFER_MAX_PLANES] = {0, 0, 0};
+ nAllocLen[0] = pExynosOutputPort->portDefinition.format.video.nFrameWidth * pExynosOutputPort->portDefinition.format.video.nFrameHeight;
+ nAllocLen[1] = pExynosOutputPort->portDefinition.format.video.nFrameWidth * pExynosOutputPort->portDefinition.format.video.nFrameHeight / 2;
+
+ codecReturn = pOutbufOps->ExtensionEnqueue(hMFCHandle,
+ (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
+ (unsigned int **)pDstInputData->buffer.multiPlaneBuffer.fd,
+ (unsigned int *)nAllocLen, (unsigned int *)dataLen,
+ MFC_OUTPUT_BUFFER_PLANE, pDstInputData->bufferHeader);
if (codecReturn != VIDEO_ERROR_NONE) {
Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
@@ -1521,6 +1506,7 @@ OMX_ERRORTYPE Exynos_VP8Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_
ExynosVideoDecOps *pDecOps = pVp8Dec->hMFCVp8Handle.pDecOps;
ExynosVideoDecBufferOps *pOutbufOps = pVp8Dec->hMFCVp8Handle.pOutbufOps;
ExynosVideoBuffer *pVideoBuffer;
+ ExynosVideoBuffer videoBuffer;
ExynosVideoFrameStatusType displayStatus = VIDEO_FRAME_STATUS_UNKNOWN;
ExynosVideoGeometry *bufferGeometry;
DECODE_CODEC_EXTRA_BUFFERINFO *pBufferInfo = NULL;
@@ -1535,7 +1521,11 @@ OMX_ERRORTYPE Exynos_VP8Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_
}
while (1) {
- if ((pVideoBuffer = pOutbufOps->Dequeue(hMFCHandle)) == NULL) {
+ Exynos_OSAL_Memset(&videoBuffer, 0, sizeof(ExynosVideoBuffer));
+ if (pOutbufOps->ExtensionDequeue(hMFCHandle, &videoBuffer) == VIDEO_ERROR_NONE) {
+ pVideoBuffer = &videoBuffer;
+ } else {
+ pVideoBuffer = NULL;
ret = OMX_ErrorNone;
goto EXIT;
}
@@ -1571,6 +1561,31 @@ OMX_ERRORTYPE Exynos_VP8Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_
}
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++) {
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecOutputBuffer[%d]:0x%x", i, pVideoDec->pMFCDecOutputBuffer[i]);
+ if ((pVideoDec->pMFCDecOutputBuffer[i] != NULL) &&
+ (pDstOutputData->buffer.multiPlaneBuffer.dataBuffer[0] ==
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0])) {
+ pDstOutputData->pPrivate = pVideoDec->pMFCDecOutputBuffer[i];
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[0]: 0x%x, ADDR[1]: 0x%x, FD[0]:%d, FD[1]:%d", __FUNCTION__, __LINE__,
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0],
+ pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[1],
+ pVideoDec->pMFCDecOutputBuffer[i]->fd[0],
+ pVideoDec->pMFCDecOutputBuffer[i]->fd[1]);
+ 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;
@@ -1578,6 +1593,7 @@ OMX_ERRORTYPE Exynos_VP8Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_
bufferGeometry = &pVp8Dec->hMFCVp8Handle.codecOutbufConf;
pBufferInfo->imageWidth = bufferGeometry->nFrameWidth;
pBufferInfo->imageHeight = bufferGeometry->nFrameHeight;
+ Exynos_OSAL_Memcpy(&pBufferInfo->PDSB, &pVideoBuffer->PDSB, sizeof(PrivateDataShareBuffer));
switch (bufferGeometry->eColorFormat) {
case VIDEO_COLORFORMAT_NV12:
pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420SemiPlanar;
diff --git a/exynos_omx/openmax/exynos_omx/component/video/enc/Exynos_OMX_Venc.c b/exynos_omx/openmax/exynos_omx/component/video/enc/Exynos_OMX_Venc.c
index e59a555..68ceaaf 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/enc/Exynos_OMX_Venc.c
+++ b/exynos_omx/openmax/exynos_omx/component/video/enc/Exynos_OMX_Venc.c
@@ -339,7 +339,7 @@ OMX_BOOL Exynos_Preprocessor_InputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_
#ifdef USE_METADATABUFFERTYPE
if (exynosInputPort->bStoreMetaData == OMX_TRUE) {
OMX_PTR ppBuf[MAX_BUFFER_PLANE];
- OMX_PTR allocSize[MAX_BUFFER_PLANE];
+ OMX_U32 allocSize[MAX_BUFFER_PLANE];
int plane = 0;
if (inputUseBuffer->dataLen <= 0) {
@@ -352,11 +352,11 @@ OMX_BOOL Exynos_Preprocessor_InputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_
/* Make EOS Buffer for MFC Processing scheme */
/* Use ION Allocator */
/*Alloc Y-Buffer */
- allocSize[0] = nFrameWidth * nFrameHeight;
+ allocSize[0] = ALIGN(nFrameWidth, 16) * ALIGN(nFrameHeight, 16);
srcInputData->buffer.multiPlaneBuffer.dataBuffer[0] = (void *)Exynos_OSAL_SharedMemory_Alloc(pVideoEnc->hSharedMemory, allocSize[0], NORMAL_MEMORY);
srcInputData->buffer.multiPlaneBuffer.fd[0] = Exynos_OSAL_SharedMemory_VirtToION(pVideoEnc->hSharedMemory, srcInputData->buffer.multiPlaneBuffer.dataBuffer[0]);
/*Alloc C-Buffer */
- allocSize[1] = nFrameWidth * nFrameHeight >> 1;
+ allocSize[1] = ALIGN(allocSize[0] / 2, 256);
srcInputData->buffer.multiPlaneBuffer.dataBuffer[1] = (void *)Exynos_OSAL_SharedMemory_Alloc(pVideoEnc->hSharedMemory, allocSize[1], NORMAL_MEMORY);
srcInputData->buffer.multiPlaneBuffer.fd[1] = Exynos_OSAL_SharedMemory_VirtToION(pVideoEnc->hSharedMemory, srcInputData->buffer.multiPlaneBuffer.dataBuffer[1]);
/* input buffers are 2 plane. */
diff --git a/exynos_omx/openmax/exynos_omx/component/video/enc/h264/Android.mk b/exynos_omx/openmax/exynos_omx/component/video/enc/h264/Android.mk
index 074d506..716fcd8 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/enc/h264/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/component/video/enc/h264/Android.mk
@@ -23,7 +23,8 @@ LOCAL_STATIC_LIBRARIES := libExynosOMX_Venc libExynosOMX_OSAL libExynosOMX_Basec
libswconverter libExynosVideoApi
LOCAL_SHARED_LIBRARIES := libc libdl libcutils libutils liblog libui \
- libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos
+ libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos \
+ libhardware
LOCAL_C_INCLUDES := $(EXYNOS_OMX_INC)/khronos \
$(EXYNOS_OMX_INC)/exynos \
diff --git a/exynos_omx/openmax/exynos_omx/component/video/enc/mpeg4/Android.mk b/exynos_omx/openmax/exynos_omx/component/video/enc/mpeg4/Android.mk
index e1c5af6..c7bdebf 100644
--- a/exynos_omx/openmax/exynos_omx/component/video/enc/mpeg4/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/component/video/enc/mpeg4/Android.mk
@@ -22,7 +22,8 @@ LOCAL_ARM_MODE := arm
LOCAL_STATIC_LIBRARIES := libExynosOMX_Venc libExynosOMX_OSAL libExynosOMX_Basecomponent \
libswconverter libExynosVideoApi
LOCAL_SHARED_LIBRARIES := libc libdl libcutils libutils liblog libui \
- libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos
+ libExynosOMX_Resourcemanager libcsc libexynosv4l2 libion_exynos \
+ libhardware
LOCAL_C_INCLUDES := $(EXYNOS_OMX_INC)/khronos \
$(EXYNOS_OMX_INC)/exynos \
diff --git a/exynos_omx/openmax/exynos_omx/include/exynos/Exynos_OMX_Def.h b/exynos_omx/openmax/exynos_omx/include/exynos/Exynos_OMX_Def.h
index 1980735..5c8f230 100644
--- a/exynos_omx/openmax/exynos_omx/include/exynos/Exynos_OMX_Def.h
+++ b/exynos_omx/openmax/exynos_omx/include/exynos/Exynos_OMX_Def.h
@@ -45,6 +45,7 @@
#define MAX_TIMESTAMP 40
#define MAX_FLAGS 40
+#define MAX_BUFFER_REF 40
#define MAX_BUFFER_PLANE 3
diff --git a/exynos_omx/openmax/exynos_omx/osal/Android.mk b/exynos_omx/openmax/exynos_omx/osal/Android.mk
index c58f5e0..ec9127a 100644
--- a/exynos_omx/openmax/exynos_omx/osal/Android.mk
+++ b/exynos_omx/openmax/exynos_omx/osal/Android.mk
@@ -25,6 +25,7 @@ ifeq ($(BOARD_USE_S3D_SUPPORT), true)
LOCAL_CFLAGS += -DS3D_SUPPORT
endif
+LOCAL_SHARED_LIBRARIES := libhardware
LOCAL_STATIC_LIBRARIES := liblog libcutils
LOCAL_C_INCLUDES := $(EXYNOS_OMX_INC)/khronos \
diff --git a/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.cpp b/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.cpp
index 3220345..7f10331 100644
--- a/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.cpp
+++ b/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.cpp
@@ -39,6 +39,7 @@
#include <media/hardware/MetadataBufferType.h>
#include <gralloc_priv.h>
+#include "Exynos_OSAL_Mutex.h"
#include "Exynos_OSAL_Semaphore.h"
#include "Exynos_OMX_Baseport.h"
#include "Exynos_OMX_Basecomponent.h"
@@ -47,6 +48,7 @@
#include "Exynos_OMX_Venc.h"
#include "Exynos_OSAL_Android.h"
#include "exynos_format.h"
+#include "ion.h"
#undef EXYNOS_LOG_TAG
#define EXYNOS_LOG_TAG "Exynos_OSAL_Android"
@@ -59,6 +61,11 @@ using namespace android;
extern "C" {
#endif
+int getIonFd(gralloc_module_t const *module)
+{
+ private_module_t* m = const_cast<private_module_t*>(reinterpret_cast<const private_module_t*>(module));
+ return m->ionfd;
+}
OMX_ERRORTYPE Exynos_OSAL_LockANBHandle(
OMX_IN OMX_U32 handle,
@@ -156,6 +163,21 @@ EXIT:
return ret;
}
+OMX_U32 Exynos_OSAL_GetANBStride(OMX_IN OMX_U32 handle)
+{
+ FunctionIn();
+
+ OMX_U32 nStride = 0;
+ private_handle_t *priv_hnd = (private_handle_t *) handle;
+
+ nStride = priv_hnd->stride;
+
+EXIT:
+ FunctionOut();
+
+ return nStride;
+}
+
OMX_ERRORTYPE Exynos_OSAL_LockANB(
OMX_IN OMX_PTR pBuffer,
OMX_IN OMX_U32 width,
@@ -193,6 +215,267 @@ EXIT:
return ret;
}
+OMX_ERRORTYPE Exynos_OSAL_LockMetaData(
+ OMX_IN OMX_PTR pBuffer,
+ OMX_IN OMX_U32 width,
+ OMX_IN OMX_U32 height,
+ OMX_IN OMX_COLOR_FORMATTYPE format,
+ OMX_OUT OMX_U32 *pStride,
+ OMX_OUT OMX_PTR planes)
+{
+ FunctionIn();
+
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ OMX_PTR pBuf;
+
+ ret = Exynos_OSAL_GetInfoFromMetaData((OMX_BYTE)pBuffer, &pBuf);
+ if (ret == OMX_ErrorNone) {
+ ret = Exynos_OSAL_LockANBHandle((OMX_U32)pBuf, width, height, format, planes);
+ *pStride = Exynos_OSAL_GetANBStride((OMX_U32)pBuf);
+ }
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
+OMX_ERRORTYPE Exynos_OSAL_UnlockMetaData(OMX_IN OMX_PTR pBuffer)
+{
+ FunctionIn();
+
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ OMX_PTR pBuf;
+
+ ret = Exynos_OSAL_GetInfoFromMetaData((OMX_BYTE)pBuffer, &pBuf);
+ if (ret == OMX_ErrorNone)
+ ret = Exynos_OSAL_UnlockANBHandle((OMX_U32)pBuf);
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
+OMX_HANDLETYPE Exynos_OSAL_RefANB_Create()
+{
+ int i = 0;
+ EXYNOS_OMX_REF_HANDLE *phREF = NULL;
+ OMX_ERRORTYPE err = OMX_ErrorNone;
+
+ FunctionIn();
+
+ phREF = (EXYNOS_OMX_REF_HANDLE *) Exynos_OSAL_Malloc(sizeof(EXYNOS_OMX_REF_HANDLE));
+ if (phREF == NULL)
+ goto EXIT;
+
+ Exynos_OSAL_Memset(phREF, 0, sizeof(EXYNOS_OMX_REF_HANDLE));
+ for (i = 0; i < MAX_BUFFER_REF; i++) {
+ phREF->SharedBuffer[i].BufferFd = -1;
+ phREF->SharedBuffer[i].BufferFd1 = -1;
+ phREF->SharedBuffer[i].BufferFd2 = -1;
+ }
+
+ err = Exynos_OSAL_MutexCreate(&phREF->hMutex);
+ if (err != OMX_ErrorNone) {
+ Exynos_OSAL_Free(phREF);
+ phREF = NULL;
+ }
+
+EXIT:
+ FunctionOut();
+
+ return ((OMX_HANDLETYPE)phREF);
+}
+
+OMX_ERRORTYPE Exynos_OSAL_RefANB_Reset(OMX_HANDLETYPE hREF)
+{
+ int i = 0;
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_REF_HANDLE *phREF = (EXYNOS_OMX_REF_HANDLE *)hREF;
+ gralloc_module_t* module = NULL;
+
+ FunctionIn();
+
+ if (phREF == NULL) {
+ ret = OMX_ErrorBadParameter;
+ goto EXIT;
+ }
+
+ hw_get_module(GRALLOC_HARDWARE_MODULE_ID, (const hw_module_t **)&module);
+
+ Exynos_OSAL_MutexLock(phREF->hMutex);
+ for (i = 0; i < MAX_BUFFER_REF; i++) {
+ if (phREF->SharedBuffer[i].BufferFd > -1) {
+ while(phREF->SharedBuffer[i].cnt > 0) {
+ if (phREF->SharedBuffer[i].BufferFd > -1)
+ ion_decRef(getIonFd(module), phREF->SharedBuffer[i].pIonHandle);
+ if (phREF->SharedBuffer[i].BufferFd1 > -1)
+ ion_decRef(getIonFd(module), phREF->SharedBuffer[i].pIonHandle1);
+ if (phREF->SharedBuffer[i].BufferFd2 > -1)
+ ion_decRef(getIonFd(module), phREF->SharedBuffer[i].pIonHandle2);
+ phREF->SharedBuffer[i].cnt--;
+ }
+ phREF->SharedBuffer[i].BufferFd = -1;
+ phREF->SharedBuffer[i].BufferFd1 = -1;
+ phREF->SharedBuffer[i].BufferFd2 = -1;
+ phREF->SharedBuffer[i].pIonHandle = NULL;
+ phREF->SharedBuffer[i].pIonHandle1 = NULL;
+ phREF->SharedBuffer[i].pIonHandle2 = NULL;
+ }
+ }
+ Exynos_OSAL_MutexUnlock(phREF->hMutex);
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
+OMX_ERRORTYPE Exynos_OSAL_RefANB_Terminate(OMX_HANDLETYPE hREF)
+{
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_REF_HANDLE *phREF = (EXYNOS_OMX_REF_HANDLE *)hREF;
+ FunctionIn();
+
+ if (phREF == NULL) {
+ ret = OMX_ErrorBadParameter;
+ goto EXIT;
+ }
+
+ Exynos_OSAL_RefANB_Reset(phREF);
+
+ ret = Exynos_OSAL_MutexTerminate(phREF->hMutex);
+ if (ret != OMX_ErrorNone)
+ goto EXIT;
+
+ Exynos_OSAL_Free(phREF);
+ phREF = NULL;
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
+OMX_ERRORTYPE Exynos_OSAL_RefANB_Increase(OMX_HANDLETYPE hREF, OMX_PTR pBuffer)
+{
+ int i;
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ buffer_handle_t bufferHandle = (buffer_handle_t) pBuffer;//pANB->handle;
+ private_handle_t *priv_hnd = (private_handle_t *) bufferHandle;
+ EXYNOS_OMX_REF_HANDLE *phREF = (EXYNOS_OMX_REF_HANDLE *)hREF;
+ gralloc_module_t* module = NULL;
+
+ unsigned long *pIonHandle;
+ unsigned long *pIonHandle1;
+ unsigned long *pIonHandle2;
+
+ FunctionIn();
+
+ if (phREF == NULL) {
+ ret = OMX_ErrorBadParameter;
+ goto EXIT;
+ }
+
+ hw_get_module(GRALLOC_HARDWARE_MODULE_ID, (const hw_module_t **)&module);
+
+ Exynos_OSAL_MutexLock(phREF->hMutex);
+
+ if (priv_hnd->fd >= 0) {
+ ion_incRef(getIonFd(module), priv_hnd->fd, &pIonHandle);
+ }
+ if (priv_hnd->fd1 >= 0) {
+ ion_incRef(getIonFd(module), priv_hnd->fd1, &pIonHandle1);
+ }
+ if (priv_hnd->fd2 >= 0) {
+ ion_incRef(getIonFd(module), priv_hnd->fd2, &pIonHandle2);
+ }
+
+ for (i = 0; i < MAX_BUFFER_REF; i++) {
+ if (phREF->SharedBuffer[i].BufferFd == priv_hnd->fd) {
+ phREF->SharedBuffer[i].cnt++;
+ break;
+ }
+ }
+
+ if (i >= MAX_BUFFER_REF) {
+ for (i = 0; i < MAX_BUFFER_REF; i++) {
+ if (phREF->SharedBuffer[i].BufferFd == -1) {
+ phREF->SharedBuffer[i].BufferFd = priv_hnd->fd;
+ phREF->SharedBuffer[i].BufferFd1 = priv_hnd->fd1;
+ phREF->SharedBuffer[i].BufferFd2 = priv_hnd->fd2;
+ phREF->SharedBuffer[i].pIonHandle = pIonHandle;
+ phREF->SharedBuffer[i].pIonHandle1 = pIonHandle1;
+ phREF->SharedBuffer[i].pIonHandle2 = pIonHandle2;
+ phREF->SharedBuffer[i].cnt++;
+ break;
+ }
+ }
+ }
+
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "inc fd:%d cnt:%d", phREF->SharedBuffer[i].BufferFd, phREF->SharedBuffer[i].cnt);
+
+ Exynos_OSAL_MutexUnlock(phREF->hMutex);
+
+ if (i >= MAX_BUFFER_REF) {
+ ret = OMX_ErrorUndefined;
+ }
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
+OMX_ERRORTYPE Exynos_OSAL_RefANB_Decrease(OMX_HANDLETYPE hREF, OMX_U32 BufferFd)
+{
+ int i;
+ OMX_ERRORTYPE ret = OMX_ErrorNone;
+ EXYNOS_OMX_REF_HANDLE *phREF = (EXYNOS_OMX_REF_HANDLE *)hREF;
+ gralloc_module_t* module = NULL;
+
+ FunctionIn();
+
+ if ((phREF == NULL) || (BufferFd < 0)) {
+ ret = OMX_ErrorBadParameter;
+ goto EXIT;
+ }
+
+ Exynos_OSAL_MutexLock(phREF->hMutex);
+ hw_get_module(GRALLOC_HARDWARE_MODULE_ID, (const hw_module_t **)&module);
+ for (i = 0; i < MAX_BUFFER_REF; i++) {
+ if (phREF->SharedBuffer[i].BufferFd == BufferFd) {
+ ion_decRef(getIonFd(module), phREF->SharedBuffer[i].pIonHandle);
+ ion_decRef(getIonFd(module), phREF->SharedBuffer[i].pIonHandle1);
+ ion_decRef(getIonFd(module), phREF->SharedBuffer[i].pIonHandle2);
+ phREF->SharedBuffer[i].cnt--;
+ if (phREF->SharedBuffer[i].cnt == 0) {
+ phREF->SharedBuffer[i].BufferFd = -1;
+ phREF->SharedBuffer[i].BufferFd1 = -1;
+ phREF->SharedBuffer[i].BufferFd2 = -1;
+ phREF->SharedBuffer[i].pIonHandle = NULL;
+ phREF->SharedBuffer[i].pIonHandle1 = NULL;
+ phREF->SharedBuffer[i].pIonHandle2 = NULL;
+ }
+ break;
+ }
+ }
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "dec fd:%d cnt:%d", phREF->SharedBuffer[i].BufferFd, phREF->SharedBuffer[i].cnt);
+
+ Exynos_OSAL_MutexUnlock(phREF->hMutex);
+
+ if (i >= MAX_BUFFER_REF) {
+ ret = OMX_ErrorUndefined;
+ goto EXIT;
+ }
+
+EXIT:
+ FunctionOut();
+
+ return ret;
+}
+
OMX_ERRORTYPE useAndroidNativeBuffer(
EXYNOS_OMX_BASEPORT *pExynosPort,
OMX_BUFFERHEADERTYPE **ppBufferHdr,
@@ -428,7 +711,8 @@ OMX_ERRORTYPE Exynos_OSAL_SetANBParameter(
}
/* ANB and DPB Buffer Sharing */
- pExynosPort->bIsANBEnabled = pANBParams->enable;
+ if (pExynosPort->bStoreMetaData != OMX_TRUE)
+ pExynosPort->bIsANBEnabled = pANBParams->enable;
if ((portIndex == OUTPUT_PORT_INDEX) &&
(pExynosPort->bIsANBEnabled == OMX_TRUE) &&
((pExynosPort->bufferProcessType & BUFFER_ANBSHARE) == BUFFER_ANBSHARE)) {
@@ -494,7 +778,6 @@ OMX_ERRORTYPE Exynos_OSAL_SetANBParameter(
case OMX_IndexParamStoreMetaDataBuffer:
{
- EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;;
StoreMetaDataInBuffersParams *pANBParams = (StoreMetaDataInBuffersParams *) ComponentParameterStructure;
OMX_U32 portIndex = pANBParams->nPortIndex;
EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
@@ -525,7 +808,20 @@ OMX_ERRORTYPE Exynos_OSAL_SetANBParameter(
}
pExynosPort->bStoreMetaData = pANBParams->bStoreMetaData;
- pVideoEnc->bFirstInput = OMX_TRUE;
+ if (pExynosComponent->codecType == HW_VIDEO_ENC_CODEC) {
+ EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;;
+ pVideoEnc->bFirstInput = OMX_TRUE;
+ } else if (pExynosComponent->codecType == HW_VIDEO_DEC_CODEC) {
+ EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;;
+ if ((portIndex == OUTPUT_PORT_INDEX) &&
+ (pExynosPort->bStoreMetaData == OMX_TRUE) &&
+ ((pExynosPort->bufferProcessType & BUFFER_ANBSHARE) == BUFFER_ANBSHARE)) {
+ pExynosPort->bufferProcessType = BUFFER_SHARE;
+ pExynosPort->portDefinition.format.video.eColorFormat = (OMX_COLOR_FORMATTYPE)OMX_SEC_COLOR_FormatNV12Tiled;
+ Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "OMX_IndexParamStoreMetaDataBuffer & bufferProcessType change to BUFFER_SHARE");
+ }
+
+ }
}
break;
diff --git a/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.h b/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.h
index 381b9f9..2996976 100644
--- a/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.h
+++ b/exynos_omx/openmax/exynos_omx/osal/Exynos_OSAL_Android.h
@@ -33,12 +33,30 @@
#include "OMX_Core.h"
#include "OMX_Index.h"
+typedef struct _EXYNOS_OMX_SHARED_BUFFER {
+ OMX_S32 BufferFd;
+ OMX_S32 BufferFd1;
+ OMX_S32 BufferFd2;
+ unsigned long *pIonHandle;
+ unsigned long *pIonHandle1;
+ unsigned long *pIonHandle2;
+ OMX_U32 cnt;
+} EXYNOS_OMX_SHARED_BUFFER;
+
+typedef struct _EXYNOS_OMX_REF_HANDLE {
+ OMX_HANDLETYPE hMutex;
+ EXYNOS_OMX_SHARED_BUFFER SharedBuffer[MAX_BUFFER_REF];
+} EXYNOS_OMX_REF_HANDLE;
+
+
#ifdef __cplusplus
extern "C" {
#endif
OMX_COLOR_FORMATTYPE Exynos_OSAL_GetANBColorFormat(OMX_IN OMX_U32 handle);
+OMX_U32 Exynos_OSAL_GetANBStride(OMX_IN OMX_U32 handle);
+
OMX_ERRORTYPE Exynos_OSAL_GetANBParameter(OMX_IN OMX_HANDLETYPE hComponent,
OMX_IN OMX_INDEXTYPE nIndex,
OMX_INOUT OMX_PTR ComponentParameterStructure);
@@ -56,6 +74,15 @@ OMX_ERRORTYPE Exynos_OSAL_LockANB(OMX_IN OMX_PTR pBuffer,
OMX_ERRORTYPE Exynos_OSAL_UnlockANB(OMX_IN OMX_PTR pBuffer);
+OMX_ERRORTYPE Exynos_OSAL_LockMetaData(OMX_IN OMX_PTR pBuffer,
+ OMX_IN OMX_U32 width,
+ OMX_IN OMX_U32 height,
+ OMX_IN OMX_COLOR_FORMATTYPE format,
+ OMX_OUT OMX_U32 *pStride,
+ OMX_OUT OMX_PTR planes);
+
+OMX_ERRORTYPE Exynos_OSAL_UnlockMetaData(OMX_IN OMX_PTR pBuffer);
+
OMX_ERRORTYPE Exynos_OSAL_LockANBHandle(OMX_IN OMX_U32 pBuffer,
OMX_IN OMX_U32 width,
OMX_IN OMX_U32 height,