Initial version of libomxil-e3250-v4l2
[platform/adaptation/ap_samsung/libomxil-e3250-v4l2.git] / openmax / component / video / enc / Exynos_OMX_VencControl.c
1 /*
2  *
3  * Copyright 2012 Samsung Electronics S.LSI Co. LTD
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  *      http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17
18 /*
19  * @file        Exynos_OMX_VencControl.c
20  * @brief
21  * @author      SeungBeom Kim (sbcrux.kim@samsung.com)
22  * @version     2.0.0
23  * @history
24  *   2012.02.20 : Create
25  */
26
27 #include <stdio.h>
28 #include <stdlib.h>
29 #include <string.h>
30 #include "Exynos_OMX_Macros.h"
31 #include "Exynos_OSAL_Event.h"
32 #include "Exynos_OMX_Venc.h"
33 #include "Exynos_OMX_VencControl.h"
34 #include "Exynos_OMX_Basecomponent.h"
35 #include "Exynos_OSAL_Thread.h"
36 #include "Exynos_OSAL_Semaphore.h"
37 #include "Exynos_OSAL_Mutex.h"
38 #include "Exynos_OSAL_ETC.h"
39 #include "Exynos_OSAL_SharedMemory.h"
40
41 #ifdef USE_PB
42 #include "Exynos_OSAL_Platform_Specific.h"
43 #endif
44
45 #undef  EXYNOS_LOG_TAG
46 #define EXYNOS_LOG_TAG    "EXYNOS_VIDEO_ENCCONTROL"
47 #define EXYNOS_LOG_OFF
48 //#define EXYNOS_TRACE_ON
49 #include "Exynos_OSAL_Log.h"
50
51
52 OMX_ERRORTYPE Exynos_OMX_UseBuffer(
53     OMX_IN OMX_HANDLETYPE            hComponent,
54     OMX_INOUT OMX_BUFFERHEADERTYPE **ppBufferHdr,
55     OMX_IN OMX_U32                   nPortIndex,
56     OMX_IN OMX_PTR                   pAppPrivate,
57     OMX_IN OMX_U32                   nSizeBytes,
58     OMX_IN OMX_U8                   *pBuffer)
59 {
60     OMX_ERRORTYPE                    ret               = OMX_ErrorNone;
61     OMX_COMPONENTTYPE               *pOMXComponent     = NULL;
62     EXYNOS_OMX_BASECOMPONENT        *pExynosComponent  = NULL;
63     EXYNOS_OMX_VIDEOENC_COMPONENT   *pVideoEnc         = NULL;
64     EXYNOS_OMX_BASEPORT             *pExynosPort       = NULL;
65     OMX_BUFFERHEADERTYPE            *pTempBufferHdr    = NULL;
66     OMX_U32 i = 0;
67
68     FunctionIn();
69
70     if (hComponent == NULL) {
71         ret = OMX_ErrorBadParameter;
72         goto EXIT;
73     }
74     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
75
76     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
77     if (ret != OMX_ErrorNone) {
78         goto EXIT;
79     }
80
81     if (pOMXComponent->pComponentPrivate == NULL) {
82         ret = OMX_ErrorBadParameter;
83         goto EXIT;
84     }
85     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
86
87     if (pExynosComponent->hComponentHandle == NULL) {
88         ret = OMX_ErrorBadParameter;
89         goto EXIT;
90     }
91     pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
92
93     if ((nPortIndex < 0) ||
94         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
95         ret = OMX_ErrorBadPortIndex;
96         goto EXIT;
97     }
98     pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
99
100     if (pExynosPort->portState != OMX_StateIdle) {
101         ret = OMX_ErrorIncorrectStateOperation;
102         goto EXIT;
103     }
104
105     if (CHECK_PORT_TUNNELED(pExynosPort) && CHECK_PORT_BUFFER_SUPPLIER(pExynosPort)) {
106         ret = OMX_ErrorBadPortIndex;
107         goto EXIT;
108     }
109
110     pTempBufferHdr = (OMX_BUFFERHEADERTYPE *)Exynos_OSAL_Malloc(sizeof(OMX_BUFFERHEADERTYPE));
111     if (pTempBufferHdr == NULL) {
112         ret = OMX_ErrorInsufficientResources;
113         goto EXIT;
114     }
115     Exynos_OSAL_Memset(pTempBufferHdr, 0, sizeof(OMX_BUFFERHEADERTYPE));
116
117     for (i = 0; i < pExynosPort->portDefinition.nBufferCountActual; i++) {
118         if (pExynosPort->bufferStateAllocate[i] == BUFFER_STATE_FREE) {
119             pExynosPort->extendBufferHeader[i].OMXBufferHeader = pTempBufferHdr;
120             pExynosPort->bufferStateAllocate[i] = (BUFFER_STATE_ASSIGNED | HEADER_STATE_ALLOCATED);
121             INIT_SET_SIZE_VERSION(pTempBufferHdr, OMX_BUFFERHEADERTYPE);
122             pTempBufferHdr->pBuffer        = pBuffer;
123             pTempBufferHdr->nAllocLen      = nSizeBytes;
124             pTempBufferHdr->pAppPrivate    = pAppPrivate;
125             if (nPortIndex == INPUT_PORT_INDEX)
126                 pTempBufferHdr->nInputPortIndex = INPUT_PORT_INDEX;
127             else
128                 pTempBufferHdr->nOutputPortIndex = OUTPUT_PORT_INDEX;
129 #ifdef SLP_PLATFORM
130             if (nPortIndex == OUTPUT_PORT_INDEX && pVideoEnc->bSharedOutputFD == OMX_TRUE)
131                 pExynosPort->extendBufferHeader[i].buf_fd[0] = (int)(pBuffer); /*IL Client provides only FD value*/
132 #endif
133             pExynosPort->assignedBufferNum++;
134             if (pExynosPort->assignedBufferNum == pExynosPort->portDefinition.nBufferCountActual) {
135                 pExynosPort->portDefinition.bPopulated = OMX_TRUE;
136                 /* Exynos_OSAL_MutexLock(pExynosComponent->compMutex); */
137                 Exynos_OSAL_SemaphorePost(pExynosPort->loadedResource);
138                 /* Exynos_OSAL_MutexUnlock(pExynosComponent->compMutex); */
139             }
140             *ppBufferHdr = pTempBufferHdr;
141             ret = OMX_ErrorNone;
142             goto EXIT;
143         }
144     }
145
146     Exynos_OSAL_Free(pTempBufferHdr);
147     ret = OMX_ErrorInsufficientResources;
148
149 EXIT:
150     FunctionOut();
151
152     return ret;
153 }
154
155 OMX_ERRORTYPE Exynos_OMX_AllocateBuffer(
156     OMX_IN OMX_HANDLETYPE            hComponent,
157     OMX_INOUT OMX_BUFFERHEADERTYPE **ppBufferHdr,
158     OMX_IN OMX_U32                   nPortIndex,
159     OMX_IN OMX_PTR                   pAppPrivate,
160     OMX_IN OMX_U32                   nSizeBytes)
161 {
162     OMX_ERRORTYPE                    ret                = OMX_ErrorNone;
163     OMX_COMPONENTTYPE               *pOMXComponent      = NULL;
164     EXYNOS_OMX_BASECOMPONENT        *pExynosComponent   = NULL;
165     EXYNOS_OMX_VIDEOENC_COMPONENT   *pVideoEnc          = NULL;
166     EXYNOS_OMX_BASEPORT             *pExynosPort        = NULL;
167     OMX_BUFFERHEADERTYPE            *pTempBufferHdr     = NULL;
168     OMX_U8                          *pTempBuffer        = NULL;
169     int                              fdTempBuffer       = -1;
170     MEMORY_TYPE                      eMemType;
171     OMX_U32                          i                  = 0;
172
173     FunctionIn();
174
175     if (hComponent == NULL) {
176         ret = OMX_ErrorBadParameter;
177         goto EXIT;
178     }
179     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
180
181     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
182     if (ret != OMX_ErrorNone) {
183         goto EXIT;
184     }
185
186     if (pOMXComponent->pComponentPrivate == NULL) {
187         ret = OMX_ErrorBadParameter;
188         goto EXIT;
189     }
190     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
191
192     if (pExynosComponent->hComponentHandle == NULL) {
193         ret = OMX_ErrorBadParameter;
194         goto EXIT;
195     }
196     pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
197
198     if ((nPortIndex < 0) ||
199         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
200         ret = OMX_ErrorBadPortIndex;
201         goto EXIT;
202     }
203     pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
204 /*
205     if (pExynosPort->portState != OMX_StateIdle ) {
206         ret = OMX_ErrorIncorrectStateOperation;
207         goto EXIT;
208     }
209 */
210     if (CHECK_PORT_TUNNELED(pExynosPort) && CHECK_PORT_BUFFER_SUPPLIER(pExynosPort)) {
211         ret = OMX_ErrorBadPortIndex;
212         goto EXIT;
213     }
214
215     if (pExynosPort->bufferProcessType & BUFFER_SHARE)
216         eMemType = NORMAL_MEMORY;
217     else
218         eMemType = SYSTEM_MEMORY;
219
220     pTempBuffer = Exynos_OSAL_SharedMemory_Alloc(pVideoEnc->hSharedMemory, nSizeBytes, eMemType);
221     if (pTempBuffer == NULL) {
222         ret = OMX_ErrorInsufficientResources;
223         goto EXIT;
224     }
225     fdTempBuffer = Exynos_OSAL_SharedMemory_VirtToION(pVideoEnc->hSharedMemory, pTempBuffer);
226
227     pTempBufferHdr = (OMX_BUFFERHEADERTYPE *)Exynos_OSAL_Malloc(sizeof(OMX_BUFFERHEADERTYPE));
228     if (pTempBufferHdr == NULL) {
229         Exynos_OSAL_SharedMemory_Free(pVideoEnc->hSharedMemory, pTempBuffer);
230         ret = OMX_ErrorInsufficientResources;
231         goto EXIT;
232     }
233     Exynos_OSAL_Memset(pTempBufferHdr, 0, sizeof(OMX_BUFFERHEADERTYPE));
234
235     for (i = 0; i < pExynosPort->portDefinition.nBufferCountActual; i++) {
236         if (pExynosPort->bufferStateAllocate[i] == BUFFER_STATE_FREE) {
237             pExynosPort->extendBufferHeader[i].OMXBufferHeader = pTempBufferHdr;
238             pExynosPort->extendBufferHeader[i].buf_fd[0] = fdTempBuffer;
239             pExynosPort->bufferStateAllocate[i] = (BUFFER_STATE_ALLOCATED | HEADER_STATE_ALLOCATED);
240             INIT_SET_SIZE_VERSION(pTempBufferHdr, OMX_BUFFERHEADERTYPE);
241             pTempBufferHdr->pBuffer        = pTempBuffer;
242             pTempBufferHdr->nAllocLen      = nSizeBytes;
243             pTempBufferHdr->pAppPrivate    = pAppPrivate;
244             if (nPortIndex == INPUT_PORT_INDEX)
245                 pTempBufferHdr->nInputPortIndex = INPUT_PORT_INDEX;
246             else
247                 pTempBufferHdr->nOutputPortIndex = OUTPUT_PORT_INDEX;
248             pExynosPort->assignedBufferNum++;
249             if (pExynosPort->assignedBufferNum == pExynosPort->portDefinition.nBufferCountActual) {
250                 pExynosPort->portDefinition.bPopulated = OMX_TRUE;
251                 /* Exynos_OSAL_MutexLock(pExynosComponent->compMutex); */
252                 Exynos_OSAL_SemaphorePost(pExynosPort->loadedResource);
253                 /* Exynos_OSAL_MutexUnlock(pExynosComponent->compMutex); */
254             }
255             *ppBufferHdr = pTempBufferHdr;
256             ret = OMX_ErrorNone;
257             goto EXIT;
258         }
259     }
260
261     Exynos_OSAL_Free(pTempBufferHdr);
262     Exynos_OSAL_SharedMemory_Free(pVideoEnc->hSharedMemory, pTempBuffer);
263     ret = OMX_ErrorInsufficientResources;
264
265 EXIT:
266     FunctionOut();
267
268     return ret;
269 }
270
271 OMX_ERRORTYPE Exynos_OMX_FreeBuffer(
272     OMX_IN OMX_HANDLETYPE        hComponent,
273     OMX_IN OMX_U32               nPortIndex,
274     OMX_IN OMX_BUFFERHEADERTYPE *pBufferHdr)
275 {
276     OMX_ERRORTYPE                    ret                = OMX_ErrorNone;
277     OMX_COMPONENTTYPE               *pOMXComponent      = NULL;
278     EXYNOS_OMX_BASECOMPONENT        *pExynosComponent   = NULL;
279     EXYNOS_OMX_VIDEOENC_COMPONENT   *pVideoEnc          = NULL;
280     EXYNOS_OMX_BASEPORT             *pExynosPort        = NULL;
281     OMX_BUFFERHEADERTYPE            *pOMXBufferHdr      = NULL;
282     OMX_U32                          i                  = 0;
283
284     FunctionIn();
285
286     if (hComponent == NULL) {
287         ret = OMX_ErrorBadParameter;
288         goto EXIT;
289     }
290     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
291
292     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
293     if (ret != OMX_ErrorNone) {
294         goto EXIT;
295     }
296
297     if (pOMXComponent->pComponentPrivate == NULL) {
298         ret = OMX_ErrorBadParameter;
299         goto EXIT;
300     }
301     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
302
303     if (pExynosComponent->hComponentHandle == NULL) {
304         ret = OMX_ErrorBadParameter;
305         goto EXIT;
306     }
307     pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
308
309     if ((nPortIndex < 0) ||
310         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
311         ret = OMX_ErrorBadPortIndex;
312         goto EXIT;
313     }
314     pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
315
316     if (CHECK_PORT_TUNNELED(pExynosPort) && CHECK_PORT_BUFFER_SUPPLIER(pExynosPort)) {
317         ret = OMX_ErrorBadPortIndex;
318         goto EXIT;
319     }
320
321     if ((pExynosPort->portState != OMX_StateLoaded) &&
322         (pExynosPort->portState != OMX_StateInvalid)) {
323         (*(pExynosComponent->pCallbacks->EventHandler)) (pOMXComponent,
324                         pExynosComponent->callbackData,
325                         (OMX_U32)OMX_EventError,
326                         (OMX_U32)OMX_ErrorPortUnpopulated,
327                         nPortIndex, NULL);
328     }
329
330     for (i = 0; i < /*pExynosPort->portDefinition.nBufferCountActual*/MAX_BUFFER_NUM; i++) {
331         if ((pExynosPort->bufferStateAllocate[i] != BUFFER_STATE_FREE) &&
332             (pExynosPort->extendBufferHeader[i].OMXBufferHeader != NULL)) {
333             pOMXBufferHdr = pExynosPort->extendBufferHeader[i].OMXBufferHeader;
334
335             if (pOMXBufferHdr->pBuffer == pBufferHdr->pBuffer) {
336                 if (pExynosPort->bufferStateAllocate[i] & BUFFER_STATE_ALLOCATED) {
337                     Exynos_OSAL_SharedMemory_Free(pVideoEnc->hSharedMemory, pOMXBufferHdr->pBuffer);
338                     pOMXBufferHdr->pBuffer = NULL;
339                     pBufferHdr->pBuffer = NULL;
340                 } else if (pExynosPort->bufferStateAllocate[i] & BUFFER_STATE_ASSIGNED) {
341                     ; /* None*/
342                 }
343                 pExynosPort->assignedBufferNum--;
344
345                 if (pExynosPort->bufferStateAllocate[i] & HEADER_STATE_ALLOCATED) {
346                     Exynos_OSAL_Free(pOMXBufferHdr);
347                     pExynosPort->extendBufferHeader[i].OMXBufferHeader = NULL;
348                     pBufferHdr = NULL;
349                 }
350
351                 pExynosPort->bufferStateAllocate[i] = BUFFER_STATE_FREE;
352                 ret = OMX_ErrorNone;
353                 goto EXIT;
354             }
355         }
356     }
357
358 EXIT:
359     if ((ret == OMX_ErrorNone) &&
360         (pExynosPort->assignedBufferNum == 0)) {
361         Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pExynosPort->unloadedResource signal set");
362         /* Exynos_OSAL_MutexLock(pExynosComponent->compMutex); */
363         Exynos_OSAL_SemaphorePost(pExynosPort->unloadedResource);
364         /* Exynos_OSAL_MutexUnlock(pExynosComponent->compMutex); */
365         pExynosPort->portDefinition.bPopulated = OMX_FALSE;
366     }
367
368     FunctionOut();
369
370     return ret;
371 }
372
373 OMX_ERRORTYPE Exynos_OMX_AllocateTunnelBuffer(
374     EXYNOS_OMX_BASEPORT     *pOMXBasePort,
375     OMX_U32                  nPortIndex)
376 {
377     OMX_ERRORTYPE                 ret               = OMX_ErrorNone;
378     EXYNOS_OMX_BASEPORT          *pExynosPort       = NULL;
379     OMX_BUFFERHEADERTYPE         *pTempBufferHdr    = NULL;
380     OMX_U8                       *pTempBuffer       = NULL;
381     OMX_U32                       nBufferSize       = 0;
382     OMX_PARAM_PORTDEFINITIONTYPE  portDefinition;
383
384     ret = OMX_ErrorTunnelingUnsupported;
385 EXIT:
386     return ret;
387 }
388
389 OMX_ERRORTYPE Exynos_OMX_FreeTunnelBuffer(
390     EXYNOS_OMX_BASEPORT     *pOMXBasePort,
391     OMX_U32                  nPortIndex)
392 {
393     OMX_ERRORTYPE            ret            = OMX_ErrorNone;
394     EXYNOS_OMX_BASEPORT     *pExynosPort    = NULL;
395     OMX_BUFFERHEADERTYPE    *pTempBufferHdr = NULL;
396     OMX_U8                  *pTempBuffer    = NULL;
397     OMX_U32                  nBufferSize    = 0;
398
399     ret = OMX_ErrorTunnelingUnsupported;
400 EXIT:
401     return ret;
402 }
403
404 OMX_ERRORTYPE Exynos_OMX_ComponentTunnelRequest(
405     OMX_IN OMX_HANDLETYPE hComp,
406     OMX_IN OMX_U32        nPort,
407     OMX_IN OMX_HANDLETYPE hTunneledComp,
408     OMX_IN OMX_U32        nTunneledPort,
409     OMX_INOUT OMX_TUNNELSETUPTYPE *pTunnelSetup)
410 {
411     OMX_ERRORTYPE ret = OMX_ErrorNone;
412
413     ret = OMX_ErrorTunnelingUnsupported;
414 EXIT:
415     return ret;
416 }
417
418 OMX_ERRORTYPE Exynos_OMX_GetFlushBuffer(
419     EXYNOS_OMX_BASEPORT     *pExynosPort,
420     EXYNOS_OMX_DATABUFFER   *pDataBuffer[])
421 {
422     OMX_ERRORTYPE ret = OMX_ErrorNone;
423
424     FunctionIn();
425
426     *pDataBuffer = NULL;
427
428     if (pExynosPort->portWayType == WAY1_PORT) {
429         *pDataBuffer = &pExynosPort->way.port1WayDataBuffer.dataBuffer;
430     } else if (pExynosPort->portWayType == WAY2_PORT) {
431         pDataBuffer[0] = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
432         pDataBuffer[1] = &(pExynosPort->way.port2WayDataBuffer.outputDataBuffer);
433     }
434
435 EXIT:
436     FunctionOut();
437
438     return ret;
439 }
440
441 OMX_ERRORTYPE Exynos_OMX_FlushPort(
442     OMX_COMPONENTTYPE   *pOMXComponent,
443     OMX_S32              nPortIndex)
444 {
445     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
446     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
447     EXYNOS_OMX_BASEPORT      *pExynosPort       = NULL;
448     OMX_BUFFERHEADERTYPE     *pBufferHdr        = NULL;
449     EXYNOS_OMX_DATABUFFER    *pDataBuffer[2]    = {NULL, NULL};
450     EXYNOS_OMX_MESSAGE       *pMessage          = NULL;
451     OMX_S32                   nSemaCnt          = 0;
452     int                       i                 = 0;
453
454     FunctionIn();
455 #ifdef SLP_PLATFORM
456     Exynos_OSAL_Log(EXYNOS_LOG_WARNING, "flushPort idx:%d", nPortIndex);
457 #endif
458
459     if (pOMXComponent == NULL) {
460         ret = OMX_ErrorBadParameter;
461         goto EXIT;
462     }
463
464     if (pOMXComponent->pComponentPrivate == NULL) {
465         ret = OMX_ErrorBadParameter;
466         goto EXIT;
467     }
468     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
469
470     if ((nPortIndex < 0) ||
471         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
472         ret = OMX_ErrorBadPortIndex;
473         goto EXIT;
474     }
475     pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
476
477     while (Exynos_OSAL_GetElemNum(&pExynosPort->bufferQ) > 0) {
478         Exynos_OSAL_Get_SemaphoreCount(pExynosPort->bufferSemID, &nSemaCnt);
479         if (nSemaCnt == 0)
480             Exynos_OSAL_SemaphorePost(pExynosPort->bufferSemID);
481
482         Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
483         pMessage = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
484         if ((pMessage != NULL) &&
485             (pMessage->messageType != EXYNOS_OMX_CommandFakeBuffer)) {
486             pBufferHdr = (OMX_BUFFERHEADERTYPE *)pMessage->pCmdData;
487             pBufferHdr->nFilledLen = 0;
488
489             if (nPortIndex == OUTPUT_PORT_INDEX) {
490                 Exynos_OMX_OutputBufferReturn(pOMXComponent, pBufferHdr);
491             } else if (nPortIndex == INPUT_PORT_INDEX) {
492                 Exynos_OMX_InputBufferReturn(pOMXComponent, pBufferHdr);
493             }
494         }
495         Exynos_OSAL_Free(pMessage);
496         pMessage = NULL;
497     }
498
499     Exynos_OMX_GetFlushBuffer(pExynosPort, pDataBuffer);
500     if ((pDataBuffer[0] != NULL) &&
501         (pDataBuffer[0]->dataValid == OMX_TRUE)) {
502         if (nPortIndex == INPUT_PORT_INDEX)
503             Exynos_FlushInputBufferReturn(pOMXComponent, pDataBuffer[0]);
504         else if (nPortIndex == OUTPUT_PORT_INDEX)
505             Exynos_FlushOutputBufferReturn(pOMXComponent, pDataBuffer[0]);
506     }
507     if ((pDataBuffer[1] != NULL) &&
508         (pDataBuffer[1]->dataValid == OMX_TRUE)) {
509         if (nPortIndex == INPUT_PORT_INDEX)
510             Exynos_FlushInputBufferReturn(pOMXComponent, pDataBuffer[1]);
511         else if (nPortIndex == OUTPUT_PORT_INDEX)
512             Exynos_FlushOutputBufferReturn(pOMXComponent, pDataBuffer[1]);
513     }
514
515     if (pExynosComponent->bMultiThreadProcess == OMX_TRUE) {
516         if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
517             if (pExynosPort->processData.bufferHeader != NULL) {
518                 if (nPortIndex == INPUT_PORT_INDEX) {
519                     Exynos_OMX_InputBufferReturn(pOMXComponent, pExynosPort->processData.bufferHeader);
520                 } else if (nPortIndex == OUTPUT_PORT_INDEX) {
521                     Exynos_OMX_OutputBufferReturn(pOMXComponent, pExynosPort->processData.bufferHeader);
522                 }
523             }
524             Exynos_ResetCodecData(&pExynosPort->processData);
525
526             for (i = 0; i < pExynosPort->portDefinition.nBufferCountActual; i++) {
527                 if (pExynosPort->extendBufferHeader[i].bBufferInOMX == OMX_TRUE) {
528                     if (nPortIndex == OUTPUT_PORT_INDEX) {
529                         Exynos_OMX_OutputBufferReturn(pOMXComponent,
530                                                       pExynosPort->extendBufferHeader[i].OMXBufferHeader);
531                     } else if (nPortIndex == INPUT_PORT_INDEX) {
532                         Exynos_OMX_InputBufferReturn(pOMXComponent,
533                                                      pExynosPort->extendBufferHeader[i].OMXBufferHeader);
534                     }
535                 }
536             }
537         }
538     } else {
539         Exynos_ResetCodecData(&pExynosPort->processData);
540     }
541
542     while (1) {
543         OMX_S32 cnt = 0;
544         Exynos_OSAL_Get_SemaphoreCount(pExynosPort->bufferSemID, &cnt);
545         if (cnt <= 0)
546             break;
547         Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
548     }
549     Exynos_OSAL_ResetQueue(&pExynosPort->bufferQ);
550
551 EXIT:
552     FunctionOut();
553
554     return ret;
555 }
556
557 OMX_ERRORTYPE Exynos_OMX_BufferFlush(
558     OMX_COMPONENTTYPE   *pOMXComponent,
559     OMX_S32              nPortIndex,
560     OMX_BOOL             bEvent)
561 {
562     OMX_ERRORTYPE                    ret                = OMX_ErrorNone;
563     EXYNOS_OMX_BASECOMPONENT        *pExynosComponent   = NULL;
564     EXYNOS_OMX_VIDEOENC_COMPONENT   *pVideoEnc          = NULL;
565     EXYNOS_OMX_BASEPORT             *pExynosPort        = NULL;
566     EXYNOS_OMX_DATABUFFER           *pDataBuffer[2]     = {NULL, NULL};
567     OMX_U32                          i                  = 0;
568
569     FunctionIn();
570 #ifdef SLP_PLATFORM
571     Exynos_OSAL_Log(EXYNOS_LOG_WARNING, "bufferFlush idx:%d", nPortIndex);
572 #endif
573
574     if (pOMXComponent == NULL) {
575         ret = OMX_ErrorBadParameter;
576         goto EXIT;
577     }
578
579     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
580     if (ret != OMX_ErrorNone) {
581         goto EXIT;
582     }
583
584     if (pOMXComponent->pComponentPrivate == NULL) {
585         ret = OMX_ErrorBadParameter;
586         goto EXIT;
587     }
588     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
589
590     if (pExynosComponent->hComponentHandle == NULL) {
591         ret = OMX_ErrorBadParameter;
592         goto EXIT;
593     }
594     pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
595
596     if ((nPortIndex < 0) ||
597         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
598         ret = OMX_ErrorBadPortIndex;
599         goto EXIT;
600     }
601     pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
602
603     Exynos_OSAL_Log(EXYNOS_LOG_TRACE,"OMX_CommandFlush start, port:%d", nPortIndex);
604
605     pExynosPort->bIsPortFlushed = OMX_TRUE;
606
607     if (pExynosComponent->bMultiThreadProcess == OMX_FALSE) {
608         Exynos_OSAL_SignalSet(pExynosComponent->pauseEvent);
609     } else {
610         Exynos_OSAL_SignalSet(pExynosPort->pauseEvent);
611     }
612
613     Exynos_OMX_GetFlushBuffer(pExynosPort, pDataBuffer);
614     if (pDataBuffer[0] == NULL) {
615         ret = OMX_ErrorBadParameter;
616         goto EXIT;
617     }
618
619     if (pExynosPort->bufferProcessType & BUFFER_COPY)
620         Exynos_OSAL_SemaphorePost(pExynosPort->codecSemID);
621     Exynos_OSAL_SemaphorePost(pExynosPort->bufferSemID);
622
623     pVideoEnc->exynos_codec_bufferProcessRun(pOMXComponent, nPortIndex);
624
625     Exynos_OSAL_MutexLock(pDataBuffer[0]->bufferMutex);
626     pVideoEnc->exynos_codec_stop(pOMXComponent, nPortIndex);
627
628     if (pDataBuffer[1] != NULL)
629         Exynos_OSAL_MutexLock(pDataBuffer[1]->bufferMutex);
630
631     ret = Exynos_OMX_FlushPort(pOMXComponent, nPortIndex);
632     if (ret != OMX_ErrorNone)
633         goto EXIT;
634
635     if (pExynosPort->bufferProcessType & BUFFER_COPY)
636         pVideoEnc->exynos_codec_enqueueAllBuffer(pOMXComponent, nPortIndex);
637     Exynos_ResetCodecData(&pExynosPort->processData);
638
639     if (ret == OMX_ErrorNone) {
640         if (nPortIndex == INPUT_PORT_INDEX) {
641             pExynosComponent->checkTimeStamp.needSetStartTimeStamp = OMX_TRUE;
642             pExynosComponent->checkTimeStamp.needCheckStartTimeStamp = OMX_FALSE;
643             Exynos_OSAL_Memset(pExynosComponent->timeStamp, -19771003, sizeof(OMX_TICKS) * MAX_TIMESTAMP);
644             Exynos_OSAL_Memset(pExynosComponent->nFlags, 0, sizeof(OMX_U32) * MAX_FLAGS);
645             pExynosComponent->getAllDelayBuffer = OMX_FALSE;
646             pExynosComponent->bSaveFlagEOS = OMX_FALSE;
647             pExynosComponent->reInputData = OMX_FALSE;
648         }
649
650         pExynosPort->bIsPortFlushed = OMX_FALSE;
651         Exynos_OSAL_Log(EXYNOS_LOG_TRACE,"OMX_CommandFlush EventCmdComplete, port:%d", nPortIndex);
652         if (bEvent == OMX_TRUE)
653             pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent,
654                             pExynosComponent->callbackData,
655                             OMX_EventCmdComplete,
656                             OMX_CommandFlush, nPortIndex, NULL);
657     }
658
659     if (pDataBuffer[1] != NULL)
660         Exynos_OSAL_MutexUnlock(pDataBuffer[1]->bufferMutex);
661
662     Exynos_OSAL_MutexUnlock(pDataBuffer[0]->bufferMutex);
663
664 EXIT:
665     if ((ret != OMX_ErrorNone) && (pOMXComponent != NULL) && (pExynosComponent != NULL)) {
666         Exynos_OSAL_Log(EXYNOS_LOG_ERROR,"%s : %d", __FUNCTION__, __LINE__);
667         pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
668                         pExynosComponent->callbackData,
669                         OMX_EventError,
670                         ret, 0, NULL);
671     }
672
673     FunctionOut();
674
675     return ret;
676 }
677
678 OMX_ERRORTYPE Exynos_InputBufferReturn(
679     OMX_COMPONENTTYPE   *pOMXComponent)
680 {
681     OMX_ERRORTYPE                ret                = OMX_ErrorNone;
682     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent   = NULL;
683     EXYNOS_OMX_BASEPORT         *pExynosPort        = NULL;
684     EXYNOS_OMX_DATABUFFER       *pDataBuffer        = NULL;
685     OMX_BUFFERHEADERTYPE        *pBufferHdr         = NULL;
686
687     FunctionIn();
688
689     if (pOMXComponent == NULL) {
690         ret = OMX_ErrorBadParameter;
691         goto EXIT;
692     }
693
694     if (pOMXComponent->pComponentPrivate == NULL) {
695         ret = OMX_ErrorBadParameter;
696         goto EXIT;
697     }
698     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
699     pExynosPort = &(pExynosComponent->pExynosPort[INPUT_PORT_INDEX]);
700
701     if (pExynosPort->bufferProcessType & BUFFER_COPY) {
702         pDataBuffer = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
703     } else if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
704         pDataBuffer = &(pExynosPort->way.port2WayDataBuffer.outputDataBuffer);
705     }
706
707     pBufferHdr = pDataBuffer->bufferHeader;
708
709     if (pBufferHdr != NULL) {
710         if (pExynosPort->markType.hMarkTargetComponent != NULL) {
711             pBufferHdr->hMarkTargetComponent = pExynosPort->markType.hMarkTargetComponent;
712             pBufferHdr->pMarkData            = pExynosPort->markType.pMarkData;
713             pExynosPort->markType.hMarkTargetComponent = NULL;
714             pExynosPort->markType.pMarkData = NULL;
715         }
716
717         if (pBufferHdr->hMarkTargetComponent != NULL) {
718             if (pBufferHdr->hMarkTargetComponent == pOMXComponent) {
719                 pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
720                                 pExynosComponent->callbackData,
721                                 OMX_EventMark,
722                                 0, 0, pBufferHdr->pMarkData);
723             } else {
724                 pExynosComponent->propagateMarkType.hMarkTargetComponent = pBufferHdr->hMarkTargetComponent;
725                 pExynosComponent->propagateMarkType.pMarkData = pBufferHdr->pMarkData;
726             }
727         }
728
729         pBufferHdr->nFilledLen = 0;
730         pBufferHdr->nOffset = 0;
731         Exynos_OMX_InputBufferReturn(pOMXComponent, pBufferHdr);
732     }
733
734     /* reset dataBuffer */
735     Exynos_ResetDataBuffer(pDataBuffer);
736
737 EXIT:
738     FunctionOut();
739
740     return ret;
741 }
742
743 OMX_ERRORTYPE Exynos_FlushInputBufferReturn(
744     OMX_COMPONENTTYPE       *pOMXComponent,
745     EXYNOS_OMX_DATABUFFER   *pDataBuffer)
746 {
747     OMX_ERRORTYPE                ret = OMX_ErrorNone;
748     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent   = NULL;
749     EXYNOS_OMX_BASEPORT         *pExynosPort        = NULL;
750     OMX_BUFFERHEADERTYPE        *pBufferHdr         = NULL;
751
752     FunctionIn();
753
754     if (pOMXComponent == NULL) {
755         ret = OMX_ErrorBadParameter;
756         goto EXIT;
757     }
758
759     if (pOMXComponent->pComponentPrivate == NULL) {
760         ret = OMX_ErrorBadParameter;
761         goto EXIT;
762     }
763     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
764     pExynosPort = &(pExynosComponent->pExynosPort[INPUT_PORT_INDEX]);
765
766     pBufferHdr = pDataBuffer->bufferHeader;
767
768     if (pBufferHdr != NULL) {
769         if (pExynosPort->markType.hMarkTargetComponent != NULL) {
770             pBufferHdr->hMarkTargetComponent  = pExynosPort->markType.hMarkTargetComponent;
771             pBufferHdr->pMarkData             = pExynosPort->markType.pMarkData;
772             pExynosPort->markType.hMarkTargetComponent = NULL;
773             pExynosPort->markType.pMarkData = NULL;
774         }
775
776         if (pBufferHdr->hMarkTargetComponent != NULL) {
777             if (pBufferHdr->hMarkTargetComponent == pOMXComponent) {
778                 pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
779                                 pExynosComponent->callbackData,
780                                 OMX_EventMark,
781                                 0, 0, pBufferHdr->pMarkData);
782             } else {
783                 pExynosComponent->propagateMarkType.hMarkTargetComponent = pBufferHdr->hMarkTargetComponent;
784                 pExynosComponent->propagateMarkType.pMarkData = pBufferHdr->pMarkData;
785             }
786         }
787
788         pBufferHdr->nFilledLen = 0;
789         pBufferHdr->nOffset = 0;
790         Exynos_OMX_InputBufferReturn(pOMXComponent, pBufferHdr);
791     }
792
793     /* reset dataBuffer */
794     Exynos_ResetDataBuffer(pDataBuffer);
795
796 EXIT:
797     FunctionOut();
798
799     return ret;
800 }
801
802 OMX_ERRORTYPE Exynos_InputBufferGetQueue(
803     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent)
804 {
805     OMX_ERRORTYPE          ret          = OMX_ErrorUndefined;
806     EXYNOS_OMX_BASEPORT   *pExynosPort  = NULL;
807     EXYNOS_OMX_MESSAGE    *pMessage     = NULL;
808     EXYNOS_OMX_DATABUFFER *pDataBuffer  = NULL;
809
810     FunctionIn();
811
812     if (pExynosComponent == NULL) {
813         ret = OMX_ErrorBadParameter;
814         goto EXIT;
815     }
816     pExynosPort = &(pExynosComponent->pExynosPort[INPUT_PORT_INDEX]);
817     pDataBuffer = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
818
819     if (pExynosComponent->currentState != OMX_StateExecuting) {
820         ret = OMX_ErrorUndefined;
821         goto EXIT;
822     } else if ((pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) &&
823                (!CHECK_PORT_BEING_FLUSHED(pExynosPort))) {
824         Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
825         if (pDataBuffer->dataValid != OMX_TRUE) {
826             pMessage = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
827             if (pMessage == NULL) {
828                 ret = OMX_ErrorUndefined;
829                 goto EXIT;
830             }
831             if (pMessage->messageType == EXYNOS_OMX_CommandFakeBuffer) {
832                 Exynos_OSAL_Free(pMessage);
833                 ret = OMX_ErrorCodecFlush;
834                 goto EXIT;
835             }
836
837             pDataBuffer->bufferHeader  = (OMX_BUFFERHEADERTYPE *)(pMessage->pCmdData);
838             pDataBuffer->allocSize     = pDataBuffer->bufferHeader->nAllocLen;
839             pDataBuffer->dataLen       = pDataBuffer->bufferHeader->nFilledLen;
840             pDataBuffer->remainDataLen = pDataBuffer->dataLen;
841             pDataBuffer->usedDataLen   = 0;
842             pDataBuffer->dataValid     = OMX_TRUE;
843             pDataBuffer->nFlags        = pDataBuffer->bufferHeader->nFlags;
844             pDataBuffer->timeStamp     = pDataBuffer->bufferHeader->nTimeStamp;
845
846             Exynos_OSAL_Free(pMessage);
847
848 #ifndef SLP_PLATFORM
849             if (pDataBuffer->allocSize <= pDataBuffer->dataLen)
850                 Exynos_OSAL_Log(EXYNOS_LOG_WARNING, "Input Buffer Full, Check input buffer size! allocSize:%d, dataLen:%d", pDataBuffer->allocSize, pDataBuffer->dataLen);
851 #endif
852         }
853         ret = OMX_ErrorNone;
854     }
855 EXIT:
856     FunctionOut();
857
858     return ret;
859 }
860
861 OMX_ERRORTYPE Exynos_OutputBufferReturn(
862     OMX_COMPONENTTYPE   *pOMXComponent)
863 {
864     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
865     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
866     EXYNOS_OMX_BASEPORT      *pExynosPort       = NULL;
867     EXYNOS_OMX_DATABUFFER    *pDataBuffer       = NULL;
868     OMX_BUFFERHEADERTYPE     *pBufferHdr        = NULL;
869
870     FunctionIn();
871
872     if (pOMXComponent == NULL) {
873         ret = OMX_ErrorBadParameter;
874         goto EXIT;
875     }
876
877     if (pOMXComponent->pComponentPrivate == NULL) {
878         ret = OMX_ErrorBadParameter;
879         goto EXIT;
880     }
881     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
882     pExynosPort = &(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]);
883
884     pDataBuffer = &(pExynosPort->way.port2WayDataBuffer.outputDataBuffer);
885     pBufferHdr = pDataBuffer->bufferHeader;
886
887     if (pBufferHdr != NULL) {
888         pBufferHdr->nFilledLen = pDataBuffer->remainDataLen;
889         pBufferHdr->nOffset    = 0;
890         pBufferHdr->nFlags     = pDataBuffer->nFlags;
891         pBufferHdr->nTimeStamp = pDataBuffer->timeStamp;
892
893         if (pExynosComponent->propagateMarkType.hMarkTargetComponent != NULL) {
894             pBufferHdr->hMarkTargetComponent = pExynosComponent->propagateMarkType.hMarkTargetComponent;
895             pBufferHdr->pMarkData            = pExynosComponent->propagateMarkType.pMarkData;
896             pExynosComponent->propagateMarkType.hMarkTargetComponent = NULL;
897             pExynosComponent->propagateMarkType.pMarkData = NULL;
898         }
899
900         if ((pBufferHdr->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) {
901             pBufferHdr->nFilledLen = 0;
902             Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "event OMX_BUFFERFLAG_EOS!!!");
903             pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
904                             pExynosComponent->callbackData,
905                             OMX_EventBufferFlag,
906                             OUTPUT_PORT_INDEX,
907                             pBufferHdr->nFlags, NULL);
908         }
909
910         Exynos_OMX_OutputBufferReturn(pOMXComponent, pBufferHdr);
911     }
912
913     /* reset dataBuffer */
914     Exynos_ResetDataBuffer(pDataBuffer);
915
916 EXIT:
917     FunctionOut();
918
919     return ret;
920 }
921
922 OMX_ERRORTYPE Exynos_FlushOutputBufferReturn(
923     OMX_COMPONENTTYPE       *pOMXComponent,
924     EXYNOS_OMX_DATABUFFER   *pDataBuffer)
925 {
926     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
927     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
928     OMX_BUFFERHEADERTYPE     *pBufferHdr        = NULL;
929
930     FunctionIn();
931
932     if (pOMXComponent == NULL) {
933         ret = OMX_ErrorBadParameter;
934         goto EXIT;
935     }
936
937     if (pOMXComponent->pComponentPrivate == NULL) {
938         ret = OMX_ErrorBadParameter;
939         goto EXIT;
940     }
941     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
942     pBufferHdr = pDataBuffer->bufferHeader;
943
944     if (pBufferHdr != NULL) {
945         pBufferHdr->nFilledLen = pDataBuffer->remainDataLen;
946         pBufferHdr->nOffset    = 0;
947         pBufferHdr->nFlags     = pDataBuffer->nFlags;
948         pBufferHdr->nTimeStamp = pDataBuffer->timeStamp;
949
950         if (pExynosComponent->propagateMarkType.hMarkTargetComponent != NULL) {
951             pBufferHdr->hMarkTargetComponent    = pExynosComponent->propagateMarkType.hMarkTargetComponent;
952             pBufferHdr->pMarkData               = pExynosComponent->propagateMarkType.pMarkData;
953             pExynosComponent->propagateMarkType.hMarkTargetComponent = NULL;
954             pExynosComponent->propagateMarkType.pMarkData = NULL;
955         }
956
957         if ((pBufferHdr->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) {
958             pBufferHdr->nFilledLen = 0;
959             Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "event OMX_BUFFERFLAG_EOS!!!");
960             pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
961                             pExynosComponent->callbackData,
962                             OMX_EventBufferFlag,
963                             OUTPUT_PORT_INDEX,
964                             pBufferHdr->nFlags, NULL);
965         }
966         Exynos_OMX_OutputBufferReturn(pOMXComponent, pBufferHdr);
967     }
968
969     /* reset dataBuffer */
970     Exynos_ResetDataBuffer(pDataBuffer);
971
972 EXIT:
973     FunctionOut();
974
975     return ret;
976 }
977
978 OMX_ERRORTYPE Exynos_OutputBufferGetQueue(
979     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent)
980 {
981     OMX_ERRORTYPE          ret          = OMX_ErrorUndefined;
982     EXYNOS_OMX_BASEPORT   *pExynosPort  = NULL;
983     EXYNOS_OMX_MESSAGE    *pMessage     = NULL;
984     EXYNOS_OMX_DATABUFFER *pDataBuffer  = NULL;
985
986     FunctionIn();
987
988     if (pExynosComponent == NULL) {
989         ret = OMX_ErrorBadParameter;
990         goto EXIT;
991     }
992     pExynosPort = &(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]);
993
994     if (pExynosPort->bufferProcessType & BUFFER_COPY) {
995         pDataBuffer = &(pExynosPort->way.port2WayDataBuffer.outputDataBuffer);
996     } else if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
997         pDataBuffer = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
998     }
999
1000     if (pExynosComponent->currentState != OMX_StateExecuting) {
1001         ret = OMX_ErrorUndefined;
1002         goto EXIT;
1003     } else if ((pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) &&
1004                (!CHECK_PORT_BEING_FLUSHED(pExynosPort))) {
1005         Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
1006         if (pDataBuffer->dataValid != OMX_TRUE) {
1007             pMessage = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
1008             if (pMessage == NULL) {
1009                 ret = OMX_ErrorUndefined;
1010                 goto EXIT;
1011             }
1012             if (pMessage->messageType == EXYNOS_OMX_CommandFakeBuffer) {
1013                 Exynos_OSAL_Free(pMessage);
1014                 ret = OMX_ErrorCodecFlush;
1015                 goto EXIT;
1016             }
1017
1018             pDataBuffer->bufferHeader  = (OMX_BUFFERHEADERTYPE *)(pMessage->pCmdData);
1019             pDataBuffer->allocSize     = pDataBuffer->bufferHeader->nAllocLen;
1020             pDataBuffer->dataLen       = 0; //dataBuffer->bufferHeader->nFilledLen;
1021             pDataBuffer->remainDataLen = pDataBuffer->dataLen;
1022             pDataBuffer->usedDataLen   = 0; //dataBuffer->bufferHeader->nOffset;
1023             pDataBuffer->dataValid     = OMX_TRUE;
1024             /* pDataBuffer->nFlags             = pDataBuffer->bufferHeader->nFlags; */
1025             /* pDtaBuffer->nTimeStamp         = pDataBuffer->bufferHeader->nTimeStamp; */
1026 /*
1027             if (pExynosPort->bufferProcessType & BUFFER_SHARE)
1028                 pDataBuffer->pPrivate      = pDataBuffer->bufferHeader->pOutputPortPrivate;
1029             else if (pExynosPort->bufferProcessType & BUFFER_COPY) {
1030                 pExynosPort->processData.dataBuffer = pDataBuffer->bufferHeader->pBuffer;
1031                 pExynosPort->processData.allocSize  = pDataBuffer->bufferHeader->nAllocLen;
1032             }
1033 */
1034             Exynos_OSAL_Free(pMessage);
1035         }
1036         ret = OMX_ErrorNone;
1037     }
1038 EXIT:
1039     FunctionOut();
1040
1041     return ret;
1042 }
1043
1044 OMX_BUFFERHEADERTYPE *Exynos_OutputBufferGetQueue_Direct(
1045     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent)
1046 {
1047     OMX_BUFFERHEADERTYPE  *pBufferHdr   = NULL;
1048     EXYNOS_OMX_BASEPORT   *pExynosPort  = NULL;
1049     EXYNOS_OMX_MESSAGE    *pMessage     = NULL;
1050
1051     FunctionIn();
1052
1053     if (pExynosComponent == NULL) {
1054         pBufferHdr = NULL;
1055         goto EXIT;
1056     }
1057     pExynosPort = &(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]);
1058
1059     if (pExynosComponent->currentState != OMX_StateExecuting) {
1060         pBufferHdr = NULL;
1061         goto EXIT;
1062     } else if ((pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) &&
1063                (!CHECK_PORT_BEING_FLUSHED(pExynosPort))) {
1064         Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
1065
1066         pMessage = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
1067         if (pMessage == NULL) {
1068             pBufferHdr = NULL;
1069             goto EXIT;
1070         }
1071         if (pMessage->messageType == EXYNOS_OMX_CommandFakeBuffer) {
1072             Exynos_OSAL_Free(pMessage);
1073             pBufferHdr = NULL;
1074             goto EXIT;
1075         }
1076
1077         pBufferHdr  = (OMX_BUFFERHEADERTYPE *)(pMessage->pCmdData);
1078         Exynos_OSAL_Free(pMessage);
1079     }
1080
1081 EXIT:
1082     FunctionOut();
1083
1084     return pBufferHdr;
1085 }
1086
1087 OMX_ERRORTYPE Exynos_CodecBufferEnqueue(
1088     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent,
1089     OMX_U32                      nPortIndex,
1090     OMX_PTR                      pData)
1091 {
1092     OMX_ERRORTYPE          ret         = OMX_ErrorNone;
1093     EXYNOS_OMX_BASEPORT   *pExynosPort = NULL;
1094
1095     FunctionIn();
1096
1097     if (pExynosComponent == NULL) {
1098         ret = OMX_ErrorBadParameter;
1099         goto EXIT;
1100     }
1101
1102     if ((nPortIndex < 0) ||
1103         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1104         ret = OMX_ErrorBadPortIndex;
1105         goto EXIT;
1106     }
1107     pExynosPort = &(pExynosComponent->pExynosPort[nPortIndex]);
1108
1109     if (pData == NULL) {
1110         ret = OMX_ErrorInsufficientResources;
1111         goto EXIT;
1112     }
1113
1114     ret = Exynos_OSAL_Queue(&pExynosPort->codecBufferQ, (void *)pData);
1115     if (ret != 0) {
1116         ret = OMX_ErrorUndefined;
1117         goto EXIT;
1118     }
1119     Exynos_OSAL_SemaphorePost(pExynosPort->codecSemID);
1120
1121     ret = OMX_ErrorNone;
1122
1123 EXIT:
1124     FunctionOut();
1125
1126     return ret;
1127 }
1128
1129 OMX_ERRORTYPE Exynos_CodecBufferDequeue(
1130     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent,
1131     OMX_U32                      nPortIndex,
1132     OMX_PTR                     *pData)
1133 {
1134     OMX_ERRORTYPE          ret         = OMX_ErrorNone;
1135     EXYNOS_OMX_BASEPORT   *pExynosPort = NULL;
1136     OMX_PTR                pTempData   = NULL;
1137
1138     FunctionIn();
1139
1140     if (pExynosComponent == NULL) {
1141         ret = OMX_ErrorBadParameter;
1142         goto EXIT;
1143     }
1144
1145     if ((nPortIndex < 0) ||
1146         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1147         ret = OMX_ErrorBadPortIndex;
1148         goto EXIT;
1149     }
1150     pExynosPort = &(pExynosComponent->pExynosPort[nPortIndex]);
1151
1152     Exynos_OSAL_SemaphoreWait(pExynosPort->codecSemID);
1153     pTempData = (OMX_PTR)Exynos_OSAL_Dequeue(&pExynosPort->codecBufferQ);
1154     if (pTempData != NULL) {
1155         *pData = (OMX_PTR)pTempData;
1156         ret = OMX_ErrorNone;
1157     } else {
1158         *pData = NULL;
1159         ret = OMX_ErrorUndefined;
1160     }
1161
1162 EXIT:
1163     FunctionOut();
1164
1165     return ret;
1166 }
1167
1168 OMX_ERRORTYPE Exynos_CodecBufferReset(
1169     EXYNOS_OMX_BASECOMPONENT    *pExynosComponent,
1170     OMX_U32                      nPortIndex)
1171 {
1172     OMX_ERRORTYPE          ret          = OMX_ErrorNone;
1173     EXYNOS_OMX_BASEPORT   *pExynosPort  = NULL;
1174
1175     FunctionIn();
1176
1177     if (pExynosComponent == NULL) {
1178         ret = OMX_ErrorBadParameter;
1179         goto EXIT;
1180     }
1181
1182     if ((nPortIndex < 0) ||
1183         (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1184         ret = OMX_ErrorBadPortIndex;
1185         goto EXIT;
1186     }
1187     pExynosPort = &(pExynosComponent->pExynosPort[nPortIndex]);
1188
1189     ret = Exynos_OSAL_ResetQueue(&pExynosPort->codecBufferQ);
1190     if (ret != 0) {
1191         ret = OMX_ErrorUndefined;
1192         goto EXIT;
1193     }
1194
1195     while (1) {
1196         int cnt = 0;
1197         Exynos_OSAL_Get_SemaphoreCount(pExynosPort->codecSemID, &cnt);
1198         if (cnt > 0)
1199             Exynos_OSAL_SemaphoreWait(pExynosPort->codecSemID);
1200         else
1201             break;
1202     }
1203     ret = OMX_ErrorNone;
1204
1205 EXIT:
1206     FunctionOut();
1207
1208     return ret;
1209 }
1210
1211 OMX_ERRORTYPE Exynos_OMX_VideoEncodeGetParameter(
1212     OMX_IN OMX_HANDLETYPE hComponent,
1213     OMX_IN OMX_INDEXTYPE  nParamIndex,
1214     OMX_INOUT OMX_PTR     pComponentParameterStructure)
1215 {
1216     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
1217     OMX_COMPONENTTYPE        *pOMXComponent     = NULL;
1218     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
1219     EXYNOS_OMX_BASEPORT      *pExynosPort       = NULL;
1220
1221     FunctionIn();
1222
1223     if (hComponent == NULL) {
1224         ret = OMX_ErrorBadParameter;
1225         goto EXIT;
1226     }
1227     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1228
1229     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1230     if (ret != OMX_ErrorNone) {
1231         goto EXIT;
1232     }
1233
1234     if (pOMXComponent->pComponentPrivate == NULL) {
1235         ret = OMX_ErrorBadParameter;
1236         goto EXIT;
1237     }
1238     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1239
1240     if (pExynosComponent->currentState == OMX_StateInvalid) {
1241         ret = OMX_ErrorInvalidState;
1242         goto EXIT;
1243     }
1244
1245     if (pComponentParameterStructure == NULL) {
1246         ret = OMX_ErrorBadParameter;
1247         goto EXIT;
1248     }
1249
1250     switch (nParamIndex) {
1251     case OMX_IndexParamVideoInit:
1252     {
1253         OMX_PORT_PARAM_TYPE *pPortParam = (OMX_PORT_PARAM_TYPE *)pComponentParameterStructure;
1254         ret = Exynos_OMX_Check_SizeVersion(pPortParam, sizeof(OMX_PORT_PARAM_TYPE));
1255         if (ret != OMX_ErrorNone) {
1256             goto EXIT;
1257         }
1258
1259         pPortParam->nPorts           = pExynosComponent->portParam.nPorts;
1260         pPortParam->nStartPortNumber = pExynosComponent->portParam.nStartPortNumber;
1261         ret = OMX_ErrorNone;
1262     }
1263         break;
1264     case OMX_IndexParamVideoPortFormat:
1265     {
1266         OMX_VIDEO_PARAM_PORTFORMATTYPE *pPortFormat     = (OMX_VIDEO_PARAM_PORTFORMATTYPE *)pComponentParameterStructure;
1267         OMX_U32                         nPortIndex      = pPortFormat->nPortIndex;
1268         OMX_U32                         nIndex          = pPortFormat->nIndex;
1269         EXYNOS_OMX_BASEPORT            *pExynosPort     = NULL;
1270         OMX_PARAM_PORTDEFINITIONTYPE   *pPortDef        = NULL;
1271         OMX_U32                         nSupportFormat  = 0;
1272
1273         ret = Exynos_OMX_Check_SizeVersion(pPortFormat, sizeof(OMX_VIDEO_PARAM_PORTFORMATTYPE));
1274         if (ret != OMX_ErrorNone) {
1275             goto EXIT;
1276         }
1277
1278         if ((nPortIndex < 0) ||
1279             (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1280             ret = OMX_ErrorBadPortIndex;
1281             goto EXIT;
1282         }
1283
1284         if (nPortIndex == INPUT_PORT_INDEX) {
1285             pExynosPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1286             pPortDef = &pExynosPort->portDefinition;
1287
1288             switch (nIndex) {
1289             case supportFormat_0:
1290                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1291                 pPortFormat->eColorFormat       = OMX_COLOR_FormatYUV420Planar;
1292                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1293                 break;
1294             case supportFormat_1:
1295                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1296                 pPortFormat->eColorFormat       = OMX_COLOR_FormatYUV420SemiPlanar;
1297                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1298                 break;
1299             case supportFormat_2:
1300                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1301                 pPortFormat->eColorFormat       = OMX_SEC_COLOR_FormatNV12Tiled;
1302                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1303                 break;
1304             case supportFormat_3:
1305                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1306                 pPortFormat->eColorFormat       = OMX_SEC_COLOR_FormatNV21Linear;
1307                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1308                 break;
1309             case supportFormat_4:
1310 #ifdef SLP_PLATFORM
1311                 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "can not support this format");
1312 #else
1313                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1314                 pPortFormat->eColorFormat       = OMX_COLOR_FormatAndroidOpaque;
1315                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1316 #endif
1317                 break;
1318             case supportFormat_5:
1319                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1320                 pPortFormat->eColorFormat       = OMX_SEC_COLOR_FormatNV12L_DmaBuf_Fd;
1321                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1322                 break;
1323             case supportFormat_6:
1324                 pPortFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1325                 pPortFormat->eColorFormat       = OMX_SEC_COLOR_FormatNV12T_DmaBuf_Fd;
1326                 pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1327                 break;
1328             default:
1329                 if (nIndex > supportFormat_0) {
1330                     ret = OMX_ErrorNoMore;
1331                     goto EXIT;
1332                 }
1333                 break;
1334             }
1335         } else if (nPortIndex == OUTPUT_PORT_INDEX) {
1336             nSupportFormat = OUTPUT_PORT_SUPPORTFORMAT_NUM_MAX - 1;
1337             if (nIndex > nSupportFormat) {
1338                 ret = OMX_ErrorNoMore;
1339                 goto EXIT;
1340             }
1341
1342             pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1343             pPortDef = &pExynosPort->portDefinition;
1344
1345             pPortFormat->eCompressionFormat = pPortDef->format.video.eCompressionFormat;
1346             pPortFormat->eColorFormat       = pPortDef->format.video.eColorFormat;
1347             pPortFormat->xFramerate         = pPortDef->format.video.xFramerate;
1348         }
1349         ret = OMX_ErrorNone;
1350     }
1351         break;
1352     case OMX_IndexParamVideoBitrate:
1353     {
1354         OMX_VIDEO_PARAM_BITRATETYPE     *pVideoBitrate  = (OMX_VIDEO_PARAM_BITRATETYPE *)pComponentParameterStructure;
1355         OMX_U32                          nPortIndex     = pVideoBitrate->nPortIndex;
1356         EXYNOS_OMX_BASEPORT             *pExynosPort    = NULL;
1357         EXYNOS_OMX_VIDEOENC_COMPONENT   *pVideoEnc      = NULL;
1358         OMX_PARAM_PORTDEFINITIONTYPE    *pPortDef       = NULL;
1359
1360         if (nPortIndex != OUTPUT_PORT_INDEX) {
1361             ret = OMX_ErrorBadPortIndex;
1362             goto EXIT;
1363         } else {
1364             pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
1365             if (pVideoEnc == NULL) {
1366                 ret = OMX_ErrorBadParameter;
1367                 goto EXIT;
1368             }
1369             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1370             pPortDef = &pExynosPort->portDefinition;
1371
1372             pVideoBitrate->eControlRate = pVideoEnc->eControlRate[nPortIndex];
1373             pVideoBitrate->nTargetBitrate = pPortDef->format.video.nBitrate;
1374         }
1375         ret = OMX_ErrorNone;
1376     }
1377         break;
1378     case OMX_IndexParamVideoQuantization:
1379     {
1380         OMX_VIDEO_PARAM_QUANTIZATIONTYPE  *pVideoQuantization = (OMX_VIDEO_PARAM_QUANTIZATIONTYPE *)pComponentParameterStructure;
1381         OMX_U32                            nPortIndex         = pVideoQuantization->nPortIndex;
1382         EXYNOS_OMX_BASEPORT               *pExynosPort        = NULL;
1383         EXYNOS_OMX_VIDEOENC_COMPONENT     *pVideoEnc          = NULL;
1384         OMX_PARAM_PORTDEFINITIONTYPE      *pPortDef           = NULL;
1385
1386         if (nPortIndex != OUTPUT_PORT_INDEX) {
1387             ret = OMX_ErrorBadPortIndex;
1388             goto EXIT;
1389         } else {
1390             pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
1391             if (pVideoEnc == NULL) {
1392                 ret = OMX_ErrorBadParameter;
1393                 goto EXIT;
1394             }
1395             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1396             pPortDef = &pExynosPort->portDefinition;
1397
1398             pVideoQuantization->nQpI = pVideoEnc->quantization.nQpI;
1399             pVideoQuantization->nQpP = pVideoEnc->quantization.nQpP;
1400             pVideoQuantization->nQpB = pVideoEnc->quantization.nQpB;
1401         }
1402         ret = OMX_ErrorNone;
1403     }
1404         break;
1405     case OMX_IndexParamPortDefinition:
1406     {
1407         OMX_PARAM_PORTDEFINITIONTYPE *pPortDef      = (OMX_PARAM_PORTDEFINITIONTYPE *)pComponentParameterStructure;
1408         OMX_U32                       nPortIndex    = pPortDef->nPortIndex;
1409         EXYNOS_OMX_BASEPORT          *pExynosPort   = NULL;
1410
1411         if ((nPortIndex < 0) ||
1412             (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1413             ret = OMX_ErrorBadPortIndex;
1414             goto EXIT;
1415         }
1416
1417         ret = Exynos_OMX_Check_SizeVersion(pPortDef, sizeof(OMX_PARAM_PORTDEFINITIONTYPE));
1418         if (ret != OMX_ErrorNone) {
1419             goto EXIT;
1420         }
1421
1422         pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1423         Exynos_OSAL_Memcpy(pPortDef, &pExynosPort->portDefinition, pPortDef->nSize);
1424
1425 #ifdef USE_STOREMETADATA
1426         if ((nPortIndex == 0) &&
1427             (pExynosPort->bStoreMetaData == OMX_TRUE)) {
1428             pPortDef->nBufferSize = MAX_INPUT_METADATA_BUFFER_SIZE;
1429         }
1430 #endif
1431     }
1432         break;
1433     default:
1434     {
1435         ret = Exynos_OMX_GetParameter(hComponent, nParamIndex, pComponentParameterStructure);
1436     }
1437         break;
1438     }
1439 EXIT:
1440     FunctionOut();
1441
1442     return ret;
1443 }
1444
1445 OMX_ERRORTYPE Exynos_OMX_VideoEncodeSetParameter(
1446     OMX_IN OMX_HANDLETYPE hComponent,
1447     OMX_IN OMX_INDEXTYPE  nParamIndex,
1448     OMX_IN OMX_PTR        pComponentParameterStructure)
1449 {
1450     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
1451     OMX_COMPONENTTYPE        *pOMXComponent     = NULL;
1452     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
1453     EXYNOS_OMX_BASEPORT      *pExynosPort       = NULL;
1454
1455     FunctionIn();
1456
1457     if (hComponent == NULL) {
1458         ret = OMX_ErrorBadParameter;
1459         goto EXIT;
1460     }
1461     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1462
1463     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1464     if (ret != OMX_ErrorNone) {
1465         goto EXIT;
1466     }
1467
1468     if (pOMXComponent->pComponentPrivate == NULL) {
1469         ret = OMX_ErrorBadParameter;
1470         goto EXIT;
1471     }
1472     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1473
1474     if (pExynosComponent->currentState == OMX_StateInvalid) {
1475         ret = OMX_ErrorInvalidState;
1476         goto EXIT;
1477     }
1478
1479     if (pComponentParameterStructure == NULL) {
1480         ret = OMX_ErrorBadParameter;
1481         goto EXIT;
1482     }
1483
1484     switch (nParamIndex) {
1485     case OMX_IndexParamVideoPortFormat:
1486     {
1487         OMX_VIDEO_PARAM_PORTFORMATTYPE *pPortFormat     = (OMX_VIDEO_PARAM_PORTFORMATTYPE *)pComponentParameterStructure;
1488         OMX_U32                         nPortIndex      = pPortFormat->nPortIndex;
1489         OMX_U32                         nIndex          = pPortFormat->nIndex;
1490         OMX_PARAM_PORTDEFINITIONTYPE   *pPortDef        = NULL;
1491         OMX_U32                         nSupportFormat  = 0;
1492
1493         ret = Exynos_OMX_Check_SizeVersion(pPortFormat, sizeof(OMX_VIDEO_PARAM_PORTFORMATTYPE));
1494         if (ret != OMX_ErrorNone) {
1495             goto EXIT;
1496         }
1497
1498         if ((nPortIndex < 0) ||
1499             (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1500             ret = OMX_ErrorBadPortIndex;
1501             goto EXIT;
1502         }
1503         pPortDef = &(pExynosComponent->pExynosPort[nPortIndex].portDefinition);
1504
1505         pPortDef->format.video.eColorFormat       = pPortFormat->eColorFormat;
1506         pPortDef->format.video.eCompressionFormat = pPortFormat->eCompressionFormat;
1507         pPortDef->format.video.xFramerate         = pPortFormat->xFramerate;
1508     }
1509         break;
1510     case OMX_IndexParamVideoBitrate:
1511     {
1512         OMX_VIDEO_PARAM_BITRATETYPE     *pVideoBitrate = (OMX_VIDEO_PARAM_BITRATETYPE *)pComponentParameterStructure;
1513         OMX_U32                          nPortIndex    = pVideoBitrate->nPortIndex;
1514         EXYNOS_OMX_BASEPORT             *pExynosPort   = NULL;
1515         EXYNOS_OMX_VIDEOENC_COMPONENT   *pVideoEnc     = NULL;
1516         OMX_PARAM_PORTDEFINITIONTYPE    *pPortDef      = NULL;
1517
1518         if (nPortIndex != OUTPUT_PORT_INDEX) {
1519             ret = OMX_ErrorBadPortIndex;
1520             goto EXIT;
1521         } else {
1522             pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
1523             if (pVideoEnc == NULL) {
1524                 ret = OMX_ErrorBadParameter;
1525                 goto EXIT;
1526             }
1527             pPortDef = &(pExynosComponent->pExynosPort[nPortIndex].portDefinition);
1528
1529             pVideoEnc->eControlRate[nPortIndex] = pVideoBitrate->eControlRate;
1530             pPortDef->format.video.nBitrate = pVideoBitrate->nTargetBitrate;
1531         }
1532         ret = OMX_ErrorNone;
1533     }
1534         break;
1535     case OMX_IndexParamVideoQuantization:
1536     {
1537         OMX_VIDEO_PARAM_QUANTIZATIONTYPE *pVideoQuantization = (OMX_VIDEO_PARAM_QUANTIZATIONTYPE *)pComponentParameterStructure;
1538         OMX_U32                           nPortIndex         = pVideoQuantization->nPortIndex;
1539         EXYNOS_OMX_BASEPORT              *pExynosPort        = NULL;
1540         EXYNOS_OMX_VIDEOENC_COMPONENT    *pVideoEnc          = NULL;
1541         OMX_PARAM_PORTDEFINITIONTYPE     *pPortDef           = NULL;
1542
1543         if (nPortIndex != OUTPUT_PORT_INDEX) {
1544             ret = OMX_ErrorBadPortIndex;
1545             goto EXIT;
1546         } else {
1547             pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
1548             if (pVideoEnc == NULL) {
1549                 ret = OMX_ErrorBadParameter;
1550                 goto EXIT;
1551             }
1552             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1553             pPortDef = &pExynosPort->portDefinition;
1554
1555             pVideoEnc->quantization.nQpI = pVideoQuantization->nQpI;
1556             pVideoEnc->quantization.nQpP = pVideoQuantization->nQpP;
1557             pVideoEnc->quantization.nQpB = pVideoQuantization->nQpB;
1558         }
1559         ret = OMX_ErrorNone;
1560     }
1561         break;
1562     case OMX_IndexParamPortDefinition:
1563     {
1564         OMX_PARAM_PORTDEFINITIONTYPE *pPortDef      = (OMX_PARAM_PORTDEFINITIONTYPE *)pComponentParameterStructure;
1565         OMX_U32                       nPortIndex    = pPortDef->nPortIndex;
1566         EXYNOS_OMX_BASEPORT          *pExynosPort   = NULL;
1567         OMX_U32 width, height, size;
1568
1569         if ((nPortIndex < 0) ||
1570             (nPortIndex >= pExynosComponent->portParam.nPorts)) {
1571             ret = OMX_ErrorBadPortIndex;
1572             goto EXIT;
1573         }
1574
1575         ret = Exynos_OMX_Check_SizeVersion(pPortDef, sizeof(OMX_PARAM_PORTDEFINITIONTYPE));
1576         if (ret != OMX_ErrorNone) {
1577             goto EXIT;
1578         }
1579
1580         pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1581
1582         if ((pExynosComponent->currentState != OMX_StateLoaded) &&
1583             (pExynosComponent->currentState != OMX_StateWaitForResources)) {
1584             if (pExynosPort->portDefinition.bEnabled == OMX_TRUE) {
1585                 ret = OMX_ErrorIncorrectStateOperation;
1586                 goto EXIT;
1587             }
1588         }
1589
1590         if (pPortDef->nBufferCountActual < pExynosPort->portDefinition.nBufferCountMin) {
1591             ret = OMX_ErrorBadParameter;
1592             goto EXIT;
1593         }
1594
1595         Exynos_OSAL_Memcpy(&pExynosPort->portDefinition, pPortDef, pPortDef->nSize);
1596         if (nPortIndex == INPUT_PORT_INDEX) {
1597             pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1598             Exynos_UpdateFrameSize(pOMXComponent);
1599             Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pExynosOutputPort->portDefinition.nBufferSize: %d",
1600                             pExynosPort->portDefinition.nBufferSize);
1601         }
1602         ret = OMX_ErrorNone;
1603     }
1604         break;
1605 #ifdef USE_STOREMETADATA
1606     case OMX_IndexParamStoreMetaDataBuffer:
1607     {
1608         ret = Exynos_OSAL_SetANBParameter(hComponent, nParamIndex, pComponentParameterStructure);
1609     }
1610         break;
1611 #endif
1612     default:
1613     {
1614         ret = Exynos_OMX_SetParameter(hComponent, nParamIndex, pComponentParameterStructure);
1615     }
1616         break;
1617     }
1618 EXIT:
1619     FunctionOut();
1620
1621     return ret;
1622 }
1623
1624 OMX_ERRORTYPE Exynos_OMX_VideoEncodeGetConfig(
1625     OMX_HANDLETYPE  hComponent,
1626     OMX_INDEXTYPE   nParamIndex,
1627     OMX_PTR         pComponentConfigStructure)
1628 {
1629     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
1630     OMX_COMPONENTTYPE        *pOMXComponent     = NULL;
1631     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
1632
1633     FunctionIn();
1634
1635     if ((hComponent == NULL) ||
1636         (pComponentConfigStructure == NULL)) {
1637         ret = OMX_ErrorBadParameter;
1638         goto EXIT;
1639     }
1640     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1641
1642     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1643     if (ret != OMX_ErrorNone) {
1644         goto EXIT;
1645     }
1646
1647     if (pOMXComponent->pComponentPrivate == NULL) {
1648         ret = OMX_ErrorBadParameter;
1649         goto EXIT;
1650     }
1651     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1652
1653     if (pExynosComponent->currentState == OMX_StateInvalid) {
1654         ret = OMX_ErrorInvalidState;
1655         goto EXIT;
1656     }
1657
1658     switch (nParamIndex) {
1659     case OMX_IndexConfigVideoBitrate:
1660     {
1661         OMX_VIDEO_CONFIG_BITRATETYPE *pConfigBitrate = (OMX_VIDEO_CONFIG_BITRATETYPE *)pComponentConfigStructure;
1662         OMX_U32                       nPortIndex     = pConfigBitrate->nPortIndex;
1663         EXYNOS_OMX_BASEPORT          *pExynosPort    = NULL;
1664
1665         if (nPortIndex != OUTPUT_PORT_INDEX) {
1666             ret = OMX_ErrorBadPortIndex;
1667             goto EXIT;
1668         } else {
1669             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1670             pConfigBitrate->nEncodeBitrate = pExynosPort->portDefinition.format.video.nBitrate;
1671         }
1672     }
1673         break;
1674     case OMX_IndexConfigVideoFramerate:
1675     {
1676         OMX_CONFIG_FRAMERATETYPE *pConfigFramerate = (OMX_CONFIG_FRAMERATETYPE *)pComponentConfigStructure;
1677         OMX_U32                   nPortIndex       = pConfigFramerate->nPortIndex;
1678         EXYNOS_OMX_BASEPORT      *pExynosPort      = NULL;
1679
1680         if (nPortIndex != OUTPUT_PORT_INDEX) {
1681             ret = OMX_ErrorBadPortIndex;
1682             goto EXIT;
1683         } else {
1684             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1685             pConfigFramerate->xEncodeFramerate = pExynosPort->portDefinition.format.video.xFramerate;
1686         }
1687     }
1688         break;
1689     default:
1690     {
1691         ret = Exynos_OMX_GetConfig(hComponent, nParamIndex, pComponentConfigStructure);
1692     }
1693         break;
1694     }
1695 EXIT:
1696     FunctionOut();
1697
1698     return ret;
1699 }
1700
1701 OMX_ERRORTYPE Exynos_OMX_VideoEncodeSetConfig(
1702     OMX_HANDLETYPE  hComponent,
1703     OMX_INDEXTYPE   nParamIndex,
1704     OMX_PTR         pComponentConfigStructure)
1705     {
1706     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
1707     OMX_COMPONENTTYPE        *pOMXComponent     = NULL;
1708     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
1709
1710     FunctionIn();
1711
1712     if ((hComponent == NULL) ||
1713         (pComponentConfigStructure == NULL)) {
1714         ret = OMX_ErrorBadParameter;
1715         goto EXIT;
1716     }
1717     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1718
1719     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1720     if (ret != OMX_ErrorNone) {
1721         goto EXIT;
1722     }
1723
1724     if (pOMXComponent->pComponentPrivate == NULL) {
1725         ret = OMX_ErrorBadParameter;
1726         goto EXIT;
1727     }
1728     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1729
1730     if (pExynosComponent->currentState == OMX_StateInvalid) {
1731         ret = OMX_ErrorInvalidState;
1732         goto EXIT;
1733     }
1734
1735     switch (nParamIndex) {
1736     case OMX_IndexConfigVideoBitrate:
1737     {
1738         OMX_VIDEO_CONFIG_BITRATETYPE *pConfigBitrate = (OMX_VIDEO_CONFIG_BITRATETYPE *)pComponentConfigStructure;
1739         OMX_U32                       nPortIndex     = pConfigBitrate->nPortIndex;
1740         EXYNOS_OMX_BASEPORT          *pExynosPort    = NULL;
1741
1742         if (nPortIndex != OUTPUT_PORT_INDEX) {
1743             ret = OMX_ErrorBadPortIndex;
1744             goto EXIT;
1745         } else {
1746             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1747             pExynosPort->portDefinition.format.video.nBitrate = pConfigBitrate->nEncodeBitrate;
1748         }
1749     }
1750         break;
1751     case OMX_IndexConfigVideoFramerate:
1752     {
1753         OMX_CONFIG_FRAMERATETYPE *pConfigFramerate = (OMX_CONFIG_FRAMERATETYPE *)pComponentConfigStructure;
1754         OMX_U32                   nPortIndex       = pConfigFramerate->nPortIndex;
1755         EXYNOS_OMX_BASEPORT      *pExynosPort      = NULL;
1756
1757         if (nPortIndex != OUTPUT_PORT_INDEX) {
1758             ret = OMX_ErrorBadPortIndex;
1759             goto EXIT;
1760         } else {
1761             pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1762             pExynosPort->portDefinition.format.video.xFramerate = pConfigFramerate->xEncodeFramerate;
1763         }
1764     }
1765         break;
1766     case OMX_IndexConfigVideoIntraVOPRefresh:
1767     {
1768         OMX_CONFIG_INTRAREFRESHVOPTYPE *pIntraRefreshVOP = (OMX_CONFIG_INTRAREFRESHVOPTYPE *)pComponentConfigStructure;
1769         EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc         = NULL;
1770         OMX_U32                        nPortIndex        = pIntraRefreshVOP->nPortIndex;
1771
1772         if (pExynosComponent->hComponentHandle == NULL) {
1773             ret = OMX_ErrorBadParameter;
1774             goto EXIT;
1775         }
1776         pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle;
1777
1778         if (nPortIndex != OUTPUT_PORT_INDEX) {
1779             ret = OMX_ErrorBadPortIndex;
1780             goto EXIT;
1781         } else {
1782             pVideoEnc->IntraRefreshVOP = pIntraRefreshVOP->IntraRefreshVOP;
1783         }
1784     }
1785         break;
1786     default:
1787     {
1788         ret = Exynos_OMX_SetConfig(hComponent, nParamIndex, pComponentConfigStructure);
1789     }
1790         break;
1791     }
1792 EXIT:
1793     FunctionOut();
1794
1795     return ret;
1796 }
1797
1798 OMX_ERRORTYPE Exynos_OMX_VideoEncodeGetExtensionIndex(
1799     OMX_IN OMX_HANDLETYPE  hComponent,
1800     OMX_IN OMX_STRING      szParamName,
1801     OMX_OUT OMX_INDEXTYPE *pIndexType)
1802 {
1803     OMX_ERRORTYPE             ret               = OMX_ErrorNone;
1804     OMX_COMPONENTTYPE        *pOMXComponent     = NULL;
1805     EXYNOS_OMX_BASECOMPONENT *pExynosComponent  = NULL;
1806
1807     FunctionIn();
1808
1809     if (hComponent == NULL) {
1810         ret = OMX_ErrorBadParameter;
1811         goto EXIT;
1812     }
1813     pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1814
1815     ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1816     if (ret != OMX_ErrorNone) {
1817         goto EXIT;
1818     }
1819
1820     if (pOMXComponent->pComponentPrivate == NULL) {
1821         ret = OMX_ErrorBadParameter;
1822         goto EXIT;
1823     }
1824     pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1825
1826     if ((szParamName == NULL) || (pIndexType == NULL)) {
1827         ret = OMX_ErrorBadParameter;
1828         goto EXIT;
1829     }
1830
1831     if (pExynosComponent->currentState == OMX_StateInvalid) {
1832         ret = OMX_ErrorInvalidState;
1833         goto EXIT;
1834     }
1835
1836 #ifdef USE_STOREMETADATA
1837     if (Exynos_OSAL_Strcmp(szParamName, EXYNOS_INDEX_PARAM_STORE_METADATA_BUFFER) == 0) {
1838         *pIndexType = (OMX_INDEXTYPE)OMX_IndexParamStoreMetaDataBuffer;
1839     } else {
1840         ret = Exynos_OMX_GetExtensionIndex(hComponent, szParamName, pIndexType);
1841     }
1842 #else
1843     ret = Exynos_OMX_GetExtensionIndex(hComponent, szParamName, pIndexType);
1844 #endif
1845 EXIT:
1846     FunctionOut();
1847
1848     return ret;
1849 }