c29666ffa197ba2e9bb08a39fec71f19c89791cd
[GitHub/LineageOS/android_hardware_samsung_slsi_openmax.git] / component / video / dec / Exynos_OMX_VdecControl.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_VdecControl.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_Vdec.h"
33 #include "Exynos_OMX_VdecControl.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_ANB
42 #include "Exynos_OSAL_Android.h"
43 #endif
44
45 #include "ExynosVideoApi.h"
46
47 #undef EXYNOS_LOG_TAG
48 #define EXYNOS_LOG_TAG "EXYNOS_VIDEO_DECCONTROL"
49 #define EXYNOS_LOG_OFF
50 //#define EXYNOS_TRACE_ON
51 #include "Exynos_OSAL_Log.h"
52
53
54 OMX_ERRORTYPE Exynos_OMX_UseBuffer(
55 OMX_IN OMX_HANDLETYPE hComponent,
56 OMX_INOUT OMX_BUFFERHEADERTYPE **ppBufferHdr,
57 OMX_IN OMX_U32 nPortIndex,
58 OMX_IN OMX_PTR pAppPrivate,
59 OMX_IN OMX_U32 nSizeBytes,
60 OMX_IN OMX_U8 *pBuffer)
61 {
62 OMX_ERRORTYPE ret = OMX_ErrorNone;
63 OMX_COMPONENTTYPE *pOMXComponent = NULL;
64 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
65 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
66 OMX_BUFFERHEADERTYPE *temp_bufferHeader = NULL;
67 OMX_U32 i = 0;
68
69 FunctionIn();
70
71 if (hComponent == NULL) {
72 ret = OMX_ErrorBadParameter;
73 goto EXIT;
74 }
75 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
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 pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
88 if (nPortIndex >= pExynosComponent->portParam.nPorts) {
89 ret = OMX_ErrorBadPortIndex;
90 goto EXIT;
91 }
92 if (pExynosPort->portState != OMX_StateIdle) {
93 ret = OMX_ErrorIncorrectStateOperation;
94 goto EXIT;
95 }
96
97 if (CHECK_PORT_TUNNELED(pExynosPort) && CHECK_PORT_BUFFER_SUPPLIER(pExynosPort)) {
98 ret = OMX_ErrorBadPortIndex;
99 goto EXIT;
100 }
101
102 temp_bufferHeader = (OMX_BUFFERHEADERTYPE *)Exynos_OSAL_Malloc(sizeof(OMX_BUFFERHEADERTYPE));
103 if (temp_bufferHeader == NULL) {
104 ret = OMX_ErrorInsufficientResources;
105 goto EXIT;
106 }
107 Exynos_OSAL_Memset(temp_bufferHeader, 0, sizeof(OMX_BUFFERHEADERTYPE));
108
109 for (i = 0; i < pExynosPort->portDefinition.nBufferCountActual; i++) {
110 if (pExynosPort->bufferStateAllocate[i] == BUFFER_STATE_FREE) {
111 pExynosPort->extendBufferHeader[i].OMXBufferHeader = temp_bufferHeader;
112 pExynosPort->bufferStateAllocate[i] = (BUFFER_STATE_ASSIGNED | HEADER_STATE_ALLOCATED);
113 INIT_SET_SIZE_VERSION(temp_bufferHeader, OMX_BUFFERHEADERTYPE);
114 temp_bufferHeader->pBuffer = pBuffer;
115 temp_bufferHeader->nAllocLen = nSizeBytes;
116 temp_bufferHeader->pAppPrivate = pAppPrivate;
117 if (nPortIndex == INPUT_PORT_INDEX)
118 temp_bufferHeader->nInputPortIndex = INPUT_PORT_INDEX;
119 else
120 temp_bufferHeader->nOutputPortIndex = OUTPUT_PORT_INDEX;
121
122 pExynosPort->assignedBufferNum++;
123 if (pExynosPort->assignedBufferNum == pExynosPort->portDefinition.nBufferCountActual) {
124 pExynosPort->portDefinition.bPopulated = OMX_TRUE;
125 /* Exynos_OSAL_MutexLock(pExynosComponent->compMutex); */
126 Exynos_OSAL_SemaphorePost(pExynosPort->loadedResource);
127 /* Exynos_OSAL_MutexUnlock(pExynosComponent->compMutex); */
128 }
129 *ppBufferHdr = temp_bufferHeader;
130 ret = OMX_ErrorNone;
131 goto EXIT;
132 }
133 }
134
135 Exynos_OSAL_Free(temp_bufferHeader);
136 ret = OMX_ErrorInsufficientResources;
137
138 EXIT:
139 FunctionOut();
140
141 return ret;
142 }
143
144 OMX_ERRORTYPE Exynos_OMX_AllocateBuffer(
145 OMX_IN OMX_HANDLETYPE hComponent,
146 OMX_INOUT OMX_BUFFERHEADERTYPE **ppBuffer,
147 OMX_IN OMX_U32 nPortIndex,
148 OMX_IN OMX_PTR pAppPrivate,
149 OMX_IN OMX_U32 nSizeBytes)
150 {
151 OMX_ERRORTYPE ret = OMX_ErrorNone;
152 OMX_COMPONENTTYPE *pOMXComponent = NULL;
153 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
154 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
155 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
156 OMX_BUFFERHEADERTYPE *temp_bufferHeader = NULL;
157 OMX_U8 *temp_buffer = NULL;
158 int temp_buffer_fd = -1;
159 OMX_U32 i = 0;
160 MEMORY_TYPE mem_type = SYSTEM_MEMORY;
161
162 FunctionIn();
163
164 if (hComponent == NULL) {
165 ret = OMX_ErrorBadParameter;
166 goto EXIT;
167 }
168 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
169 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
170 if (ret != OMX_ErrorNone) {
171 goto EXIT;
172 }
173
174 if (pOMXComponent->pComponentPrivate == NULL) {
175 ret = OMX_ErrorBadParameter;
176 goto EXIT;
177 }
178 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
179 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
180
181 pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
182 if (nPortIndex >= pExynosComponent->portParam.nPorts) {
183 ret = OMX_ErrorBadPortIndex;
184 goto EXIT;
185 }
186 /*
187 if (pExynosPort->portState != OMX_StateIdle ) {
188 ret = OMX_ErrorIncorrectStateOperation;
189 goto EXIT;
190 }
191 */
192 if (CHECK_PORT_TUNNELED(pExynosPort) && CHECK_PORT_BUFFER_SUPPLIER(pExynosPort)) {
193 ret = OMX_ErrorBadPortIndex;
194 goto EXIT;
195 }
196
197 if ((pVideoDec->bDRMPlayerMode == OMX_TRUE) &&
198 (nPortIndex == INPUT_PORT_INDEX)) {
199 mem_type = SECURE_MEMORY;
200 } else if (pExynosPort->bNeedContigMem == OMX_TRUE) {
201 mem_type = CONTIG_MEMORY;
202 } else if ((nPortIndex == OUTPUT_PORT_INDEX) &&
203 (pExynosPort->bufferProcessType & BUFFER_SHARE)) {
204 mem_type = NORMAL_MEMORY;
205 }
206
207 temp_buffer = Exynos_OSAL_SharedMemory_Alloc(pVideoDec->hSharedMemory, nSizeBytes, mem_type);
208 if (temp_buffer == NULL) {
209 ret = OMX_ErrorInsufficientResources;
210 goto EXIT;
211 }
212 temp_buffer_fd = Exynos_OSAL_SharedMemory_VirtToION(pVideoDec->hSharedMemory, temp_buffer);
213
214 temp_bufferHeader = (OMX_BUFFERHEADERTYPE *)Exynos_OSAL_Malloc(sizeof(OMX_BUFFERHEADERTYPE));
215 if (temp_bufferHeader == NULL) {
216 Exynos_OSAL_SharedMemory_Free(pVideoDec->hSharedMemory, temp_buffer);
217 ret = OMX_ErrorInsufficientResources;
218 goto EXIT;
219 }
220 Exynos_OSAL_Memset(temp_bufferHeader, 0, sizeof(OMX_BUFFERHEADERTYPE));
221
222 for (i = 0; i < pExynosPort->portDefinition.nBufferCountActual; i++) {
223 if (pExynosPort->bufferStateAllocate[i] == BUFFER_STATE_FREE) {
224 pExynosPort->extendBufferHeader[i].OMXBufferHeader = temp_bufferHeader;
225 pExynosPort->extendBufferHeader[i].buf_fd[0] = temp_buffer_fd;
226 pExynosPort->bufferStateAllocate[i] = (BUFFER_STATE_ALLOCATED | HEADER_STATE_ALLOCATED);
227 INIT_SET_SIZE_VERSION(temp_bufferHeader, OMX_BUFFERHEADERTYPE);
228 if (mem_type == SECURE_MEMORY)
229 temp_bufferHeader->pBuffer = temp_buffer_fd;
230 else
231 temp_bufferHeader->pBuffer = temp_buffer;
232 temp_bufferHeader->nAllocLen = nSizeBytes;
233 temp_bufferHeader->pAppPrivate = pAppPrivate;
234 if (nPortIndex == INPUT_PORT_INDEX)
235 temp_bufferHeader->nInputPortIndex = INPUT_PORT_INDEX;
236 else
237 temp_bufferHeader->nOutputPortIndex = OUTPUT_PORT_INDEX;
238 pExynosPort->assignedBufferNum++;
239 if (pExynosPort->assignedBufferNum == pExynosPort->portDefinition.nBufferCountActual) {
240 pExynosPort->portDefinition.bPopulated = OMX_TRUE;
241 /* Exynos_OSAL_MutexLock(pExynosComponent->compMutex); */
242 Exynos_OSAL_SemaphorePost(pExynosPort->loadedResource);
243 /* Exynos_OSAL_MutexUnlock(pExynosComponent->compMutex); */
244 }
245 *ppBuffer = temp_bufferHeader;
246 ret = OMX_ErrorNone;
247 goto EXIT;
248 }
249 }
250
251 Exynos_OSAL_Free(temp_bufferHeader);
252 Exynos_OSAL_SharedMemory_Free(pVideoDec->hSharedMemory, temp_buffer);
253
254 ret = OMX_ErrorInsufficientResources;
255
256 EXIT:
257 FunctionOut();
258
259 return ret;
260 }
261
262 OMX_ERRORTYPE Exynos_OMX_FreeBuffer(
263 OMX_IN OMX_HANDLETYPE hComponent,
264 OMX_IN OMX_U32 nPortIndex,
265 OMX_IN OMX_BUFFERHEADERTYPE *pBufferHdr)
266 {
267 OMX_ERRORTYPE ret = OMX_ErrorNone;
268 OMX_COMPONENTTYPE *pOMXComponent = NULL;
269 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
270 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
271 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
272 OMX_BUFFERHEADERTYPE *temp_bufferHeader = NULL;
273 OMX_U8 *temp_buffer = NULL;
274 OMX_U32 i = 0;
275
276 FunctionIn();
277
278 if (hComponent == NULL) {
279 ret = OMX_ErrorBadParameter;
280 goto EXIT;
281 }
282 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
283 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
284 if (ret != OMX_ErrorNone) {
285 goto EXIT;
286 }
287
288 if (pOMXComponent->pComponentPrivate == NULL) {
289 ret = OMX_ErrorBadParameter;
290 goto EXIT;
291 }
292 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
293 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
294 pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
295
296 if (CHECK_PORT_TUNNELED(pExynosPort) && CHECK_PORT_BUFFER_SUPPLIER(pExynosPort)) {
297 ret = OMX_ErrorBadPortIndex;
298 goto EXIT;
299 }
300
301 if (((pExynosPort->portState != OMX_StateLoaded) &&
302 (pExynosPort->portState != OMX_StateInvalid)) &&
303 (pExynosPort->portDefinition.bEnabled != OMX_FALSE)) {
304 (*(pExynosComponent->pCallbacks->EventHandler)) (pOMXComponent,
305 pExynosComponent->callbackData,
306 (OMX_U32)OMX_EventError,
307 (OMX_U32)OMX_ErrorPortUnpopulated,
308 nPortIndex, NULL);
309 ret = OMX_ErrorInvalidState;
310 goto EXIT;
311 }
312
313 for (i = 0; i < /*pExynosPort->portDefinition.nBufferCountActual*/MAX_BUFFER_NUM; i++) {
314 if (((pExynosPort->bufferStateAllocate[i] | BUFFER_STATE_FREE) != 0) && (pExynosPort->extendBufferHeader[i].OMXBufferHeader != NULL)) {
315 if (pExynosPort->extendBufferHeader[i].OMXBufferHeader->pBuffer == pBufferHdr->pBuffer) {
316 if (pExynosPort->bufferStateAllocate[i] & BUFFER_STATE_ALLOCATED) {
317 if ((pVideoDec->bDRMPlayerMode == OMX_TRUE) && (nPortIndex == INPUT_PORT_INDEX)) {
318 OMX_PTR mapBuffer = Exynos_OSAL_SharedMemory_IONToVirt(pVideoDec->hSharedMemory, (int)pExynosPort->extendBufferHeader[i].OMXBufferHeader->pBuffer);
319 Exynos_OSAL_SharedMemory_Free(pVideoDec->hSharedMemory, mapBuffer);
320 } else {
321 Exynos_OSAL_SharedMemory_Free(pVideoDec->hSharedMemory, pExynosPort->extendBufferHeader[i].OMXBufferHeader->pBuffer);
322 }
323 pExynosPort->extendBufferHeader[i].OMXBufferHeader->pBuffer = NULL;
324 pBufferHdr->pBuffer = NULL;
325 } else if (pExynosPort->bufferStateAllocate[i] & BUFFER_STATE_ASSIGNED) {
326 ; /* None*/
327 }
328 pExynosPort->assignedBufferNum--;
329 if (pExynosPort->bufferStateAllocate[i] & HEADER_STATE_ALLOCATED) {
330 Exynos_OSAL_Free(pExynosPort->extendBufferHeader[i].OMXBufferHeader);
331 pExynosPort->extendBufferHeader[i].OMXBufferHeader = NULL;
332 pBufferHdr = NULL;
333 }
334 pExynosPort->bufferStateAllocate[i] = BUFFER_STATE_FREE;
335 ret = OMX_ErrorNone;
336 goto EXIT;
337 }
338 }
339 }
340
341 EXIT:
342 if (ret == OMX_ErrorNone) {
343 if (pExynosPort->assignedBufferNum == 0) {
344 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pExynosPort->unloadedResource signal set");
345 /* Exynos_OSAL_MutexLock(pExynosComponent->compMutex); */
346 Exynos_OSAL_SemaphorePost(pExynosPort->unloadedResource);
347 /* Exynos_OSAL_MutexUnlock(pExynosComponent->compMutex); */
348 pExynosPort->portDefinition.bPopulated = OMX_FALSE;
349 }
350 }
351
352 FunctionOut();
353
354 return ret;
355 }
356
357 OMX_ERRORTYPE Exynos_OMX_AllocateTunnelBuffer(EXYNOS_OMX_BASEPORT *pOMXBasePort, OMX_U32 nPortIndex)
358 {
359 OMX_ERRORTYPE ret = OMX_ErrorNone;
360 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
361 OMX_BUFFERHEADERTYPE *temp_bufferHeader = NULL;
362 OMX_U8 *temp_buffer = NULL;
363 OMX_U32 bufferSize = 0;
364 OMX_PARAM_PORTDEFINITIONTYPE portDefinition;
365
366 ret = OMX_ErrorTunnelingUnsupported;
367 EXIT:
368 return ret;
369 }
370
371 OMX_ERRORTYPE Exynos_OMX_FreeTunnelBuffer(EXYNOS_OMX_BASEPORT *pOMXBasePort, OMX_U32 nPortIndex)
372 {
373 OMX_ERRORTYPE ret = OMX_ErrorNone;
374 EXYNOS_OMX_BASEPORT* pExynosPort = NULL;
375 OMX_BUFFERHEADERTYPE* temp_bufferHeader = NULL;
376 OMX_U8 *temp_buffer = NULL;
377 OMX_U32 bufferSize = 0;
378
379 ret = OMX_ErrorTunnelingUnsupported;
380 EXIT:
381 return ret;
382 }
383
384 OMX_ERRORTYPE Exynos_OMX_ComponentTunnelRequest(
385 OMX_IN OMX_HANDLETYPE hComp,
386 OMX_IN OMX_U32 nPort,
387 OMX_IN OMX_HANDLETYPE hTunneledComp,
388 OMX_IN OMX_U32 nTunneledPort,
389 OMX_INOUT OMX_TUNNELSETUPTYPE *pTunnelSetup)
390 {
391 OMX_ERRORTYPE ret = OMX_ErrorNone;
392
393 ret = OMX_ErrorTunnelingUnsupported;
394 EXIT:
395 return ret;
396 }
397
398 OMX_ERRORTYPE Exynos_OMX_GetFlushBuffer(EXYNOS_OMX_BASEPORT *pExynosPort, EXYNOS_OMX_DATABUFFER *pDataBuffer[])
399 {
400 OMX_ERRORTYPE ret = OMX_ErrorNone;
401
402 FunctionIn();
403
404 *pDataBuffer = NULL;
405
406 if (pExynosPort->portWayType == WAY1_PORT) {
407 *pDataBuffer = &pExynosPort->way.port1WayDataBuffer.dataBuffer;
408 } else if (pExynosPort->portWayType == WAY2_PORT) {
409 pDataBuffer[0] = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
410 pDataBuffer[1] = &(pExynosPort->way.port2WayDataBuffer.outputDataBuffer);
411 }
412
413 EXIT:
414 FunctionOut();
415
416 return ret;
417 }
418
419 OMX_ERRORTYPE Exynos_OMX_FlushPort(OMX_COMPONENTTYPE *pOMXComponent, OMX_S32 portIndex)
420 {
421 OMX_ERRORTYPE ret = OMX_ErrorNone;
422 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
423 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
424 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
425 OMX_BUFFERHEADERTYPE *bufferHeader = NULL;
426 EXYNOS_OMX_DATABUFFER *pDataPortBuffer[2] = {NULL, NULL};
427 EXYNOS_OMX_MESSAGE *message = NULL;
428 OMX_U32 flushNum = 0;
429 OMX_S32 semValue = 0;
430 int i = 0, maxBufferNum = 0;
431 FunctionIn();
432
433 pExynosPort = &pExynosComponent->pExynosPort[portIndex];
434
435 while (Exynos_OSAL_GetElemNum(&pExynosPort->bufferQ) > 0) {
436 Exynos_OSAL_Get_SemaphoreCount(pExynosComponent->pExynosPort[portIndex].bufferSemID, &semValue);
437 if (semValue == 0)
438 Exynos_OSAL_SemaphorePost(pExynosComponent->pExynosPort[portIndex].bufferSemID);
439
440 Exynos_OSAL_SemaphoreWait(pExynosComponent->pExynosPort[portIndex].bufferSemID);
441 message = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
442 if ((message != NULL) && (message->messageType != EXYNOS_OMX_CommandFakeBuffer)) {
443 bufferHeader = (OMX_BUFFERHEADERTYPE *)message->pCmdData;
444 bufferHeader->nFilledLen = 0;
445
446 if (portIndex == OUTPUT_PORT_INDEX) {
447 Exynos_OMX_OutputBufferReturn(pOMXComponent, bufferHeader);
448 } else if (portIndex == INPUT_PORT_INDEX) {
449 Exynos_OMX_InputBufferReturn(pOMXComponent, bufferHeader);
450 }
451 }
452 Exynos_OSAL_Free(message);
453 message = NULL;
454 }
455
456 Exynos_OMX_GetFlushBuffer(pExynosPort, pDataPortBuffer);
457 if (portIndex == INPUT_PORT_INDEX) {
458 if (pDataPortBuffer[0]->dataValid == OMX_TRUE)
459 Exynos_InputBufferReturn(pOMXComponent, pDataPortBuffer[0]);
460 if (pDataPortBuffer[1]->dataValid == OMX_TRUE)
461 Exynos_InputBufferReturn(pOMXComponent, pDataPortBuffer[1]);
462 } else if (portIndex == OUTPUT_PORT_INDEX) {
463 if (pDataPortBuffer[0]->dataValid == OMX_TRUE)
464 Exynos_OutputBufferReturn(pOMXComponent, pDataPortBuffer[0]);
465 if (pDataPortBuffer[1]->dataValid == OMX_TRUE)
466 Exynos_OutputBufferReturn(pOMXComponent, pDataPortBuffer[1]);
467 }
468
469 if (pExynosComponent->bMultiThreadProcess == OMX_TRUE) {
470 if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
471 if (pExynosPort->processData.bufferHeader != NULL) {
472 if (portIndex == INPUT_PORT_INDEX) {
473 Exynos_OMX_InputBufferReturn(pOMXComponent, pExynosPort->processData.bufferHeader);
474 } else if (portIndex == OUTPUT_PORT_INDEX) {
475 #ifdef USE_ANB
476 if (pExynosPort->bIsANBEnabled == OMX_TRUE)
477 Exynos_OSAL_UnlockANB(pExynosPort->processData.bufferHeader->pBuffer);
478 #endif
479 Exynos_OMX_OutputBufferReturn(pOMXComponent, pExynosPort->processData.bufferHeader);
480 }
481 }
482 Exynos_ResetCodecData(&pExynosPort->processData);
483
484 maxBufferNum = pExynosPort->portDefinition.nBufferCountActual;
485 for (i = 0; i < maxBufferNum; i++) {
486 if (pExynosPort->extendBufferHeader[i].bBufferInOMX == OMX_TRUE) {
487 if (portIndex == OUTPUT_PORT_INDEX) {
488 #ifdef USE_ANB
489 if (pExynosPort->bIsANBEnabled == OMX_TRUE)
490 Exynos_OSAL_UnlockANB(pExynosPort->extendBufferHeader[i].OMXBufferHeader->pBuffer);
491 #endif
492 Exynos_OMX_OutputBufferReturn(pOMXComponent, pExynosPort->extendBufferHeader[i].OMXBufferHeader);
493 } else if (portIndex == INPUT_PORT_INDEX) {
494 Exynos_OMX_InputBufferReturn(pOMXComponent, pExynosPort->extendBufferHeader[i].OMXBufferHeader);
495 }
496 }
497 }
498 }
499 } else {
500 Exynos_ResetCodecData(&pExynosPort->processData);
501 }
502
503 if (pExynosPort->bufferSemID != NULL) {
504 while (1) {
505 OMX_S32 cnt = 0;
506 Exynos_OSAL_Get_SemaphoreCount(pExynosPort->bufferSemID, &cnt);
507 if (cnt == 0)
508 break;
509 else if (cnt > 0)
510 Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
511 else if (cnt < 0)
512 Exynos_OSAL_SemaphorePost(pExynosPort->bufferSemID);
513 Exynos_OSAL_SleepMillisec(0);
514 }
515 }
516 Exynos_OSAL_ResetQueue(&pExynosPort->bufferQ);
517
518 EXIT:
519 FunctionOut();
520
521 return ret;
522 }
523
524 OMX_ERRORTYPE Exynos_OMX_BufferFlush(OMX_COMPONENTTYPE *pOMXComponent, OMX_S32 nPortIndex, OMX_BOOL bEvent)
525 {
526 OMX_ERRORTYPE ret = OMX_ErrorNone;
527 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
528 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
529 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
530 EXYNOS_OMX_DATABUFFER *flushPortBuffer[2] = {NULL, NULL};
531 OMX_U32 i = 0, cnt = 0;
532
533 FunctionIn();
534
535 if (pOMXComponent == NULL) {
536 ret = OMX_ErrorBadParameter;
537 goto EXIT;
538 }
539 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
540 if (ret != OMX_ErrorNone) {
541 goto EXIT;
542 }
543
544 if (pOMXComponent->pComponentPrivate == NULL) {
545 ret = OMX_ErrorBadParameter;
546 goto EXIT;
547 }
548 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
549 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
550
551 Exynos_OSAL_Log(EXYNOS_LOG_TRACE,"OMX_CommandFlush start, port:%d", nPortIndex);
552
553 pExynosComponent->pExynosPort[nPortIndex].bIsPortFlushed = OMX_TRUE;
554
555 if (pExynosComponent->bMultiThreadProcess == OMX_FALSE) {
556 Exynos_OSAL_SignalSet(pExynosComponent->pauseEvent);
557 } else {
558 Exynos_OSAL_SignalSet(pExynosComponent->pExynosPort[nPortIndex].pauseEvent);
559 }
560
561 pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
562 Exynos_OMX_GetFlushBuffer(pExynosPort, flushPortBuffer);
563
564 if (pExynosComponent->pExynosPort[nPortIndex].bufferProcessType & BUFFER_COPY)
565 Exynos_OSAL_SemaphorePost(pExynosPort->codecSemID);
566
567 if (pExynosPort->bufferSemID != NULL) {
568 while (1) {
569 OMX_S32 cnt = 0;
570 Exynos_OSAL_Get_SemaphoreCount(pExynosPort->bufferSemID, &cnt);
571 if (cnt > 0)
572 break;
573 else
574 Exynos_OSAL_SemaphorePost(pExynosPort->bufferSemID);
575 Exynos_OSAL_SleepMillisec(0);
576 }
577 }
578
579 pVideoDec->exynos_codec_bufferProcessRun(pOMXComponent, nPortIndex);
580 Exynos_OSAL_MutexLock(flushPortBuffer[0]->bufferMutex);
581 pVideoDec->exynos_codec_stop(pOMXComponent, nPortIndex);
582 Exynos_OSAL_MutexLock(flushPortBuffer[1]->bufferMutex);
583 ret = Exynos_OMX_FlushPort(pOMXComponent, nPortIndex);
584 if (pVideoDec->bReconfigDPB == OMX_TRUE)
585 pVideoDec->exynos_codec_reconfigAllBuffers(pOMXComponent, nPortIndex);
586 else if (pExynosComponent->pExynosPort[nPortIndex].bufferProcessType & BUFFER_COPY)
587 pVideoDec->exynos_codec_enqueueAllBuffer(pOMXComponent, nPortIndex);
588 Exynos_ResetCodecData(&pExynosPort->processData);
589
590 if (ret == OMX_ErrorNone) {
591 if (nPortIndex == INPUT_PORT_INDEX) {
592 pExynosComponent->checkTimeStamp.needSetStartTimeStamp = OMX_TRUE;
593 pExynosComponent->checkTimeStamp.needCheckStartTimeStamp = OMX_FALSE;
594 Exynos_OSAL_Memset(pExynosComponent->timeStamp, -19771003, sizeof(OMX_TICKS) * MAX_TIMESTAMP);
595 Exynos_OSAL_Memset(pExynosComponent->nFlags, 0, sizeof(OMX_U32) * MAX_FLAGS);
596 pExynosComponent->getAllDelayBuffer = OMX_FALSE;
597 pExynosComponent->bSaveFlagEOS = OMX_FALSE;
598 pExynosComponent->bBehaviorEOS = OMX_FALSE;
599 pExynosComponent->reInputData = OMX_FALSE;
600 }
601
602 pExynosComponent->pExynosPort[nPortIndex].bIsPortFlushed = OMX_FALSE;
603 Exynos_OSAL_Log(EXYNOS_LOG_TRACE,"OMX_CommandFlush EventCmdComplete, port:%d", nPortIndex);
604 if (bEvent == OMX_TRUE)
605 pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent,
606 pExynosComponent->callbackData,
607 OMX_EventCmdComplete,
608 OMX_CommandFlush, nPortIndex, NULL);
609 }
610 Exynos_OSAL_MutexUnlock(flushPortBuffer[1]->bufferMutex);
611 Exynos_OSAL_MutexUnlock(flushPortBuffer[0]->bufferMutex);
612
613 EXIT:
614 if ((ret != OMX_ErrorNone) && (pOMXComponent != NULL) && (pExynosComponent != NULL)) {
615 Exynos_OSAL_Log(EXYNOS_LOG_ERROR,"%s : %d", __FUNCTION__, __LINE__);
616 pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
617 pExynosComponent->callbackData,
618 OMX_EventError,
619 ret, 0, NULL);
620 }
621
622 FunctionOut();
623
624 return ret;
625 }
626
627 OMX_ERRORTYPE Exynos_ResolutionUpdate(OMX_COMPONENTTYPE *pOMXComponent)
628 {
629 OMX_ERRORTYPE ret = OMX_ErrorNone;
630 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
631 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
632 EXYNOS_OMX_BASEPORT *pInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
633 EXYNOS_OMX_BASEPORT *pOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
634
635 pOutputPort->cropRectangle.nTop = pOutputPort->newCropRectangle.nTop;
636 pOutputPort->cropRectangle.nLeft = pOutputPort->newCropRectangle.nLeft;
637 pOutputPort->cropRectangle.nWidth = pOutputPort->newCropRectangle.nWidth;
638 pOutputPort->cropRectangle.nHeight = pOutputPort->newCropRectangle.nHeight;
639
640 pInputPort->portDefinition.format.video.nFrameWidth = pInputPort->newPortDefinition.format.video.nFrameWidth;
641 pInputPort->portDefinition.format.video.nFrameHeight = pInputPort->newPortDefinition.format.video.nFrameHeight;
642 pInputPort->portDefinition.format.video.nStride = pInputPort->newPortDefinition.format.video.nStride;
643 pInputPort->portDefinition.format.video.nSliceHeight = pInputPort->newPortDefinition.format.video.nSliceHeight;
644
645 pOutputPort->portDefinition.nBufferCountActual = pOutputPort->newPortDefinition.nBufferCountActual;
646 pOutputPort->portDefinition.nBufferCountMin = pOutputPort->newPortDefinition.nBufferCountMin;
647
648 Exynos_UpdateFrameSize(pOMXComponent);
649
650 return ret;
651 }
652
653 OMX_ERRORTYPE Exynos_InputBufferReturn(
654 OMX_COMPONENTTYPE *pOMXComponent,
655 EXYNOS_OMX_DATABUFFER *pDataBuffer)
656 {
657 OMX_ERRORTYPE ret = OMX_ErrorNone;
658 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
659 EXYNOS_OMX_BASEPORT *pInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
660 OMX_BUFFERHEADERTYPE *pBufferHdr = NULL;
661
662 FunctionIn();
663
664 pBufferHdr = pDataBuffer->bufferHeader;
665
666 if (pBufferHdr != NULL) {
667 if (pInputPort->markType.hMarkTargetComponent != NULL) {
668 pBufferHdr->hMarkTargetComponent = pInputPort->markType.hMarkTargetComponent;
669 pBufferHdr->pMarkData = pInputPort->markType.pMarkData;
670 pInputPort->markType.hMarkTargetComponent = NULL;
671 pInputPort->markType.pMarkData = NULL;
672 }
673
674 if (pBufferHdr->hMarkTargetComponent != NULL) {
675 if (pBufferHdr->hMarkTargetComponent == pOMXComponent) {
676 pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
677 pExynosComponent->callbackData,
678 OMX_EventMark,
679 0, 0, pBufferHdr->pMarkData);
680 } else {
681 pExynosComponent->propagateMarkType.hMarkTargetComponent = pBufferHdr->hMarkTargetComponent;
682 pExynosComponent->propagateMarkType.pMarkData = pBufferHdr->pMarkData;
683 }
684 }
685
686 pBufferHdr->nFilledLen = 0;
687 pBufferHdr->nOffset = 0;
688 Exynos_OMX_InputBufferReturn(pOMXComponent, pBufferHdr);
689 }
690
691 /* reset dataBuffer */
692 Exynos_ResetDataBuffer(pDataBuffer);
693
694 EXIT:
695 FunctionOut();
696
697 return ret;
698 }
699
700 OMX_ERRORTYPE Exynos_InputBufferGetQueue(EXYNOS_OMX_BASECOMPONENT *pExynosComponent)
701 {
702 OMX_ERRORTYPE ret = OMX_ErrorUndefined;
703 EXYNOS_OMX_BASEPORT *pExynosPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
704 EXYNOS_OMX_MESSAGE *message = NULL;
705 EXYNOS_OMX_DATABUFFER *inputUseBuffer = NULL;
706
707 FunctionIn();
708
709 inputUseBuffer = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
710
711 if (pExynosComponent->currentState != OMX_StateExecuting) {
712 ret = OMX_ErrorUndefined;
713 goto EXIT;
714 } else if ((pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) &&
715 (!CHECK_PORT_BEING_FLUSHED(pExynosPort))) {
716 Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
717 if (inputUseBuffer->dataValid != OMX_TRUE) {
718 message = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
719 if (message == NULL) {
720 ret = OMX_ErrorUndefined;
721 goto EXIT;
722 }
723 if (message->messageType == EXYNOS_OMX_CommandFakeBuffer) {
724 Exynos_OSAL_Free(message);
725 ret = OMX_ErrorCodecFlush;
726 goto EXIT;
727 }
728
729 inputUseBuffer->bufferHeader = (OMX_BUFFERHEADERTYPE *)(message->pCmdData);
730 inputUseBuffer->allocSize = inputUseBuffer->bufferHeader->nAllocLen;
731 inputUseBuffer->dataLen = inputUseBuffer->bufferHeader->nFilledLen;
732 inputUseBuffer->remainDataLen = inputUseBuffer->dataLen;
733 inputUseBuffer->usedDataLen = 0;
734 inputUseBuffer->dataValid = OMX_TRUE;
735 inputUseBuffer->nFlags = inputUseBuffer->bufferHeader->nFlags;
736 inputUseBuffer->timeStamp = inputUseBuffer->bufferHeader->nTimeStamp;
737
738 Exynos_OSAL_Free(message);
739
740 if (inputUseBuffer->allocSize <= inputUseBuffer->dataLen)
741 Exynos_OSAL_Log(EXYNOS_LOG_WARNING, "Input Buffer Full, Check input buffer size! allocSize:%d, dataLen:%d", inputUseBuffer->allocSize, inputUseBuffer->dataLen);
742 }
743 ret = OMX_ErrorNone;
744 }
745 EXIT:
746 FunctionOut();
747
748 return ret;
749 }
750
751 OMX_ERRORTYPE Exynos_OutputBufferReturn(
752 OMX_COMPONENTTYPE *pOMXComponent,
753 EXYNOS_OMX_DATABUFFER *pDataBuffer)
754 {
755 OMX_ERRORTYPE ret = OMX_ErrorNone;
756 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
757 OMX_BUFFERHEADERTYPE *pBufferHdr = pDataBuffer->bufferHeader;
758
759 FunctionIn();
760
761 if (pBufferHdr != NULL) {
762 pBufferHdr->nFilledLen = pDataBuffer->remainDataLen;
763 pBufferHdr->nOffset = 0;
764 pBufferHdr->nFlags = pDataBuffer->nFlags;
765 pBufferHdr->nTimeStamp = pDataBuffer->timeStamp;
766
767 if (pExynosComponent->propagateMarkType.hMarkTargetComponent != NULL) {
768 pBufferHdr->hMarkTargetComponent = pExynosComponent->propagateMarkType.hMarkTargetComponent;
769 pBufferHdr->pMarkData = pExynosComponent->propagateMarkType.pMarkData;
770
771 pExynosComponent->propagateMarkType.hMarkTargetComponent = NULL;
772 pExynosComponent->propagateMarkType.pMarkData = NULL;
773 }
774
775 if ((pBufferHdr->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) {
776 Exynos_OSAL_Log(EXYNOS_LOG_TRACE,"event OMX_BUFFERFLAG_EOS!!!");
777 pExynosComponent->pCallbacks->EventHandler(pOMXComponent,
778 pExynosComponent->callbackData,
779 OMX_EventBufferFlag,
780 OUTPUT_PORT_INDEX,
781 pBufferHdr->nFlags, NULL);
782 }
783 Exynos_OMX_OutputBufferReturn(pOMXComponent, pBufferHdr);
784 }
785
786 /* reset dataBuffer */
787 Exynos_ResetDataBuffer(pDataBuffer);
788
789 EXIT:
790 FunctionOut();
791
792 return ret;
793 }
794
795 OMX_ERRORTYPE Exynos_OutputBufferGetQueue(EXYNOS_OMX_BASECOMPONENT *pExynosComponent)
796 {
797 OMX_ERRORTYPE ret = OMX_ErrorUndefined;
798 EXYNOS_OMX_BASEPORT *pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
799 EXYNOS_OMX_MESSAGE *message = NULL;
800 EXYNOS_OMX_DATABUFFER *outputUseBuffer = NULL;
801
802 FunctionIn();
803
804 if (pExynosPort->bufferProcessType & BUFFER_COPY) {
805 outputUseBuffer = &(pExynosPort->way.port2WayDataBuffer.outputDataBuffer);
806 } else if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
807 outputUseBuffer = &(pExynosPort->way.port2WayDataBuffer.inputDataBuffer);
808 } else {
809 ret = OMX_ErrorUndefined;
810 goto EXIT;
811 }
812
813 if (pExynosComponent->currentState != OMX_StateExecuting) {
814 ret = OMX_ErrorUndefined;
815 goto EXIT;
816 } else if ((pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) &&
817 (!CHECK_PORT_BEING_FLUSHED(pExynosPort))){
818 Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
819 if (outputUseBuffer->dataValid != OMX_TRUE) {
820 message = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
821 if (message == NULL) {
822 ret = OMX_ErrorUndefined;
823 goto EXIT;
824 }
825 if (message->messageType == EXYNOS_OMX_CommandFakeBuffer) {
826 Exynos_OSAL_Free(message);
827 ret = OMX_ErrorCodecFlush;
828 goto EXIT;
829 }
830
831 outputUseBuffer->bufferHeader = (OMX_BUFFERHEADERTYPE *)(message->pCmdData);
832 outputUseBuffer->allocSize = outputUseBuffer->bufferHeader->nAllocLen;
833 outputUseBuffer->dataLen = 0; //dataBuffer->bufferHeader->nFilledLen;
834 outputUseBuffer->remainDataLen = outputUseBuffer->dataLen;
835 outputUseBuffer->usedDataLen = 0; //dataBuffer->bufferHeader->nOffset;
836 outputUseBuffer->dataValid = OMX_TRUE;
837 /* dataBuffer->nFlags = dataBuffer->bufferHeader->nFlags; */
838 /* dataBuffer->nTimeStamp = dataBuffer->bufferHeader->nTimeStamp; */
839 /*
840 if (pExynosPort->bufferProcessType & BUFFER_SHARE)
841 outputUseBuffer->pPrivate = outputUseBuffer->bufferHeader->pOutputPortPrivate;
842 else if (pExynosPort->bufferProcessType & BUFFER_COPY) {
843 pExynosPort->processData.dataBuffer = outputUseBuffer->bufferHeader->pBuffer;
844 pExynosPort->processData.allocSize = outputUseBuffer->bufferHeader->nAllocLen;
845 }
846 */
847
848 Exynos_OSAL_Free(message);
849 }
850 ret = OMX_ErrorNone;
851 }
852 EXIT:
853 FunctionOut();
854
855 return ret;
856
857 }
858
859 OMX_BUFFERHEADERTYPE *Exynos_OutputBufferGetQueue_Direct(EXYNOS_OMX_BASECOMPONENT *pExynosComponent)
860 {
861 OMX_BUFFERHEADERTYPE *retBuffer = NULL;
862 EXYNOS_OMX_BASEPORT *pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
863 EXYNOS_OMX_MESSAGE *message = NULL;
864
865 FunctionIn();
866
867 if (pExynosComponent->currentState != OMX_StateExecuting) {
868 retBuffer = NULL;
869 goto EXIT;
870 } else if ((pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) &&
871 (!CHECK_PORT_BEING_FLUSHED(pExynosPort))){
872 Exynos_OSAL_SemaphoreWait(pExynosPort->bufferSemID);
873
874 message = (EXYNOS_OMX_MESSAGE *)Exynos_OSAL_Dequeue(&pExynosPort->bufferQ);
875 if (message == NULL) {
876 retBuffer = NULL;
877 goto EXIT;
878 }
879 if (message->messageType == EXYNOS_OMX_CommandFakeBuffer) {
880 Exynos_OSAL_Free(message);
881 retBuffer = NULL;
882 goto EXIT;
883 }
884
885 retBuffer = (OMX_BUFFERHEADERTYPE *)(message->pCmdData);
886 Exynos_OSAL_Free(message);
887 }
888
889 EXIT:
890 FunctionOut();
891
892 return retBuffer;
893 }
894
895 OMX_ERRORTYPE Exynos_CodecBufferEnQueue(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_U32 PortIndex, OMX_PTR data)
896 {
897 OMX_ERRORTYPE ret = OMX_ErrorNone;
898 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
899
900 FunctionIn();
901
902 pExynosPort= &pExynosComponent->pExynosPort[PortIndex];
903
904 if (data == NULL) {
905 ret = OMX_ErrorInsufficientResources;
906 goto EXIT;
907 }
908
909 ret = Exynos_OSAL_Queue(&pExynosPort->codecBufferQ, (void *)data);
910 if (ret != 0) {
911 ret = OMX_ErrorUndefined;
912 goto EXIT;
913 }
914 Exynos_OSAL_SemaphorePost(pExynosPort->codecSemID);
915
916 ret = OMX_ErrorNone;
917
918 EXIT:
919 FunctionOut();
920
921 return ret;
922 }
923
924 OMX_ERRORTYPE Exynos_CodecBufferDeQueue(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_U32 PortIndex, OMX_PTR *data)
925 {
926 OMX_ERRORTYPE ret = OMX_ErrorNone;
927 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
928 OMX_U32 tempData;
929
930 FunctionIn();
931
932 pExynosPort = &pExynosComponent->pExynosPort[PortIndex];
933 Exynos_OSAL_SemaphoreWait(pExynosPort->codecSemID);
934 tempData = (OMX_U32)Exynos_OSAL_Dequeue(&pExynosPort->codecBufferQ);
935 if (tempData == NULL) {
936 *data = NULL;
937 ret = OMX_ErrorUndefined;
938 goto EXIT;
939 }
940 *data = (OMX_PTR)tempData;
941
942 ret = OMX_ErrorNone;
943
944 EXIT:
945 FunctionOut();
946
947 return ret;
948 }
949
950 OMX_ERRORTYPE Exynos_CodecBufferReset(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_U32 PortIndex)
951 {
952 OMX_ERRORTYPE ret = OMX_ErrorNone;
953 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
954
955 FunctionIn();
956
957 pExynosPort= &pExynosComponent->pExynosPort[PortIndex];
958
959 ret = Exynos_OSAL_ResetQueue(&pExynosPort->codecBufferQ);
960 if (ret != 0) {
961 ret = OMX_ErrorUndefined;
962 goto EXIT;
963 }
964 while (1) {
965 int cnt = 0;
966 Exynos_OSAL_Get_SemaphoreCount(pExynosPort->codecSemID, &cnt);
967 if (cnt > 0)
968 Exynos_OSAL_SemaphoreWait(pExynosPort->codecSemID);
969 else
970 break;
971 }
972 ret = OMX_ErrorNone;
973
974 EXIT:
975 FunctionOut();
976
977 return ret;
978 }
979
980 OMX_ERRORTYPE Exynos_OMX_VideoDecodeGetParameter(
981 OMX_IN OMX_HANDLETYPE hComponent,
982 OMX_IN OMX_INDEXTYPE nParamIndex,
983 OMX_INOUT OMX_PTR ComponentParameterStructure)
984 {
985 OMX_ERRORTYPE ret = OMX_ErrorNone;
986 OMX_COMPONENTTYPE *pOMXComponent = NULL;
987 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
988 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
989
990 FunctionIn();
991
992 if (hComponent == NULL) {
993 ret = OMX_ErrorBadParameter;
994 goto EXIT;
995 }
996 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
997 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
998 if (ret != OMX_ErrorNone) {
999 goto EXIT;
1000 }
1001
1002 if (pOMXComponent->pComponentPrivate == NULL) {
1003 ret = OMX_ErrorBadParameter;
1004 goto EXIT;
1005 }
1006 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1007
1008 if (pExynosComponent->currentState == OMX_StateInvalid ) {
1009 ret = OMX_ErrorInvalidState;
1010 goto EXIT;
1011 }
1012
1013 if (ComponentParameterStructure == NULL) {
1014 ret = OMX_ErrorBadParameter;
1015 goto EXIT;
1016 }
1017
1018 switch (nParamIndex) {
1019 case OMX_IndexParamVideoInit:
1020 {
1021 OMX_PORT_PARAM_TYPE *portParam = (OMX_PORT_PARAM_TYPE *)ComponentParameterStructure;
1022 ret = Exynos_OMX_Check_SizeVersion(portParam, sizeof(OMX_PORT_PARAM_TYPE));
1023 if (ret != OMX_ErrorNone) {
1024 goto EXIT;
1025 }
1026
1027 portParam->nPorts = pExynosComponent->portParam.nPorts;
1028 portParam->nStartPortNumber = pExynosComponent->portParam.nStartPortNumber;
1029 ret = OMX_ErrorNone;
1030 }
1031 break;
1032 case OMX_IndexParamVideoPortFormat:
1033 {
1034 OMX_VIDEO_PARAM_PORTFORMATTYPE *portFormat = (OMX_VIDEO_PARAM_PORTFORMATTYPE *)ComponentParameterStructure;
1035 OMX_U32 portIndex = portFormat->nPortIndex;
1036 OMX_U32 index = portFormat->nIndex;
1037 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
1038 OMX_PARAM_PORTDEFINITIONTYPE *portDefinition = NULL;
1039 OMX_U32 supportFormatNum = 0; /* supportFormatNum = N-1 */
1040
1041 ret = Exynos_OMX_Check_SizeVersion(portFormat, sizeof(OMX_VIDEO_PARAM_PORTFORMATTYPE));
1042 if (ret != OMX_ErrorNone) {
1043 goto EXIT;
1044 }
1045
1046 if ((portIndex >= pExynosComponent->portParam.nPorts)) {
1047 ret = OMX_ErrorBadPortIndex;
1048 goto EXIT;
1049 }
1050
1051
1052 if (portIndex == INPUT_PORT_INDEX) {
1053 supportFormatNum = INPUT_PORT_SUPPORTFORMAT_NUM_MAX - 1;
1054 if (index > supportFormatNum) {
1055 ret = OMX_ErrorNoMore;
1056 goto EXIT;
1057 }
1058
1059 pExynosPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1060 portDefinition = &pExynosPort->portDefinition;
1061
1062 portFormat->eCompressionFormat = portDefinition->format.video.eCompressionFormat;
1063 portFormat->eColorFormat = portDefinition->format.video.eColorFormat;
1064 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1065 } else if (portIndex == OUTPUT_PORT_INDEX) {
1066 pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1067 portDefinition = &pExynosPort->portDefinition;
1068
1069 if (pExynosPort->bIsANBEnabled == OMX_FALSE) {
1070 switch (index) {
1071 case supportFormat_0:
1072 portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1073 portFormat->eColorFormat = OMX_COLOR_FormatYUV420Planar;
1074 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1075 break;
1076 case supportFormat_1:
1077 portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1078 portFormat->eColorFormat = OMX_COLOR_FormatYUV420SemiPlanar;
1079 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1080 break;
1081 case supportFormat_2:
1082 portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1083 portFormat->eColorFormat = OMX_SEC_COLOR_FormatNV12Tiled;
1084 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1085 break;
1086 #ifdef USE_DUALDPB_MODE
1087 case supportFormat_3:
1088 portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1089 portFormat->eColorFormat = OMX_SEC_COLOR_FormatNV21Linear;
1090 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1091 break;
1092 case supportFormat_4:
1093 portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1094 portFormat->eColorFormat = OMX_SEC_COLOR_FormatYVU420Planar;
1095 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1096 break;
1097 #endif
1098 default:
1099 if (index > supportFormat_0) {
1100 ret = OMX_ErrorNoMore;
1101 goto EXIT;
1102 }
1103 break;
1104 }
1105 } else {
1106 switch (index) {
1107 case supportFormat_0:
1108 portFormat->eCompressionFormat = OMX_VIDEO_CodingUnused;
1109 portFormat->eColorFormat = OMX_SEC_COLOR_FormatNV12Tiled;
1110 portFormat->xFramerate = portDefinition->format.video.xFramerate;
1111 break;
1112 default:
1113 if (index > supportFormat_0) {
1114 ret = OMX_ErrorNoMore;
1115 goto EXIT;
1116 }
1117 break;
1118 }
1119 }
1120 }
1121 ret = OMX_ErrorNone;
1122 }
1123 break;
1124 #ifdef USE_ANB
1125 case OMX_IndexParamGetAndroidNativeBuffer:
1126 {
1127 ret = Exynos_OSAL_GetANBParameter(hComponent, nParamIndex, ComponentParameterStructure);
1128 }
1129 break;
1130 case OMX_IndexParamPortDefinition:
1131 {
1132 OMX_PARAM_PORTDEFINITIONTYPE *portDefinition = (OMX_PARAM_PORTDEFINITIONTYPE *)ComponentParameterStructure;
1133 OMX_U32 portIndex = portDefinition->nPortIndex;
1134 EXYNOS_OMX_BASEPORT *pExynosPort;
1135
1136 ret = Exynos_OMX_GetParameter(hComponent, nParamIndex, ComponentParameterStructure);
1137 if (ret != OMX_ErrorNone) {
1138 goto EXIT;
1139 }
1140
1141 /* at this point, GetParameter has done all the verification, we
1142 * just dereference things directly here
1143 */
1144 pExynosPort = &pExynosComponent->pExynosPort[portIndex];
1145 if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
1146 portDefinition->format.video.eColorFormat =
1147 (OMX_COLOR_FORMATTYPE)Exynos_OSAL_OMX2HalPixelFormat(portDefinition->format.video.eColorFormat);
1148 }
1149 }
1150 break;
1151 #endif
1152 case OMX_IndexVendorNeedContigMemory:
1153 {
1154 EXYNOS_OMX_VIDEO_PARAM_PORTMEMTYPE *pPortMemType = (EXYNOS_OMX_VIDEO_PARAM_PORTMEMTYPE *)ComponentParameterStructure;
1155 OMX_U32 nPortIndex = pPortMemType->nPortIndex;
1156 EXYNOS_OMX_BASEPORT *pExynosPort;
1157
1158 if (nPortIndex >= pExynosComponent->portParam.nPorts) {
1159 ret = OMX_ErrorBadPortIndex;
1160 goto EXIT;
1161 }
1162
1163 ret = Exynos_OMX_Check_SizeVersion(pPortMemType, sizeof(EXYNOS_OMX_VIDEO_PARAM_PORTMEMTYPE));
1164 if (ret != OMX_ErrorNone)
1165 goto EXIT;
1166
1167 pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1168
1169 pPortMemType->bNeedContigMem = pExynosPort->bNeedContigMem;
1170 }
1171 break;
1172 default:
1173 {
1174 ret = Exynos_OMX_GetParameter(hComponent, nParamIndex, ComponentParameterStructure);
1175 }
1176 break;
1177 }
1178
1179 EXIT:
1180 FunctionOut();
1181
1182 return ret;
1183 }
1184 OMX_ERRORTYPE Exynos_OMX_VideoDecodeSetParameter(
1185 OMX_IN OMX_HANDLETYPE hComponent,
1186 OMX_IN OMX_INDEXTYPE nIndex,
1187 OMX_IN OMX_PTR ComponentParameterStructure)
1188 {
1189 OMX_ERRORTYPE ret = OMX_ErrorNone;
1190 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1191 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1192 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
1193
1194 FunctionIn();
1195
1196 if (hComponent == NULL) {
1197 ret = OMX_ErrorBadParameter;
1198 goto EXIT;
1199 }
1200 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1201 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1202 if (ret != OMX_ErrorNone) {
1203 goto EXIT;
1204 }
1205
1206 if (pOMXComponent->pComponentPrivate == NULL) {
1207 ret = OMX_ErrorBadParameter;
1208 goto EXIT;
1209 }
1210 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1211
1212 if (pExynosComponent->currentState == OMX_StateInvalid ) {
1213 ret = OMX_ErrorInvalidState;
1214 goto EXIT;
1215 }
1216
1217 if (ComponentParameterStructure == NULL) {
1218 ret = OMX_ErrorBadParameter;
1219 goto EXIT;
1220 }
1221
1222 switch (nIndex) {
1223 case OMX_IndexParamVideoPortFormat:
1224 {
1225 OMX_VIDEO_PARAM_PORTFORMATTYPE *portFormat = (OMX_VIDEO_PARAM_PORTFORMATTYPE *)ComponentParameterStructure;
1226 OMX_U32 portIndex = portFormat->nPortIndex;
1227 OMX_U32 index = portFormat->nIndex;
1228 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
1229 OMX_PARAM_PORTDEFINITIONTYPE *portDefinition = NULL;
1230 OMX_U32 supportFormatNum = 0;
1231
1232 ret = Exynos_OMX_Check_SizeVersion(portFormat, sizeof(OMX_VIDEO_PARAM_PORTFORMATTYPE));
1233 if (ret != OMX_ErrorNone) {
1234 goto EXIT;
1235 }
1236
1237 if ((portIndex >= pExynosComponent->portParam.nPorts)) {
1238 ret = OMX_ErrorBadPortIndex;
1239 goto EXIT;
1240 } else {
1241 pExynosPort = &pExynosComponent->pExynosPort[portIndex];
1242 portDefinition = &pExynosPort->portDefinition;
1243
1244 portDefinition->format.video.eColorFormat = portFormat->eColorFormat;
1245 portDefinition->format.video.eCompressionFormat = portFormat->eCompressionFormat;
1246 portDefinition->format.video.xFramerate = portFormat->xFramerate;
1247 }
1248 }
1249 break;
1250 case OMX_IndexParamPortDefinition:
1251 {
1252 OMX_PARAM_PORTDEFINITIONTYPE *pPortDefinition = (OMX_PARAM_PORTDEFINITIONTYPE *)ComponentParameterStructure;
1253 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1254 OMX_U32 portIndex = pPortDefinition->nPortIndex;
1255 EXYNOS_OMX_BASEPORT *pExynosPort;
1256 OMX_U32 width, height, size;
1257 OMX_U32 realWidth, realHeight;
1258
1259 if (portIndex >= pExynosComponent->portParam.nPorts) {
1260 ret = OMX_ErrorBadPortIndex;
1261 goto EXIT;
1262 }
1263 ret = Exynos_OMX_Check_SizeVersion(pPortDefinition, sizeof(OMX_PARAM_PORTDEFINITIONTYPE));
1264 if (ret != OMX_ErrorNone) {
1265 goto EXIT;
1266 }
1267
1268 pExynosPort = &pExynosComponent->pExynosPort[portIndex];
1269
1270 if ((pExynosComponent->currentState != OMX_StateLoaded) && (pExynosComponent->currentState != OMX_StateWaitForResources)) {
1271 if (pExynosPort->portDefinition.bEnabled == OMX_TRUE) {
1272 ret = OMX_ErrorIncorrectStateOperation;
1273 goto EXIT;
1274 }
1275 }
1276 if ((pPortDefinition->nBufferCountActual < pExynosPort->portDefinition.nBufferCountMin) ||
1277 ((pVideoDec->bDRMPlayerMode == OMX_TRUE) &&
1278 (pPortDefinition->nBufferCountActual > (pExynosPort->portDefinition.nBufferCountMin + MAX_DISPLAY_EXTRA_BUFFER)))) {
1279 ret = OMX_ErrorBadParameter;
1280 goto EXIT;
1281 }
1282
1283 Exynos_OSAL_Memcpy(&pExynosPort->portDefinition, pPortDefinition, pPortDefinition->nSize);
1284
1285 #ifdef USE_ANB // Modified by Google engineer
1286 /* should not affect the format since in ANB case, the caller
1287 * is providing us a HAL format */
1288 if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
1289 pExynosPort->portDefinition.format.video.eColorFormat =
1290 Exynos_OSAL_Hal2OMXPixelFormat(pExynosPort->portDefinition.format.video.eColorFormat);
1291 }
1292 #endif
1293
1294 realWidth = pExynosPort->portDefinition.format.video.nFrameWidth;
1295 realHeight = pExynosPort->portDefinition.format.video.nFrameHeight;
1296 width = ((realWidth + 15) & (~15));
1297 height = ((realHeight + 15) & (~15));
1298 size = (width * height * 3) / 2;
1299 pExynosPort->portDefinition.format.video.nStride = width;
1300 pExynosPort->portDefinition.format.video.nSliceHeight = height;
1301 pExynosPort->portDefinition.nBufferSize = (size > pExynosPort->portDefinition.nBufferSize) ? size : pExynosPort->portDefinition.nBufferSize;
1302
1303 if (portIndex == INPUT_PORT_INDEX) {
1304 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1305 pExynosOutputPort->portDefinition.format.video.nFrameWidth = pExynosPort->portDefinition.format.video.nFrameWidth;
1306 pExynosOutputPort->portDefinition.format.video.nFrameHeight = pExynosPort->portDefinition.format.video.nFrameHeight;
1307 pExynosOutputPort->portDefinition.format.video.nStride = width;
1308 pExynosOutputPort->portDefinition.format.video.nSliceHeight = height;
1309
1310 switch (pExynosOutputPort->portDefinition.format.video.eColorFormat) {
1311 case OMX_COLOR_FormatYUV420Planar:
1312 case OMX_COLOR_FormatYUV420SemiPlanar:
1313 case OMX_SEC_COLOR_FormatNV12Tiled:
1314 pExynosOutputPort->portDefinition.nBufferSize = (width * height * 3) / 2;
1315 break;
1316 default:
1317 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Color format is not support!! use default YUV size!!");
1318 ret = OMX_ErrorUnsupportedSetting;
1319 break;
1320 }
1321 }
1322 }
1323 break;
1324 #ifdef USE_ANB
1325 case OMX_IndexParamEnableAndroidBuffers:
1326 case OMX_IndexParamUseAndroidNativeBuffer:
1327 {
1328 ret = Exynos_OSAL_SetANBParameter(hComponent, nIndex, ComponentParameterStructure);
1329 }
1330 break;
1331 #endif
1332 case OMX_IndexVendorNeedContigMemory:
1333 {
1334 EXYNOS_OMX_VIDEO_PARAM_PORTMEMTYPE *pPortMemType = (EXYNOS_OMX_VIDEO_PARAM_PORTMEMTYPE *)ComponentParameterStructure;
1335 OMX_U32 nPortIndex = pPortMemType->nPortIndex;
1336 EXYNOS_OMX_BASEPORT *pExynosPort;
1337
1338 if (nPortIndex >= pExynosComponent->portParam.nPorts) {
1339 ret = OMX_ErrorBadPortIndex;
1340 goto EXIT;
1341 }
1342
1343 ret = Exynos_OMX_Check_SizeVersion(pPortMemType, sizeof(EXYNOS_OMX_VIDEO_PARAM_PORTMEMTYPE));
1344 if (ret != OMX_ErrorNone)
1345 goto EXIT;
1346
1347 pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
1348
1349 if ((pExynosComponent->currentState != OMX_StateLoaded) && (pExynosComponent->currentState != OMX_StateWaitForResources)) {
1350 if (pExynosPort->portDefinition.bEnabled == OMX_TRUE) {
1351 ret = OMX_ErrorIncorrectStateOperation;
1352 goto EXIT;
1353 }
1354 }
1355
1356 pExynosPort->bNeedContigMem = pPortMemType->bNeedContigMem;
1357 }
1358 break;
1359 case OMX_IndexVendorSetDTSMode:
1360 {
1361 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1362 EXYNOS_OMX_VIDEO_PARAM_DTSMODE *pDTSParam = (EXYNOS_OMX_VIDEO_PARAM_DTSMODE *)ComponentParameterStructure;
1363
1364 ret = Exynos_OMX_Check_SizeVersion(pDTSParam, sizeof(EXYNOS_OMX_VIDEO_PARAM_DTSMODE));
1365 if (ret != OMX_ErrorNone)
1366 goto EXIT;
1367
1368 pVideoDec->bDTSMode = pDTSParam->bDTSMode;
1369 }
1370 break;
1371 case OMX_IndexParamEnableThumbnailMode:
1372 {
1373 EXYNOS_OMX_VIDEO_THUMBNAILMODE *pThumbnailMode = (EXYNOS_OMX_VIDEO_THUMBNAILMODE *)ComponentParameterStructure;
1374 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1375
1376 ret = Exynos_OMX_Check_SizeVersion(pThumbnailMode, sizeof(EXYNOS_OMX_VIDEO_THUMBNAILMODE));
1377 if (ret != OMX_ErrorNone) {
1378 goto EXIT;
1379 }
1380
1381 pVideoDec->bThumbnailMode = pThumbnailMode->bEnable;
1382 if (pVideoDec->bThumbnailMode == OMX_TRUE) {
1383 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1384 pExynosOutputPort->portDefinition.nBufferCountMin = 1;
1385 pExynosOutputPort->portDefinition.nBufferCountActual = 1;
1386 }
1387
1388 ret = OMX_ErrorNone;
1389 }
1390 break;
1391 default:
1392 {
1393 ret = Exynos_OMX_SetParameter(hComponent, nIndex, ComponentParameterStructure);
1394 }
1395 break;
1396 }
1397
1398 EXIT:
1399 FunctionOut();
1400
1401 return ret;
1402 }
1403
1404 OMX_ERRORTYPE Exynos_OMX_VideoDecodeGetConfig(
1405 OMX_HANDLETYPE hComponent,
1406 OMX_INDEXTYPE nIndex,
1407 OMX_PTR pComponentConfigStructure)
1408 {
1409 OMX_ERRORTYPE ret = OMX_ErrorNone;
1410 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1411 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1412
1413 FunctionIn();
1414
1415 if (hComponent == NULL) {
1416 ret = OMX_ErrorBadParameter;
1417 goto EXIT;
1418 }
1419 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1420 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1421 if (ret != OMX_ErrorNone) {
1422 goto EXIT;
1423 }
1424 if (pOMXComponent->pComponentPrivate == NULL) {
1425 ret = OMX_ErrorBadParameter;
1426 goto EXIT;
1427 }
1428 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1429 if (pComponentConfigStructure == NULL) {
1430 ret = OMX_ErrorBadParameter;
1431 goto EXIT;
1432 }
1433 if (pExynosComponent->currentState == OMX_StateInvalid) {
1434 ret = OMX_ErrorInvalidState;
1435 goto EXIT;
1436 }
1437
1438 switch (nIndex) {
1439 case OMX_IndexVendorGetBufferFD:
1440 {
1441 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1442 EXYNOS_OMX_VIDEO_CONFIG_BUFFERINFO *pBufferInfo = (EXYNOS_OMX_VIDEO_CONFIG_BUFFERINFO *)pComponentConfigStructure;
1443
1444 ret = Exynos_OMX_Check_SizeVersion(pBufferInfo, sizeof(EXYNOS_OMX_VIDEO_CONFIG_BUFFERINFO));
1445 if (ret != OMX_ErrorNone)
1446 goto EXIT;
1447
1448 pBufferInfo->fd = Exynos_OSAL_SharedMemory_VirtToION(pVideoDec->hSharedMemory, pBufferInfo->pVirAddr);
1449 }
1450 break;
1451 default:
1452 ret = Exynos_OMX_GetConfig(hComponent, nIndex, pComponentConfigStructure);
1453 break;
1454 }
1455
1456 EXIT:
1457 FunctionOut();
1458
1459 return ret;
1460 }
1461
1462 OMX_ERRORTYPE Exynos_OMX_VideoDecodeSetConfig(
1463 OMX_HANDLETYPE hComponent,
1464 OMX_INDEXTYPE nIndex,
1465 OMX_PTR pComponentConfigStructure)
1466 {
1467 OMX_ERRORTYPE ret = OMX_ErrorNone;
1468 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1469 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1470
1471 FunctionIn();
1472
1473 if (hComponent == NULL) {
1474 ret = OMX_ErrorBadParameter;
1475 goto EXIT;
1476 }
1477 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1478 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1479 if (ret != OMX_ErrorNone) {
1480 goto EXIT;
1481 }
1482 if (pOMXComponent->pComponentPrivate == NULL) {
1483 ret = OMX_ErrorBadParameter;
1484 goto EXIT;
1485 }
1486 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1487 if (pComponentConfigStructure == NULL) {
1488 ret = OMX_ErrorBadParameter;
1489 goto EXIT;
1490 }
1491 if (pExynosComponent->currentState == OMX_StateInvalid) {
1492 ret = OMX_ErrorInvalidState;
1493 goto EXIT;
1494 }
1495
1496 switch (nIndex) {
1497 #ifdef USE_QOS_CTRL
1498 case OMX_IndexVendorSetQosRatio:
1499 {
1500 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1501 EXYNOS_OMX_VIDEO_CONFIG_QOSINFO *pQosInfo = (EXYNOS_OMX_VIDEO_CONFIG_QOSINFO *)pComponentConfigStructure;
1502
1503 ret = Exynos_OMX_Check_SizeVersion(pQosInfo, sizeof(EXYNOS_OMX_VIDEO_CONFIG_QOSINFO));
1504 if (ret != OMX_ErrorNone)
1505 goto EXIT;
1506
1507 pVideoDec->nQosRatio = pQosInfo->nQosRatio;
1508 pVideoDec->bQosChanged = OMX_TRUE;
1509
1510 ret = OMX_ErrorNone;
1511 }
1512 break;
1513 #endif
1514 default:
1515 ret = Exynos_OMX_SetConfig(hComponent, nIndex, pComponentConfigStructure);
1516 break;
1517 }
1518
1519 EXIT:
1520 FunctionOut();
1521
1522 return ret;
1523 }
1524
1525 OMX_ERRORTYPE Exynos_OMX_VideoDecodeGetExtensionIndex(
1526 OMX_IN OMX_HANDLETYPE hComponent,
1527 OMX_IN OMX_STRING cParameterName,
1528 OMX_OUT OMX_INDEXTYPE *pIndexType)
1529 {
1530 OMX_ERRORTYPE ret = OMX_ErrorNone;
1531 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1532 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1533
1534 FunctionIn();
1535
1536 if (hComponent == NULL) {
1537 ret = OMX_ErrorBadParameter;
1538 goto EXIT;
1539 }
1540 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1541 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1542 if (ret != OMX_ErrorNone) {
1543 goto EXIT;
1544 }
1545
1546 if (pOMXComponent->pComponentPrivate == NULL) {
1547 ret = OMX_ErrorBadParameter;
1548 goto EXIT;
1549 }
1550 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1551
1552 if ((cParameterName == NULL) || (pIndexType == NULL)) {
1553 ret = OMX_ErrorBadParameter;
1554 goto EXIT;
1555 }
1556 if (pExynosComponent->currentState == OMX_StateInvalid) {
1557 ret = OMX_ErrorInvalidState;
1558 goto EXIT;
1559 }
1560
1561 if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_NEED_CONTIG_MEMORY) == 0) {
1562 *pIndexType = (OMX_INDEXTYPE) OMX_IndexVendorNeedContigMemory;
1563 ret = OMX_ErrorNone;
1564 goto EXIT;
1565 } else if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_CONFIG_GET_BUFFER_FD) == 0) {
1566 *pIndexType = (OMX_INDEXTYPE) OMX_IndexVendorGetBufferFD;
1567 ret = OMX_ErrorNone;
1568 goto EXIT;
1569 } else if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_SET_DTS_MODE) == 0) {
1570 *pIndexType = (OMX_INDEXTYPE) OMX_IndexVendorSetDTSMode;
1571 ret = OMX_ErrorNone;
1572 goto EXIT;
1573 }
1574 #ifdef USE_QOS_CTRL
1575 else if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_CONFIG_SET_QOS_RATIO) == 0) {
1576 *pIndexType = (OMX_INDEXTYPE) OMX_IndexVendorSetQosRatio;
1577 ret = OMX_ErrorNone;
1578 goto EXIT;
1579 }
1580 #endif
1581
1582 #ifdef USE_ANB
1583 if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_ENABLE_ANB) == 0) {
1584 *pIndexType = (OMX_INDEXTYPE) OMX_IndexParamEnableAndroidBuffers;
1585 goto EXIT;
1586 }
1587 if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_GET_ANB) == 0) {
1588 *pIndexType = (OMX_INDEXTYPE) OMX_IndexParamGetAndroidNativeBuffer;
1589 goto EXIT;
1590 }
1591 if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_USE_ANB) == 0) {
1592 *pIndexType = (OMX_INDEXTYPE) OMX_IndexParamUseAndroidNativeBuffer;
1593 goto EXIT;
1594 }
1595 #endif
1596
1597 if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_ENABLE_THUMBNAIL) == 0) {
1598 *pIndexType = OMX_IndexParamEnableThumbnailMode;
1599 goto EXIT;
1600 }
1601
1602 ret = Exynos_OMX_GetExtensionIndex(hComponent, cParameterName, pIndexType);
1603
1604 EXIT:
1605 FunctionOut();
1606
1607 return ret;
1608 }
1609
1610 #ifdef USE_ANB
1611 OMX_ERRORTYPE Exynos_Shared_ANBBufferToData(EXYNOS_OMX_DATABUFFER *pUseBuffer, EXYNOS_OMX_DATA *pData, EXYNOS_OMX_BASEPORT *pExynosPort, EXYNOS_OMX_PLANE nPlane)
1612 {
1613 OMX_ERRORTYPE ret = OMX_ErrorNone;
1614 OMX_U32 width, height;
1615 // void *pPhys[MAX_BUFFER_PLANE];
1616 ExynosVideoPlane planes[MAX_BUFFER_PLANE];
1617
1618 memset(planes, 0, sizeof(planes));
1619
1620 if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
1621 OMX_U32 stride;
1622
1623 width = pExynosPort->portDefinition.format.video.nFrameWidth;
1624 height = pExynosPort->portDefinition.format.video.nFrameHeight;
1625 if ((pUseBuffer->bufferHeader != NULL) &&
1626 (pUseBuffer->bufferHeader->pBuffer != NULL) &&
1627 (pExynosPort->exceptionFlag == GENERAL_STATE)) {
1628 Exynos_OSAL_LockANB(pUseBuffer->bufferHeader->pBuffer, width, height, pExynosPort->portDefinition.format.video.eColorFormat, &stride, planes);
1629 pUseBuffer->dataLen = sizeof(void *);
1630 } else {
1631 ret = OMX_ErrorBadParameter;
1632 goto EXIT;
1633 }
1634 } else {
1635 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
1636 ret = OMX_ErrorBadParameter;
1637 goto EXIT;
1638 }
1639
1640 if (nPlane == TWO_PLANE) {
1641 /* Case of Shared Buffer, Only support two PlaneBuffer */
1642 pData->buffer.multiPlaneBuffer.dataBuffer[0] = planes[0].addr;
1643 pData->buffer.multiPlaneBuffer.dataBuffer[1] = planes[1].addr;
1644 #ifdef USE_DMA_BUF
1645 pData->buffer.multiPlaneBuffer.fd[0] = planes[0].fd;
1646 pData->buffer.multiPlaneBuffer.fd[1] = planes[1].fd;
1647 #endif
1648 } else {
1649 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Can not support plane");
1650 ret = OMX_ErrorNotImplemented;
1651 goto EXIT;
1652 }
1653
1654 pData->allocSize = pUseBuffer->allocSize;
1655 pData->dataLen = pUseBuffer->dataLen;
1656 pData->usedDataLen = pUseBuffer->usedDataLen;
1657 pData->remainDataLen = pUseBuffer->remainDataLen;
1658 pData->timeStamp = pUseBuffer->timeStamp;
1659 pData->nFlags = pUseBuffer->nFlags;
1660 pData->pPrivate = pUseBuffer->pPrivate;
1661 pData->bufferHeader = pUseBuffer->bufferHeader;
1662
1663 EXIT:
1664 return ret;
1665 }
1666
1667 OMX_ERRORTYPE Exynos_Shared_DataToANBBuffer(EXYNOS_OMX_DATA *pData, EXYNOS_OMX_DATABUFFER *pUseBuffer, EXYNOS_OMX_BASEPORT *pExynosPort)
1668 {
1669 OMX_ERRORTYPE ret = OMX_ErrorNone;
1670
1671 pUseBuffer->bufferHeader = pData->bufferHeader;
1672 pUseBuffer->allocSize = pData->allocSize;
1673 pUseBuffer->dataLen = pData->dataLen;
1674 pUseBuffer->usedDataLen = pData->usedDataLen;
1675 pUseBuffer->remainDataLen = pData->remainDataLen;
1676 pUseBuffer->timeStamp = pData->timeStamp;
1677 pUseBuffer->nFlags = pData->nFlags;
1678 pUseBuffer->pPrivate = pData->pPrivate;
1679
1680 if ((pUseBuffer->bufferHeader == NULL) ||
1681 (pUseBuffer->bufferHeader->pBuffer == NULL)) {
1682 ret = OMX_ErrorUndefined;
1683 goto EXIT;
1684 }
1685
1686 if (pExynosPort->bIsANBEnabled == OMX_TRUE) {
1687 Exynos_OSAL_UnlockANB(pUseBuffer->bufferHeader->pBuffer);
1688 } else {
1689 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
1690 ret = OMX_ErrorBadParameter;
1691 goto EXIT;
1692 }
1693
1694 EXIT:
1695 return ret;
1696 }
1697 #endif
1698
1699 OMX_ERRORTYPE Exynos_Shared_DataToBuffer(EXYNOS_OMX_DATA *pData, EXYNOS_OMX_DATABUFFER *pUseBuffer)
1700 {
1701 OMX_ERRORTYPE ret = OMX_ErrorNone;
1702
1703 pUseBuffer->bufferHeader = pData->bufferHeader;
1704 pUseBuffer->allocSize = pData->allocSize;
1705 pUseBuffer->dataLen = pData->dataLen;
1706 pUseBuffer->usedDataLen = pData->usedDataLen;
1707 pUseBuffer->remainDataLen = pData->remainDataLen;
1708 pUseBuffer->timeStamp = pData->timeStamp;
1709 pUseBuffer->nFlags = pData->nFlags;
1710 pUseBuffer->pPrivate = pData->pPrivate;
1711
1712 return ret;
1713 }