video_dec: Add ThumbnailMode decoding to h264
[GitHub/LineageOS/android_hardware_samsung_slsi_openmax.git] / component / video / dec / h264 / Exynos_OMX_H264dec.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_H264dec.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
31 #include "Exynos_OMX_Macros.h"
32 #include "Exynos_OMX_Basecomponent.h"
33 #include "Exynos_OMX_Baseport.h"
34 #include "Exynos_OMX_Vdec.h"
35 #include "Exynos_OMX_VdecControl.h"
36 #include "Exynos_OSAL_ETC.h"
37 #include "Exynos_OSAL_Semaphore.h"
38 #include "Exynos_OSAL_Thread.h"
39 #include "library_register.h"
40 #include "Exynos_OMX_H264dec.h"
41 #include "ExynosVideoApi.h"
42 #include "Exynos_OSAL_SharedMemory.h"
43 #include "Exynos_OSAL_Event.h"
44
45 #ifdef USE_ANB
46 #include "Exynos_OSAL_Android.h"
47 #endif
48
49 /* To use CSC_METHOD_HW in EXYNOS OMX, gralloc should allocate physical memory using FIMC */
50 /* It means GRALLOC_USAGE_HW_FIMC1 should be set on Native Window usage */
51 #include "csc.h"
52
53 #undef EXYNOS_LOG_TAG
54 #define EXYNOS_LOG_TAG "EXYNOS_H264_DEC"
55 #define EXYNOS_LOG_OFF
56 //#define EXYNOS_TRACE_ON
57 #include "Exynos_OSAL_Log.h"
58
59 #define H264_DEC_NUM_OF_EXTRA_BUFFERS 7
60
61 //#define ADD_SPS_PPS_I_FRAME
62 //#define FULL_FRAME_SEARCH
63
64 /* H.264 Decoder Supported Levels & profiles */
65 EXYNOS_OMX_VIDEO_PROFILELEVEL supportedAVCProfileLevels[] ={
66 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel1},
67 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel1b},
68 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel11},
69 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel12},
70 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel13},
71 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel2},
72 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel21},
73 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel22},
74 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel3},
75 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel31},
76 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel32},
77 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel4},
78 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel41},
79 {OMX_VIDEO_AVCProfileBaseline, OMX_VIDEO_AVCLevel42},
80
81 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel1},
82 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel1b},
83 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel11},
84 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel12},
85 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel13},
86 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel2},
87 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel21},
88 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel22},
89 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel3},
90 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel31},
91 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel32},
92 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel4},
93 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel41},
94 {OMX_VIDEO_AVCProfileMain, OMX_VIDEO_AVCLevel42},
95
96 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel1},
97 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel1b},
98 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel11},
99 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel12},
100 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel13},
101 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel2},
102 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel21},
103 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel22},
104 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel3},
105 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel31},
106 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel32},
107 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel4},
108 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel41},
109 {OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCLevel42}};
110
111 OMX_ERRORTYPE H264CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent);
112
113 static OMX_ERRORTYPE GetCodecInputPrivateData(OMX_PTR codecBuffer, void *pVirtAddr, OMX_U32 *dataSize)
114 {
115 OMX_ERRORTYPE ret = OMX_ErrorNone;
116
117 EXIT:
118 return ret;
119 }
120
121 static OMX_ERRORTYPE GetCodecOutputPrivateData(OMX_PTR codecBuffer, void *addr[], int size[])
122 {
123 OMX_ERRORTYPE ret = OMX_ErrorNone;
124 ExynosVideoBuffer *pCodecBuffer;
125
126 if (codecBuffer == NULL) {
127 ret = OMX_ErrorBadParameter;
128 goto EXIT;
129 }
130
131 pCodecBuffer = (ExynosVideoBuffer *)codecBuffer;
132
133 if (addr != NULL) {
134 addr[0] = pCodecBuffer->planes[0].addr;
135 addr[1] = pCodecBuffer->planes[1].addr;
136 addr[2] = pCodecBuffer->planes[2].addr;
137 }
138
139 if (size != NULL) {
140 size[0] = pCodecBuffer->planes[0].allocSize;
141 size[1] = pCodecBuffer->planes[1].allocSize;
142 size[2] = pCodecBuffer->planes[2].allocSize;
143 }
144
145 EXIT:
146 return ret;
147 }
148
149 int Check_H264_Frame(
150 OMX_U8 *pInputStream,
151 OMX_U32 buffSize,
152 OMX_U32 flag,
153 OMX_BOOL bPreviousFrameEOF,
154 OMX_BOOL *pbEndOfFrame)
155 {
156 OMX_U32 preFourByte = (OMX_U32)-1;
157 int accessUnitSize = 0;
158 int frameTypeBoundary = 0;
159 int nextNaluSize = 0;
160 int naluStart = 0;
161
162 if (bPreviousFrameEOF == OMX_TRUE)
163 naluStart = 0;
164 else
165 naluStart = 1;
166
167 while (1) {
168 int inputOneByte = 0;
169
170 if (accessUnitSize == (int)buffSize)
171 goto EXIT;
172
173 inputOneByte = *(pInputStream++);
174 accessUnitSize += 1;
175
176 if (preFourByte == 0x00000001 || (preFourByte << 8) == 0x00000100) {
177 int naluType = inputOneByte & 0x1F;
178
179 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "NaluType : %d", naluType);
180 if (naluStart == 0) {
181 #ifdef ADD_SPS_PPS_I_FRAME
182 if (naluType == 1 || naluType == 5)
183 #else
184 if (naluType == 1 || naluType == 5 || naluType == 7 || naluType == 8)
185 #endif
186 naluStart = 1;
187 } else {
188 #ifdef OLD_DETECT
189 frameTypeBoundary = (8 - naluType) & (naluType - 10); //AUD(9)
190 #else
191 if (naluType == 9)
192 frameTypeBoundary = -2;
193 #endif
194 if (naluType == 1 || naluType == 5) {
195 if (accessUnitSize == (int)buffSize) {
196 accessUnitSize--;
197 goto EXIT;
198 }
199 inputOneByte = *pInputStream++;
200 accessUnitSize += 1;
201
202 if (inputOneByte >= 0x80)
203 frameTypeBoundary = -1;
204 }
205 if (frameTypeBoundary < 0) {
206 break;
207 }
208 }
209
210 }
211 preFourByte = (preFourByte << 8) + inputOneByte;
212 }
213
214 *pbEndOfFrame = OMX_TRUE;
215 nextNaluSize = -5;
216 if (frameTypeBoundary == -1)
217 nextNaluSize = -6;
218 if (preFourByte != 0x00000001)
219 nextNaluSize++;
220 return (accessUnitSize + nextNaluSize);
221
222 EXIT:
223 *pbEndOfFrame = OMX_FALSE;
224
225 return accessUnitSize;
226 }
227
228 static OMX_BOOL Check_H264_StartCode(
229 OMX_U8 *pInputStream,
230 OMX_U32 streamSize)
231 {
232 if (streamSize < 4) {
233 return OMX_FALSE;
234 }
235
236 if ((pInputStream[0] == 0x00) &&
237 (pInputStream[1] == 0x00) &&
238 (pInputStream[2] == 0x00) &&
239 (pInputStream[3] != 0x00) &&
240 ((pInputStream[3] >> 3) == 0x00)) {
241 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "NaluType : %d, 0x%x, 0x%x, 0x%x", (pInputStream[4] & 0x1F), pInputStream[3], pInputStream[4], pInputStream[5]);
242 return OMX_TRUE;
243 } else if ((pInputStream[0] == 0x00) &&
244 (pInputStream[1] == 0x00) &&
245 (pInputStream[2] != 0x00) &&
246 ((pInputStream[2] >> 3) == 0x00)) {
247 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "NaluType : %d, 0x%x, 0x%x, 0x%x", (pInputStream[3] & 0x1F), pInputStream[2], pInputStream[3], pInputStream[4]);
248 return OMX_TRUE;
249 } else {
250 return OMX_FALSE;
251 }
252 }
253
254 OMX_ERRORTYPE H264CodecOpen(EXYNOS_H264DEC_HANDLE *pH264Dec)
255 {
256 OMX_ERRORTYPE ret = OMX_ErrorNone;
257 ExynosVideoDecOps *pDecOps = NULL;
258 ExynosVideoDecBufferOps *pInbufOps = NULL;
259 ExynosVideoDecBufferOps *pOutbufOps = NULL;
260
261 FunctionIn();
262
263 if (pH264Dec == NULL) {
264 ret = OMX_ErrorBadParameter;
265 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorBadParameter, Line:%d", __LINE__);
266 goto EXIT;
267 }
268
269 /* alloc ops structure */
270 pDecOps = (ExynosVideoDecOps *)Exynos_OSAL_Malloc(sizeof(ExynosVideoDecOps));
271 pInbufOps = (ExynosVideoDecBufferOps *)Exynos_OSAL_Malloc(sizeof(ExynosVideoDecBufferOps));
272 pOutbufOps = (ExynosVideoDecBufferOps *)Exynos_OSAL_Malloc(sizeof(ExynosVideoDecBufferOps));
273
274 if ((pDecOps == NULL) || (pInbufOps == NULL) || (pOutbufOps == NULL)) {
275 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to allocate decoder ops buffer");
276 ret = OMX_ErrorInsufficientResources;
277 goto EXIT;
278 }
279
280 pH264Dec->hMFCH264Handle.pDecOps = pDecOps;
281 pH264Dec->hMFCH264Handle.pInbufOps = pInbufOps;
282 pH264Dec->hMFCH264Handle.pOutbufOps = pOutbufOps;
283
284 /* function pointer mapping */
285 pDecOps->nSize = sizeof(ExynosVideoDecOps);
286 pInbufOps->nSize = sizeof(ExynosVideoDecBufferOps);
287 pOutbufOps->nSize = sizeof(ExynosVideoDecBufferOps);
288
289 Exynos_Video_Register_Decoder(pDecOps, pInbufOps, pOutbufOps);
290
291 /* check mandatory functions for decoder ops */
292 if ((pDecOps->Init == NULL) || (pDecOps->Finalize == NULL) ||
293 (pDecOps->Get_ActualBufferCount == NULL) || (pDecOps->Set_FrameTag == NULL) ||
294 #ifdef USE_S3D_SUPPORT
295 (pDecOps->Enable_SEIParsing == NULL) || (pDecOps->Get_FramePackingInfo == NULL) ||
296 #endif
297 (pDecOps->Get_FrameTag == NULL)) {
298 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Mandatory functions must be supplied");
299 ret = OMX_ErrorInsufficientResources;
300 goto EXIT;
301 }
302
303 /* check mandatory functions for buffer ops */
304 if ((pInbufOps->Setup == NULL) || (pOutbufOps->Setup == NULL) ||
305 (pInbufOps->Run == NULL) || (pOutbufOps->Run == NULL) ||
306 (pInbufOps->Stop == NULL) || (pOutbufOps->Stop == NULL) ||
307 (pInbufOps->Enqueue == NULL) || (pOutbufOps->Enqueue == NULL) ||
308 (pInbufOps->Dequeue == NULL) || (pOutbufOps->Dequeue == NULL)) {
309 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Mandatory functions must be supplied");
310 ret = OMX_ErrorInsufficientResources;
311 goto EXIT;
312 }
313
314 /* alloc context, open, querycap */
315 #ifdef USE_DMA_BUF
316 pH264Dec->hMFCH264Handle.hMFCHandle = pH264Dec->hMFCH264Handle.pDecOps->Init(V4L2_MEMORY_DMABUF);
317 #else
318 pH264Dec->hMFCH264Handle.hMFCHandle = pH264Dec->hMFCH264Handle.pDecOps->Init(V4L2_MEMORY_USERPTR);
319 #endif
320 if (pH264Dec->hMFCH264Handle.hMFCHandle == NULL) {
321 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to allocate context buffer");
322 ret = OMX_ErrorInsufficientResources;
323 goto EXIT;
324 }
325
326 #ifdef USE_S3D_SUPPORT
327 /* S3D: Enable SEI parsing to check Frame Packing */
328 if (pDecOps->Enable_SEIParsing(pH264Dec->hMFCH264Handle.hMFCHandle) != VIDEO_ERROR_NONE) {
329 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Enable SEI Parsing");
330 ret = OMX_ErrorInsufficientResources;
331 goto EXIT;
332 }
333 #endif
334
335 ret = OMX_ErrorNone;
336
337 EXIT:
338 if (ret != OMX_ErrorNone) {
339 if (pDecOps != NULL) {
340 Exynos_OSAL_Free(pDecOps);
341 pH264Dec->hMFCH264Handle.pDecOps = NULL;
342 }
343 if (pInbufOps != NULL) {
344 Exynos_OSAL_Free(pInbufOps);
345 pH264Dec->hMFCH264Handle.pInbufOps = NULL;
346 }
347 if (pOutbufOps != NULL) {
348 Exynos_OSAL_Free(pOutbufOps);
349 pH264Dec->hMFCH264Handle.pOutbufOps = NULL;
350 }
351 }
352
353 FunctionOut();
354
355 return ret;
356 }
357
358 OMX_ERRORTYPE H264CodecClose(EXYNOS_H264DEC_HANDLE *pH264Dec)
359 {
360 OMX_ERRORTYPE ret = OMX_ErrorNone;
361 void *hMFCHandle = NULL;
362 ExynosVideoDecOps *pDecOps = NULL;
363 ExynosVideoDecBufferOps *pInbufOps = NULL;
364 ExynosVideoDecBufferOps *pOutbufOps = NULL;
365
366 FunctionIn();
367
368 if (pH264Dec == NULL) {
369 ret = OMX_ErrorBadParameter;
370 goto EXIT;
371 }
372
373 hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
374 pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
375 pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
376 pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
377
378 if (hMFCHandle != NULL) {
379 pDecOps->Finalize(hMFCHandle);
380 pH264Dec->hMFCH264Handle.hMFCHandle = NULL;
381 }
382 if (pOutbufOps != NULL) {
383 Exynos_OSAL_Free(pOutbufOps);
384 pH264Dec->hMFCH264Handle.pOutbufOps = NULL;
385 }
386 if (pInbufOps != NULL) {
387 Exynos_OSAL_Free(pInbufOps);
388 pH264Dec->hMFCH264Handle.pInbufOps = NULL;
389 }
390 if (pDecOps != NULL) {
391 Exynos_OSAL_Free(pDecOps);
392 pH264Dec->hMFCH264Handle.pDecOps = NULL;
393 }
394
395 ret = OMX_ErrorNone;
396
397 EXIT:
398 FunctionOut();
399
400 return ret;
401 }
402
403 OMX_ERRORTYPE H264CodecStart(OMX_COMPONENTTYPE *pOMXComponent, OMX_U32 nPortIndex)
404 {
405 OMX_ERRORTYPE ret = OMX_ErrorNone;
406 void *hMFCHandle = NULL;
407 ExynosVideoDecOps *pDecOps = NULL;
408 ExynosVideoDecBufferOps *pInbufOps = NULL;
409 ExynosVideoDecBufferOps *pOutbufOps = NULL;
410 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
411 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
412
413 FunctionIn();
414
415 if (pOMXComponent == NULL) {
416 ret = OMX_ErrorBadParameter;
417 goto EXIT;
418 }
419
420 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)((EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate)->hComponentHandle;
421 if (pVideoDec == NULL) {
422 ret = OMX_ErrorBadParameter;
423 goto EXIT;
424 }
425
426 pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
427 if (pH264Dec == NULL) {
428 ret = OMX_ErrorBadParameter;
429 goto EXIT;
430 }
431
432 hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
433 pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
434 pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
435 pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
436
437 if (nPortIndex == INPUT_PORT_INDEX)
438 pInbufOps->Run(hMFCHandle);
439 else if (nPortIndex == OUTPUT_PORT_INDEX)
440 pOutbufOps->Run(hMFCHandle);
441
442 ret = OMX_ErrorNone;
443
444 EXIT:
445 FunctionOut();
446
447 return ret;
448 }
449
450 OMX_ERRORTYPE H264CodecStop(OMX_COMPONENTTYPE *pOMXComponent, OMX_U32 nPortIndex)
451 {
452 OMX_ERRORTYPE ret = OMX_ErrorNone;
453 void *hMFCHandle = NULL;
454 ExynosVideoDecOps *pDecOps = NULL;
455 ExynosVideoDecBufferOps *pInbufOps = NULL;
456 ExynosVideoDecBufferOps *pOutbufOps = NULL;
457 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
458 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
459
460 FunctionIn();
461
462 if (pOMXComponent == NULL) {
463 ret = OMX_ErrorBadParameter;
464 goto EXIT;
465 }
466
467 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)((EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate)->hComponentHandle;
468 if (pVideoDec == NULL) {
469 ret = OMX_ErrorBadParameter;
470 goto EXIT;
471 }
472 pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
473 if (pH264Dec == NULL) {
474 ret = OMX_ErrorBadParameter;
475 goto EXIT;
476 }
477
478 hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
479 pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
480 pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
481 pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
482
483 if ((nPortIndex == INPUT_PORT_INDEX) && (pInbufOps != NULL))
484 pInbufOps->Stop(hMFCHandle);
485 else if ((nPortIndex == OUTPUT_PORT_INDEX) && (pOutbufOps != NULL))
486 pOutbufOps->Stop(hMFCHandle);
487
488 ret = OMX_ErrorNone;
489
490 EXIT:
491 FunctionOut();
492
493 return ret;
494 }
495
496 OMX_ERRORTYPE H264CodecOutputBufferProcessRun(OMX_COMPONENTTYPE *pOMXComponent, OMX_U32 nPortIndex)
497 {
498 OMX_ERRORTYPE ret = OMX_ErrorNone;
499 void *hMFCHandle = NULL;
500 ExynosVideoDecOps *pDecOps = NULL;
501 ExynosVideoDecBufferOps *pInbufOps = NULL;
502 ExynosVideoDecBufferOps *pOutbufOps = NULL;
503 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
504 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
505
506 FunctionIn();
507
508 if (pOMXComponent == NULL) {
509 ret = OMX_ErrorBadParameter;
510 goto EXIT;
511 }
512
513 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)((EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate)->hComponentHandle;
514 if (pVideoDec == NULL) {
515 ret = OMX_ErrorBadParameter;
516 goto EXIT;
517 }
518 pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
519 if (pH264Dec == NULL) {
520 ret = OMX_ErrorBadParameter;
521 goto EXIT;
522 }
523
524 hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
525 pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
526 pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
527 pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
528
529 if (nPortIndex == INPUT_PORT_INDEX) {
530 if (pH264Dec->bSourceStart == OMX_FALSE) {
531 Exynos_OSAL_SignalSet(pH264Dec->hSourceStartEvent);
532 Exynos_OSAL_SleepMillisec(0);
533 }
534 }
535
536 if (nPortIndex == OUTPUT_PORT_INDEX) {
537 if (pH264Dec->bDestinationStart == OMX_FALSE) {
538 Exynos_OSAL_SignalSet(pH264Dec->hDestinationStartEvent);
539 Exynos_OSAL_SleepMillisec(0);
540 }
541 }
542
543 ret = OMX_ErrorNone;
544
545 EXIT:
546 FunctionOut();
547
548 return ret;
549 }
550
551 OMX_ERRORTYPE H264CodecRegistCodecBuffers(
552 OMX_COMPONENTTYPE *pOMXComponent,
553 OMX_U32 nPortIndex,
554 OMX_U32 nBufferCnt)
555 {
556 OMX_ERRORTYPE ret = OMX_ErrorNone;
557 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
558 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
559 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
560 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
561 CODEC_DEC_BUFFER **ppCodecBuffer = NULL;
562 ExynosVideoDecBufferOps *pBufOps = NULL;
563 ExynosVideoPlane *pPlanes = NULL;
564
565 OMX_U32 nPlaneCnt = 0;
566 int i, j;
567
568 FunctionIn();
569
570 if (nPortIndex == INPUT_PORT_INDEX) {
571 ppCodecBuffer = &(pVideoDec->pMFCDecInputBuffer[0]);
572 pBufOps = pH264Dec->hMFCH264Handle.pInbufOps;
573 } else {
574 ppCodecBuffer = &(pVideoDec->pMFCDecOutputBuffer[0]);
575 pBufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
576 }
577 nPlaneCnt = pExynosComponent->pExynosPort[nPortIndex].nPlaneCnt;
578
579 pPlanes = (ExynosVideoPlane *)Exynos_OSAL_Malloc(sizeof(ExynosVideoPlane) * nPlaneCnt);
580 if (pPlanes == NULL) {
581 ret = OMX_ErrorInsufficientResources;
582 goto EXIT;
583 }
584
585 /* Register buffer */
586 for (i = 0; i < nBufferCnt; i++) {
587 for (j = 0; j < nPlaneCnt; j++) {
588 pPlanes[j].addr = ppCodecBuffer[i]->pVirAddr[j];
589 pPlanes[j].fd = ppCodecBuffer[i]->fd[j];
590 pPlanes[j].allocSize = ppCodecBuffer[i]->bufferSize[j];
591 }
592
593 if (pBufOps->Register(hMFCHandle, pPlanes, nPlaneCnt) != VIDEO_ERROR_NONE) {
594 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "PORT[%d]: Failed to Register buffer", nPortIndex);
595 ret = OMX_ErrorInsufficientResources;
596 Exynos_OSAL_Free(pPlanes);
597 goto EXIT;
598 }
599 }
600
601 Exynos_OSAL_Free(pPlanes);
602
603 ret = OMX_ErrorNone;
604
605 EXIT:
606 FunctionOut();
607
608 return ret;
609 }
610
611 OMX_ERRORTYPE H264CodecReconfigAllBuffers(
612 OMX_COMPONENTTYPE *pOMXComponent,
613 OMX_U32 nPortIndex)
614 {
615 OMX_ERRORTYPE ret = OMX_ErrorNone;
616 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
617 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
618 EXYNOS_OMX_BASEPORT *pExynosPort = &pExynosComponent->pExynosPort[nPortIndex];
619 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
620 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
621 ExynosVideoDecBufferOps *pBufferOps = NULL;
622
623 FunctionIn();
624
625 if ((nPortIndex == INPUT_PORT_INDEX) &&
626 (pH264Dec->bSourceStart == OMX_TRUE)) {
627 ret = OMX_ErrorNotImplemented;
628 goto EXIT;
629 } else if ((nPortIndex == OUTPUT_PORT_INDEX) &&
630 (pH264Dec->bDestinationStart == OMX_TRUE)) {
631 pBufferOps = pH264Dec->hMFCH264Handle.pOutbufOps;
632
633 if (pExynosPort->bufferProcessType & BUFFER_COPY) {
634 /**********************************/
635 /* Codec Buffer Free & Unregister */
636 /**********************************/
637 Exynos_Free_CodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX);
638 Exynos_CodecBufferReset(pExynosComponent, OUTPUT_PORT_INDEX);
639 pBufferOps->Clear_RegisteredBuffer(hMFCHandle);
640 pBufferOps->Cleanup_Buffer(hMFCHandle);
641
642 /******************************************************/
643 /* V4L2 Destnation Setup for DPB Buffer Number Change */
644 /******************************************************/
645 H264CodecDstSetup(pOMXComponent);
646
647 pVideoDec->bReconfigDPB = OMX_FALSE;
648 } else if (pExynosPort->bufferProcessType & BUFFER_SHARE) {
649 /**********************************/
650 /* Codec Buffer Unregister */
651 /**********************************/
652 pBufferOps->Clear_RegisteredBuffer(hMFCHandle);
653 pBufferOps->Cleanup_Buffer(hMFCHandle);
654 }
655 } else {
656 ret = OMX_ErrorBadParameter;
657 goto EXIT;
658 }
659
660 EXIT:
661 FunctionOut();
662
663 return ret;
664 }
665
666 OMX_ERRORTYPE H264CodecEnQueueAllBuffer(OMX_COMPONENTTYPE *pOMXComponent, OMX_U32 nPortIndex)
667 {
668 OMX_ERRORTYPE ret = OMX_ErrorNone;
669 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
670 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
671 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
672 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
673 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
674 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
675 int i, nOutbufs;
676
677 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
678 ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
679 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
680
681 FunctionIn();
682
683 if ((nPortIndex != INPUT_PORT_INDEX) && (nPortIndex != OUTPUT_PORT_INDEX)) {
684 ret = OMX_ErrorBadPortIndex;
685 goto EXIT;
686 }
687
688 if ((nPortIndex == INPUT_PORT_INDEX) &&
689 (pH264Dec->bSourceStart == OMX_TRUE)) {
690 Exynos_CodecBufferReset(pExynosComponent, INPUT_PORT_INDEX);
691
692 for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) {
693 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecInputBuffer[%d]: 0x%x", i, pVideoDec->pMFCDecInputBuffer[i]);
694 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecInputBuffer[%d]->pVirAddr[0]: 0x%x", i, pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[0]);
695
696 Exynos_CodecBufferEnQueue(pExynosComponent, INPUT_PORT_INDEX, pVideoDec->pMFCDecInputBuffer[i]);
697 }
698
699 pInbufOps->Clear_Queue(hMFCHandle);
700 } else if ((nPortIndex == OUTPUT_PORT_INDEX) &&
701 (pH264Dec->bDestinationStart == OMX_TRUE)) {
702 Exynos_CodecBufferReset(pExynosComponent, OUTPUT_PORT_INDEX);
703
704 for (i = 0; i < pH264Dec->hMFCH264Handle.maxDPBNum; i++) {
705 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecOutputBuffer[%d]: 0x%x", i, pVideoDec->pMFCDecOutputBuffer[i]);
706 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoDec->pMFCDecOutputBuffer[%d]->pVirAddr[0]: 0x%x", i, pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0]);
707
708 Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, pVideoDec->pMFCDecOutputBuffer[i]);
709 }
710 pOutbufOps->Clear_Queue(hMFCHandle);
711 }
712
713 EXIT:
714 FunctionOut();
715
716 return ret;
717 }
718
719 #ifdef USE_S3D_SUPPORT
720 OMX_BOOL H264CodecCheckFramePacking(OMX_COMPONENTTYPE *pOMXComponent)
721 {
722 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
723 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
724 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
725 ExynosVideoFramePacking framePacking;
726 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
727 OMX_BOOL ret = OMX_FALSE;
728
729 /* Get Frame packing information*/
730 if (pDecOps->Get_FramePackingInfo(pH264Dec->hMFCH264Handle.hMFCHandle, &framePacking) != VIDEO_ERROR_NONE) {
731 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Get Frame Packing Information");
732 ret = OMX_FALSE;
733 goto EXIT;
734 }
735
736 if (framePacking.available) {
737 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "arrangement ID: 0x%08x", framePacking.arrangement_id);
738 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "arrangement_type: %d", framePacking.arrangement_type);
739 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "content_interpretation_type: %d", framePacking.content_interpretation_type);
740 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "current_frame_is_frame0_flag: %d", framePacking.current_frame_is_frame0_flag);
741 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "spatial_flipping_flag: %d", framePacking.spatial_flipping_flag);
742 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "fr0X:%d fr0Y:%d fr0X:%d fr0Y:%d", framePacking.frame0_grid_pos_x,
743 framePacking.frame0_grid_pos_y, framePacking.frame1_grid_pos_x, framePacking.frame1_grid_pos_y);
744
745 pH264Dec->hMFCH264Handle.S3DFPArgmtType = (EXYNOS_OMX_FPARGMT_TYPE) framePacking.arrangement_type;
746 /** Send Port Settings changed call back - output color format change */
747 (*(pExynosComponent->pCallbacks->EventHandler))
748 (pOMXComponent,
749 pExynosComponent->callbackData,
750 OMX_EventS3DInformation, /* The command was completed */
751 OMX_TRUE, /* S3D is enabled */
752 (OMX_S32)pH264Dec->hMFCH264Handle.S3DFPArgmtType, /* S3D FPArgmtType */
753 NULL);
754
755 Exynos_OSAL_SleepMillisec(0);
756 } else {
757 pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_NONE;
758 }
759
760 ret = OMX_TRUE;
761
762 EXIT:
763 return ret;
764 }
765 #endif
766
767 OMX_ERRORTYPE H264CodecCheckResolutionChange(OMX_COMPONENTTYPE *pOMXComponent)
768 {
769 OMX_ERRORTYPE ret = OMX_ErrorNone;
770 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
771 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
772 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
773 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
774 EXYNOS_OMX_BASEPORT *pInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
775 EXYNOS_OMX_BASEPORT *pOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
776 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
777 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
778
779 FunctionIn();
780 /* get geometry for output */
781 Exynos_OSAL_Memset(&pH264Dec->hMFCH264Handle.codecOutbufConf, 0, sizeof(ExynosVideoGeometry));
782 if (pOutbufOps->Get_Geometry(hMFCHandle, &pH264Dec->hMFCH264Handle.codecOutbufConf) != VIDEO_ERROR_NONE) {
783 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to get geometry for parsed header info");
784 ret = OMX_ErrorInsufficientResources;
785 goto EXIT;
786 }
787
788 /* get dpb count */
789 pH264Dec->hMFCH264Handle.maxDPBNum = pDecOps->Get_ActualBufferCount(hMFCHandle);
790 if (pVideoDec->bThumbnailMode == OMX_FALSE) {
791 pH264Dec->hMFCH264Handle.maxDPBNum += EXTRA_DPB_NUM;
792 } else {
793 pH264Dec->hMFCH264Handle.maxDPBNum += PLATFORM_DISPLAY_BUFFER;
794 }
795 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "H264CodecSetup nOutbufs: %d", pH264Dec->hMFCH264Handle.maxDPBNum);
796
797 pH264Dec->hMFCH264Handle.bConfiguredMFCSrc = OMX_TRUE;
798
799 pOutputPort->cropRectangle.nTop = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nTop;
800 pOutputPort->cropRectangle.nLeft = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nLeft;
801 pOutputPort->cropRectangle.nWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nWidth;
802 pOutputPort->cropRectangle.nHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nHeight;
803
804 if (pVideoDec->bReconfigDPB == OMX_TRUE)
805 pVideoDec->nSavedDPBCnt = pOutputPort->portDefinition.nBufferCountActual;
806
807 if (pOutputPort->bufferProcessType & BUFFER_COPY) {
808 if ((pVideoDec->bReconfigDPB) ||
809 (pInputPort->portDefinition.format.video.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth) ||
810 (pInputPort->portDefinition.format.video.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight)) {
811 pOutputPort->exceptionFlag = NEED_PORT_DISABLE;
812
813 pInputPort->portDefinition.format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
814 pInputPort->portDefinition.format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
815 pInputPort->portDefinition.format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
816 pInputPort->portDefinition.format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
817
818 Exynos_UpdateFrameSize(pOMXComponent);
819
820 /** Send Port Settings changed call back **/
821 (*(pExynosComponent->pCallbacks->EventHandler))
822 (pOMXComponent,
823 pExynosComponent->callbackData,
824 OMX_EventPortSettingsChanged, /* The command was completed */
825 OMX_DirOutput, /* This is the port index */
826 0,
827 NULL);
828 }
829 } else if (pOutputPort->bufferProcessType & BUFFER_SHARE) {
830 if ((pVideoDec->bReconfigDPB) ||
831 (pInputPort->portDefinition.format.video.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth) ||
832 (pInputPort->portDefinition.format.video.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight) ||
833 (pOutputPort->portDefinition.nBufferCountActual != pH264Dec->hMFCH264Handle.maxDPBNum)) {
834 pOutputPort->exceptionFlag = NEED_PORT_DISABLE;
835
836 pInputPort->portDefinition.format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
837 pInputPort->portDefinition.format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
838 pInputPort->portDefinition.format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
839 pInputPort->portDefinition.format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
840
841 pOutputPort->portDefinition.nBufferCountActual = pH264Dec->hMFCH264Handle.maxDPBNum - PLATFORM_DISPLAY_BUFFER;
842 pOutputPort->portDefinition.nBufferCountMin = pH264Dec->hMFCH264Handle.maxDPBNum - PLATFORM_DISPLAY_BUFFER;
843
844 Exynos_UpdateFrameSize(pOMXComponent);
845
846 /** Send Port Settings changed call back **/
847 (*(pExynosComponent->pCallbacks->EventHandler))
848 (pOMXComponent,
849 pExynosComponent->callbackData,
850 OMX_EventPortSettingsChanged, /* The command was completed */
851 OMX_DirOutput, /* This is the port index */
852 0,
853 NULL);
854 }
855 }
856 if ((pVideoDec->bReconfigDPB == OMX_TRUE) ||
857 (pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth != pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nWidth) ||
858 (pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight != pH264Dec->hMFCH264Handle.codecOutbufConf.cropRect.nHeight)) {
859 /* Check Crop */
860 pInputPort->portDefinition.format.video.nFrameWidth = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth;
861 pInputPort->portDefinition.format.video.nFrameHeight = pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight;
862 pInputPort->portDefinition.format.video.nStride = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameWidth + 15) & (~15));
863 pInputPort->portDefinition.format.video.nSliceHeight = ((pH264Dec->hMFCH264Handle.codecOutbufConf.nFrameHeight + 15) & (~15));
864 Exynos_UpdateFrameSize(pOMXComponent);
865
866 /** Send crop info call back **/
867 (*(pExynosComponent->pCallbacks->EventHandler))
868 (pOMXComponent,
869 pExynosComponent->callbackData,
870 OMX_EventPortSettingsChanged, /* The command was completed */
871 OMX_DirOutput, /* This is the port index */
872 OMX_IndexConfigCommonOutputCrop,
873 NULL);
874 }
875
876 ret = OMX_ErrorNone;
877
878 EXIT:
879 FunctionOut();
880
881 return ret;
882 }
883
884 OMX_ERRORTYPE H264CodecSrcSetup(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcInputData)
885 {
886 OMX_ERRORTYPE ret = OMX_ErrorNone;
887 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
888 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
889 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
890 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
891 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
892 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
893 OMX_U32 oneFrameSize = pSrcInputData->dataLen;
894
895 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
896 ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
897 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
898 ExynosVideoGeometry bufferConf;
899 OMX_U32 inputBufferNumber = 0;
900 int i;
901
902 FunctionIn();
903
904 if ((oneFrameSize <= 0) && (pSrcInputData->nFlags & OMX_BUFFERFLAG_EOS)) {
905 BYPASS_BUFFER_INFO *pBufferInfo = (BYPASS_BUFFER_INFO *)Exynos_OSAL_Malloc(sizeof(BYPASS_BUFFER_INFO));
906 if (pBufferInfo == NULL) {
907 ret = OMX_ErrorInsufficientResources;
908 goto EXIT;
909 }
910
911 pBufferInfo->nFlags = pSrcInputData->nFlags;
912 pBufferInfo->timeStamp = pSrcInputData->timeStamp;
913 ret = Exynos_OSAL_Queue(&pH264Dec->bypassBufferInfoQ, (void *)pBufferInfo);
914 Exynos_OSAL_SignalSet(pH264Dec->hDestinationStartEvent);
915
916 ret = OMX_ErrorNone;
917 goto EXIT;
918 }
919
920 if (pVideoDec->bThumbnailMode == OMX_TRUE) {
921 pDecOps->Set_IFrameDecoding(hMFCHandle);
922 }
923
924 if ((pDecOps->Enable_DTSMode != NULL) &&
925 (pVideoDec->bDTSMode == OMX_TRUE))
926 pDecOps->Enable_DTSMode(hMFCHandle);
927
928 /* input buffer info */
929 Exynos_OSAL_Memset(&bufferConf, 0, sizeof(bufferConf));
930 bufferConf.eCompressionFormat = VIDEO_CODING_AVC;
931 pInbufOps->Set_Shareable(hMFCHandle);
932 if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
933 bufferConf.nSizeImage = pExynosInputPort->portDefinition.format.video.nFrameWidth
934 * pExynosInputPort->portDefinition.format.video.nFrameHeight * 3 / 2;
935 } else if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
936 bufferConf.nSizeImage = DEFAULT_MFC_INPUT_BUFFER_SIZE;
937 }
938 bufferConf.nPlaneCnt = pExynosInputPort->nPlaneCnt;
939 inputBufferNumber = MAX_INPUTBUFFER_NUM_DYNAMIC;
940
941 /* should be done before prepare input buffer */
942 if (pInbufOps->Enable_Cacheable(hMFCHandle) != VIDEO_ERROR_NONE) {
943 ret = OMX_ErrorInsufficientResources;
944 goto EXIT;
945 }
946
947 /* set input buffer geometry */
948 if (pInbufOps->Set_Geometry(hMFCHandle, &bufferConf) != VIDEO_ERROR_NONE) {
949 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to set geometry for input buffer");
950 ret = OMX_ErrorInsufficientResources;
951 goto EXIT;
952 }
953
954 /* setup input buffer */
955 if (pInbufOps->Setup(hMFCHandle, inputBufferNumber) != VIDEO_ERROR_NONE) {
956 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup input buffer");
957 ret = OMX_ErrorInsufficientResources;
958 goto EXIT;
959 }
960
961 /* set output geometry */
962 Exynos_OSAL_Memset(&bufferConf, 0, sizeof(bufferConf));
963
964 #ifdef USE_DUALDPB_MODE
965 switch (pExynosOutputPort->portDefinition.format.video.eColorFormat) {
966 case OMX_COLOR_FormatYUV420SemiPlanar:
967 bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12;
968 break;
969 case OMX_COLOR_FormatYUV420Planar:
970 bufferConf.eColorFormat = VIDEO_COLORFORMAT_I420;
971 break;
972 case OMX_SEC_COLOR_FormatYVU420Planar:
973 bufferConf.eColorFormat = VIDEO_COLORFORMAT_YV12;
974 break;
975 case OMX_SEC_COLOR_FormatNV21Linear:
976 bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV21;
977 break;
978 case OMX_SEC_COLOR_FormatNV12Tiled:
979 bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
980 break;
981 default:
982 bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
983 break;
984 }
985
986 if (bufferConf.eColorFormat != VIDEO_COLORFORMAT_NV12_TILED) {
987 if ((pDecOps->Enable_DualDPBMode != NULL) &&
988 (pDecOps->Enable_DualDPBMode(hMFCHandle) == VIDEO_ERROR_NONE)) {
989 pVideoDec->bDualDPBMode = OMX_TRUE;
990 pExynosOutputPort->nPlaneCnt = Exynos_OSAL_GetPlaneCount(pExynosOutputPort->portDefinition.format.video.eColorFormat);
991 } else {
992 bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
993 pExynosOutputPort->nPlaneCnt = MFC_DEFAULT_OUTPUT_BUFFER_PLANE;
994 }
995 }
996 pH264Dec->hMFCH264Handle.MFCOutputColorType = bufferConf.eColorFormat;
997 #else
998 pH264Dec->hMFCH264Handle.MFCOutputColorType = bufferConf.eColorFormat = VIDEO_COLORFORMAT_NV12_TILED;
999 #endif
1000 bufferConf.nPlaneCnt = pExynosOutputPort->nPlaneCnt;
1001 if (pOutbufOps->Set_Geometry(hMFCHandle, &bufferConf) != VIDEO_ERROR_NONE) {
1002 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to set geometry for output buffer");
1003 ret = OMX_ErrorInsufficientResources;
1004 goto EXIT;
1005 }
1006
1007 /* input buffer enqueue for header parsing */
1008 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "oneFrameSize: %d", oneFrameSize);
1009 OMX_U32 nAllocLen[MAX_BUFFER_PLANE] = {pSrcInputData->bufferHeader->nAllocLen, 0, 0};
1010 if (pInbufOps->ExtensionEnqueue(hMFCHandle,
1011 (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.dataBuffer,
1012 (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.fd,
1013 (unsigned int *)nAllocLen, (unsigned int *)&oneFrameSize,
1014 pExynosInputPort->nPlaneCnt, pSrcInputData->bufferHeader) != VIDEO_ERROR_NONE) {
1015 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to enqueue input buffer for header parsing");
1016 // ret = OMX_ErrorInsufficientResources;
1017 ret = (OMX_ERRORTYPE)OMX_ErrorCodecInit;
1018 goto EXIT;
1019 }
1020
1021 /* start header parsing */
1022 if (pInbufOps->Run(hMFCHandle) != VIDEO_ERROR_NONE) {
1023 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to run input buffer for header parsing");
1024 ret = OMX_ErrorCodecInit;
1025 goto EXIT;
1026 }
1027
1028 ret = H264CodecCheckResolutionChange(pOMXComponent);
1029 if (ret != OMX_ErrorNone) {
1030 H264CodecStop(pOMXComponent, INPUT_PORT_INDEX);
1031 pInbufOps->Cleanup_Buffer(hMFCHandle);
1032 goto EXIT;
1033 }
1034
1035 Exynos_OSAL_SleepMillisec(0);
1036 ret = OMX_ErrorInputDataDecodeYet;
1037 H264CodecStop(pOMXComponent, INPUT_PORT_INDEX);
1038
1039 EXIT:
1040 FunctionOut();
1041
1042 return ret;
1043 }
1044
1045 OMX_ERRORTYPE H264CodecDstSetup(OMX_COMPONENTTYPE *pOMXComponent)
1046 {
1047 OMX_ERRORTYPE ret = OMX_ErrorNone;
1048 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1049 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1050 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1051 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
1052 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1053 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1054
1055 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
1056 ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
1057 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
1058
1059 int i, nOutbufs;
1060
1061 OMX_U32 nAllocLen[MAX_BUFFER_PLANE] = {0, 0, 0};
1062 OMX_U32 dataLen[MAX_BUFFER_PLANE] = {0, 0, 0};
1063
1064 FunctionIn();
1065
1066 for (i = 0; i < pExynosOutputPort->nPlaneCnt; i++)
1067 nAllocLen[i] = pH264Dec->hMFCH264Handle.codecOutbufConf.nAlignPlaneSize[i];
1068
1069 pOutbufOps->Set_Shareable(hMFCHandle);
1070
1071 if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
1072 /* should be done before prepare output buffer */
1073 if (pOutbufOps->Enable_Cacheable(hMFCHandle) != VIDEO_ERROR_NONE) {
1074 ret = OMX_ErrorInsufficientResources;
1075 goto EXIT;
1076 }
1077
1078 /* get dpb count */
1079 nOutbufs = pH264Dec->hMFCH264Handle.maxDPBNum;
1080 if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
1081 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
1082 ret = OMX_ErrorInsufficientResources;
1083 goto EXIT;
1084 }
1085
1086 ret = Exynos_Allocate_CodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX, nOutbufs, nAllocLen);
1087 if (ret != OMX_ErrorNone)
1088 goto EXIT;
1089
1090 ret = H264CodecRegistCodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX, nOutbufs);
1091 if (ret != OMX_ErrorNone)
1092 goto EXIT;
1093
1094 /* Enqueue output buffer */
1095 for (i = 0; i < nOutbufs; i++) {
1096 pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr,
1097 (unsigned int *)dataLen, pExynosOutputPort->nPlaneCnt, NULL);
1098 }
1099
1100 if (pOutbufOps->Run(hMFCHandle) != VIDEO_ERROR_NONE) {
1101 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to run output buffer");
1102 ret = OMX_ErrorInsufficientResources;
1103 goto EXIT;
1104 }
1105 } else if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
1106 ExynosVideoPlane planes[MAX_BUFFER_PLANE] = {0, 0, 0};
1107 int plane;
1108
1109 /* get dpb count */
1110 nOutbufs = pExynosOutputPort->portDefinition.nBufferCountActual;
1111 if (pOutbufOps->Setup(hMFCHandle, nOutbufs) != VIDEO_ERROR_NONE) {
1112 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to setup output buffer");
1113 ret = OMX_ErrorInsufficientResources;
1114 goto EXIT;
1115 }
1116
1117 /* Register output buffer */
1118 /*************/
1119 /* TBD */
1120 /*************/
1121 #ifdef USE_ANB
1122 if (pExynosOutputPort->bIsANBEnabled == OMX_TRUE) {
1123 for (i = 0; i < pExynosOutputPort->assignedBufferNum; i++) {
1124 for (plane = 0; plane < pExynosOutputPort->nPlaneCnt; plane++) {
1125 planes[plane].fd = pExynosOutputPort->extendBufferHeader[i].buf_fd[plane];
1126 planes[plane].addr = pExynosOutputPort->extendBufferHeader[i].pYUVBuf[plane];
1127 planes[plane].allocSize = nAllocLen[plane];
1128 }
1129
1130 if (pOutbufOps->Register(hMFCHandle, planes, pExynosOutputPort->nPlaneCnt) != VIDEO_ERROR_NONE) {
1131 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Register output buffer");
1132 ret = OMX_ErrorInsufficientResources;
1133 goto EXIT;
1134 }
1135 pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pExynosOutputPort->extendBufferHeader[i].pYUVBuf,
1136 (unsigned int *)dataLen, pExynosOutputPort->nPlaneCnt, NULL);
1137 }
1138
1139 if (pOutbufOps->Apply_RegisteredBuffer(hMFCHandle) != VIDEO_ERROR_NONE) {
1140 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to Apply output buffer");
1141 ret = OMX_ErrorHardware;
1142 goto EXIT;
1143 }
1144 } else {
1145 ret = OMX_ErrorNotImplemented;
1146 goto EXIT;
1147 }
1148 #else
1149 ret = OMX_ErrorNotImplemented;
1150 goto EXIT;
1151 #endif
1152 }
1153
1154 pH264Dec->hMFCH264Handle.bConfiguredMFCDst = OMX_TRUE;
1155
1156 ret = OMX_ErrorNone;
1157
1158 EXIT:
1159 FunctionOut();
1160
1161 return ret;
1162 }
1163
1164 OMX_ERRORTYPE Exynos_H264Dec_GetParameter(
1165 OMX_IN OMX_HANDLETYPE hComponent,
1166 OMX_IN OMX_INDEXTYPE nParamIndex,
1167 OMX_INOUT OMX_PTR pComponentParameterStructure)
1168 {
1169 OMX_ERRORTYPE ret = OMX_ErrorNone;
1170 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1171 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1172
1173 FunctionIn();
1174
1175 if (hComponent == NULL || pComponentParameterStructure == NULL) {
1176 ret = OMX_ErrorBadParameter;
1177 goto EXIT;
1178 }
1179 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1180 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1181 if (ret != OMX_ErrorNone) {
1182 goto EXIT;
1183 }
1184 if (pOMXComponent->pComponentPrivate == NULL) {
1185 ret = OMX_ErrorBadParameter;
1186 goto EXIT;
1187 }
1188
1189 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1190 if (pExynosComponent->currentState == OMX_StateInvalid ) {
1191 ret = OMX_ErrorInvalidState;
1192 goto EXIT;
1193 }
1194
1195 switch (nParamIndex) {
1196 case OMX_IndexParamVideoAvc:
1197 {
1198 OMX_VIDEO_PARAM_AVCTYPE *pDstAVCComponent = (OMX_VIDEO_PARAM_AVCTYPE *)pComponentParameterStructure;
1199 OMX_VIDEO_PARAM_AVCTYPE *pSrcAVCComponent = NULL;
1200 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1201
1202 ret = Exynos_OMX_Check_SizeVersion(pDstAVCComponent, sizeof(OMX_VIDEO_PARAM_AVCTYPE));
1203 if (ret != OMX_ErrorNone) {
1204 goto EXIT;
1205 }
1206
1207 if (pDstAVCComponent->nPortIndex >= ALL_PORT_NUM) {
1208 ret = OMX_ErrorBadPortIndex;
1209 goto EXIT;
1210 }
1211
1212 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1213 pSrcAVCComponent = &pH264Dec->AVCComponent[pDstAVCComponent->nPortIndex];
1214
1215 Exynos_OSAL_Memcpy(pDstAVCComponent, pSrcAVCComponent, sizeof(OMX_VIDEO_PARAM_AVCTYPE));
1216 }
1217 break;
1218 case OMX_IndexParamStandardComponentRole:
1219 {
1220 OMX_PARAM_COMPONENTROLETYPE *pComponentRole = (OMX_PARAM_COMPONENTROLETYPE *)pComponentParameterStructure;
1221 ret = Exynos_OMX_Check_SizeVersion(pComponentRole, sizeof(OMX_PARAM_COMPONENTROLETYPE));
1222 if (ret != OMX_ErrorNone) {
1223 goto EXIT;
1224 }
1225
1226 Exynos_OSAL_Strcpy((char *)pComponentRole->cRole, EXYNOS_OMX_COMPONENT_H264_DEC_ROLE);
1227 }
1228 break;
1229 case OMX_IndexParamVideoProfileLevelQuerySupported:
1230 {
1231 OMX_VIDEO_PARAM_PROFILELEVELTYPE *pDstProfileLevel = (OMX_VIDEO_PARAM_PROFILELEVELTYPE*)pComponentParameterStructure;
1232 EXYNOS_OMX_VIDEO_PROFILELEVEL *pProfileLevel = NULL;
1233 OMX_U32 maxProfileLevelNum = 0;
1234
1235 ret = Exynos_OMX_Check_SizeVersion(pDstProfileLevel, sizeof(OMX_VIDEO_PARAM_PROFILELEVELTYPE));
1236 if (ret != OMX_ErrorNone) {
1237 goto EXIT;
1238 }
1239
1240 if (pDstProfileLevel->nPortIndex >= ALL_PORT_NUM) {
1241 ret = OMX_ErrorBadPortIndex;
1242 goto EXIT;
1243 }
1244
1245 pProfileLevel = supportedAVCProfileLevels;
1246 maxProfileLevelNum = sizeof(supportedAVCProfileLevels) / sizeof(EXYNOS_OMX_VIDEO_PROFILELEVEL);
1247
1248 if (pDstProfileLevel->nProfileIndex >= maxProfileLevelNum) {
1249 ret = OMX_ErrorNoMore;
1250 goto EXIT;
1251 }
1252
1253 pProfileLevel += pDstProfileLevel->nProfileIndex;
1254 pDstProfileLevel->eProfile = pProfileLevel->profile;
1255 pDstProfileLevel->eLevel = pProfileLevel->level;
1256 }
1257 break;
1258 case OMX_IndexParamVideoProfileLevelCurrent:
1259 {
1260 OMX_VIDEO_PARAM_PROFILELEVELTYPE *pDstProfileLevel = (OMX_VIDEO_PARAM_PROFILELEVELTYPE*)pComponentParameterStructure;
1261 OMX_VIDEO_PARAM_AVCTYPE *pSrcAVCComponent = NULL;
1262 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1263
1264 ret = Exynos_OMX_Check_SizeVersion(pDstProfileLevel, sizeof(OMX_VIDEO_PARAM_PROFILELEVELTYPE));
1265 if (ret != OMX_ErrorNone) {
1266 goto EXIT;
1267 }
1268
1269 if (pDstProfileLevel->nPortIndex >= ALL_PORT_NUM) {
1270 ret = OMX_ErrorBadPortIndex;
1271 goto EXIT;
1272 }
1273
1274 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1275 pSrcAVCComponent = &pH264Dec->AVCComponent[pDstProfileLevel->nPortIndex];
1276
1277 pDstProfileLevel->eProfile = pSrcAVCComponent->eProfile;
1278 pDstProfileLevel->eLevel = pSrcAVCComponent->eLevel;
1279 }
1280 break;
1281 case OMX_IndexParamVideoErrorCorrection:
1282 {
1283 OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE *pDstErrorCorrectionType = (OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE *)pComponentParameterStructure;
1284 OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE *pSrcErrorCorrectionType = NULL;
1285 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1286
1287 ret = Exynos_OMX_Check_SizeVersion(pDstErrorCorrectionType, sizeof(OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE));
1288 if (ret != OMX_ErrorNone) {
1289 goto EXIT;
1290 }
1291
1292 if (pDstErrorCorrectionType->nPortIndex != INPUT_PORT_INDEX) {
1293 ret = OMX_ErrorBadPortIndex;
1294 goto EXIT;
1295 }
1296
1297 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1298 pSrcErrorCorrectionType = &pH264Dec->errorCorrectionType[INPUT_PORT_INDEX];
1299
1300 pDstErrorCorrectionType->bEnableHEC = pSrcErrorCorrectionType->bEnableHEC;
1301 pDstErrorCorrectionType->bEnableResync = pSrcErrorCorrectionType->bEnableResync;
1302 pDstErrorCorrectionType->nResynchMarkerSpacing = pSrcErrorCorrectionType->nResynchMarkerSpacing;
1303 pDstErrorCorrectionType->bEnableDataPartitioning = pSrcErrorCorrectionType->bEnableDataPartitioning;
1304 pDstErrorCorrectionType->bEnableRVLC = pSrcErrorCorrectionType->bEnableRVLC;
1305 }
1306 break;
1307 default:
1308 ret = Exynos_OMX_VideoDecodeGetParameter(hComponent, nParamIndex, pComponentParameterStructure);
1309 break;
1310 }
1311 EXIT:
1312 FunctionOut();
1313
1314 return ret;
1315 }
1316
1317 OMX_ERRORTYPE Exynos_H264Dec_SetParameter(
1318 OMX_IN OMX_HANDLETYPE hComponent,
1319 OMX_IN OMX_INDEXTYPE nIndex,
1320 OMX_IN OMX_PTR pComponentParameterStructure)
1321 {
1322 OMX_ERRORTYPE ret = OMX_ErrorNone;
1323 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1324 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1325
1326 FunctionIn();
1327
1328 if (hComponent == NULL || pComponentParameterStructure == NULL) {
1329 ret = OMX_ErrorBadParameter;
1330 goto EXIT;
1331 }
1332 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1333 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1334 if (ret != OMX_ErrorNone) {
1335 goto EXIT;
1336 }
1337 if (pOMXComponent->pComponentPrivate == NULL) {
1338 ret = OMX_ErrorBadParameter;
1339 goto EXIT;
1340 }
1341
1342 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1343 if (pExynosComponent->currentState == OMX_StateInvalid ) {
1344 ret = OMX_ErrorInvalidState;
1345 goto EXIT;
1346 }
1347
1348 switch (nIndex) {
1349 case OMX_IndexParamVideoAvc:
1350 {
1351 OMX_VIDEO_PARAM_AVCTYPE *pDstAVCComponent = NULL;
1352 OMX_VIDEO_PARAM_AVCTYPE *pSrcAVCComponent = (OMX_VIDEO_PARAM_AVCTYPE *)pComponentParameterStructure;
1353 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1354
1355 ret = Exynos_OMX_Check_SizeVersion(pSrcAVCComponent, sizeof(OMX_VIDEO_PARAM_AVCTYPE));
1356 if (ret != OMX_ErrorNone) {
1357 goto EXIT;
1358 }
1359
1360 if (pSrcAVCComponent->nPortIndex >= ALL_PORT_NUM) {
1361 ret = OMX_ErrorBadPortIndex;
1362 goto EXIT;
1363 }
1364
1365 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1366 pDstAVCComponent = &pH264Dec->AVCComponent[pSrcAVCComponent->nPortIndex];
1367
1368 Exynos_OSAL_Memcpy(pDstAVCComponent, pSrcAVCComponent, sizeof(OMX_VIDEO_PARAM_AVCTYPE));
1369 }
1370 break;
1371 case OMX_IndexParamStandardComponentRole:
1372 {
1373 OMX_PARAM_COMPONENTROLETYPE *pComponentRole = (OMX_PARAM_COMPONENTROLETYPE*)pComponentParameterStructure;
1374
1375 ret = Exynos_OMX_Check_SizeVersion(pComponentRole, sizeof(OMX_PARAM_COMPONENTROLETYPE));
1376 if (ret != OMX_ErrorNone) {
1377 goto EXIT;
1378 }
1379
1380 if ((pExynosComponent->currentState != OMX_StateLoaded) && (pExynosComponent->currentState != OMX_StateWaitForResources)) {
1381 ret = OMX_ErrorIncorrectStateOperation;
1382 goto EXIT;
1383 }
1384
1385 if (!Exynos_OSAL_Strcmp((char*)pComponentRole->cRole, EXYNOS_OMX_COMPONENT_H264_DEC_ROLE)) {
1386 pExynosComponent->pExynosPort[INPUT_PORT_INDEX].portDefinition.format.video.eCompressionFormat = OMX_VIDEO_CodingAVC;
1387 } else {
1388 ret = OMX_ErrorBadParameter;
1389 goto EXIT;
1390 }
1391 }
1392 break;
1393 case OMX_IndexParamVideoProfileLevelCurrent:
1394 {
1395 OMX_VIDEO_PARAM_PROFILELEVELTYPE *pSrcProfileLevel = (OMX_VIDEO_PARAM_PROFILELEVELTYPE *)pComponentParameterStructure;
1396 OMX_VIDEO_PARAM_AVCTYPE *pDstAVCComponent = NULL;
1397 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1398
1399 ret = Exynos_OMX_Check_SizeVersion(pSrcProfileLevel, sizeof(OMX_VIDEO_PARAM_PROFILELEVELTYPE));
1400 if (ret != OMX_ErrorNone)
1401 goto EXIT;
1402
1403 if (pSrcProfileLevel->nPortIndex >= ALL_PORT_NUM) {
1404 ret = OMX_ErrorBadPortIndex;
1405 goto EXIT;
1406 }
1407
1408 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1409
1410 pDstAVCComponent = &pH264Dec->AVCComponent[pSrcProfileLevel->nPortIndex];
1411 pDstAVCComponent->eProfile = pSrcProfileLevel->eProfile;
1412 pDstAVCComponent->eLevel = pSrcProfileLevel->eLevel;
1413 }
1414 break;
1415 case OMX_IndexParamVideoErrorCorrection:
1416 {
1417 OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE *pSrcErrorCorrectionType = (OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE *)pComponentParameterStructure;
1418 OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE *pDstErrorCorrectionType = NULL;
1419 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1420
1421 ret = Exynos_OMX_Check_SizeVersion(pSrcErrorCorrectionType, sizeof(OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE));
1422 if (ret != OMX_ErrorNone) {
1423 goto EXIT;
1424 }
1425
1426 if (pSrcErrorCorrectionType->nPortIndex != INPUT_PORT_INDEX) {
1427 ret = OMX_ErrorBadPortIndex;
1428 goto EXIT;
1429 }
1430
1431 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1432 pDstErrorCorrectionType = &pH264Dec->errorCorrectionType[INPUT_PORT_INDEX];
1433
1434 pDstErrorCorrectionType->bEnableHEC = pSrcErrorCorrectionType->bEnableHEC;
1435 pDstErrorCorrectionType->bEnableResync = pSrcErrorCorrectionType->bEnableResync;
1436 pDstErrorCorrectionType->nResynchMarkerSpacing = pSrcErrorCorrectionType->nResynchMarkerSpacing;
1437 pDstErrorCorrectionType->bEnableDataPartitioning = pSrcErrorCorrectionType->bEnableDataPartitioning;
1438 pDstErrorCorrectionType->bEnableRVLC = pSrcErrorCorrectionType->bEnableRVLC;
1439 }
1440 break;
1441 default:
1442 ret = Exynos_OMX_VideoDecodeSetParameter(hComponent, nIndex, pComponentParameterStructure);
1443 break;
1444 }
1445 EXIT:
1446 FunctionOut();
1447
1448 return ret;
1449 }
1450
1451 OMX_ERRORTYPE Exynos_H264Dec_GetConfig(
1452 OMX_HANDLETYPE hComponent,
1453 OMX_INDEXTYPE nIndex,
1454 OMX_PTR pComponentConfigStructure)
1455 {
1456 OMX_ERRORTYPE ret = OMX_ErrorNone;
1457 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1458 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1459
1460 FunctionIn();
1461
1462 if (hComponent == NULL) {
1463 ret = OMX_ErrorBadParameter;
1464 goto EXIT;
1465 }
1466 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1467 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1468 if (ret != OMX_ErrorNone) {
1469 goto EXIT;
1470 }
1471 if (pOMXComponent->pComponentPrivate == NULL) {
1472 ret = OMX_ErrorBadParameter;
1473 goto EXIT;
1474 }
1475 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1476 if (pComponentConfigStructure == NULL) {
1477 ret = OMX_ErrorBadParameter;
1478 goto EXIT;
1479 }
1480 if (pExynosComponent->currentState == OMX_StateInvalid) {
1481 ret = OMX_ErrorInvalidState;
1482 goto EXIT;
1483 }
1484
1485 switch (nIndex) {
1486 case OMX_IndexConfigCommonOutputCrop:
1487 {
1488 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1489 OMX_CONFIG_RECTTYPE *pSrcRectType = NULL;
1490 OMX_CONFIG_RECTTYPE *pDstRectType = NULL;
1491 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1492
1493 if (pH264Dec->hMFCH264Handle.bConfiguredMFCSrc == OMX_FALSE) {
1494 ret = OMX_ErrorNotReady;
1495 break;
1496 }
1497
1498 pDstRectType = (OMX_CONFIG_RECTTYPE *)pComponentConfigStructure;
1499
1500 if ((pDstRectType->nPortIndex != INPUT_PORT_INDEX) &&
1501 (pDstRectType->nPortIndex != OUTPUT_PORT_INDEX)) {
1502 ret = OMX_ErrorBadPortIndex;
1503 goto EXIT;
1504 }
1505
1506 EXYNOS_OMX_BASEPORT *pExynosPort = &pExynosComponent->pExynosPort[pDstRectType->nPortIndex];
1507
1508 pSrcRectType = &(pExynosPort->cropRectangle);
1509
1510 pDstRectType->nTop = pSrcRectType->nTop;
1511 pDstRectType->nLeft = pSrcRectType->nLeft;
1512 pDstRectType->nHeight = pSrcRectType->nHeight;
1513 pDstRectType->nWidth = pSrcRectType->nWidth;
1514 }
1515 break;
1516 #ifdef USE_S3D_SUPPORT
1517 case OMX_IndexVendorS3DMode:
1518 {
1519 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
1520 OMX_U32 *pS3DMode = NULL;
1521 pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1522
1523 pS3DMode = (OMX_U32 *)pComponentConfigStructure;
1524 *pS3DMode = (OMX_U32) pH264Dec->hMFCH264Handle.S3DFPArgmtType;
1525 }
1526 break;
1527 #endif
1528 default:
1529 ret = Exynos_OMX_VideoDecodeGetConfig(hComponent, nIndex, pComponentConfigStructure);
1530 break;
1531 }
1532
1533 EXIT:
1534 FunctionOut();
1535
1536 return ret;
1537 }
1538
1539 OMX_ERRORTYPE Exynos_H264Dec_SetConfig(
1540 OMX_HANDLETYPE hComponent,
1541 OMX_INDEXTYPE nIndex,
1542 OMX_PTR pComponentConfigStructure)
1543 {
1544 OMX_ERRORTYPE ret = OMX_ErrorNone;
1545 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1546 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1547
1548 FunctionIn();
1549
1550 if (hComponent == NULL) {
1551 ret = OMX_ErrorBadParameter;
1552 goto EXIT;
1553 }
1554 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1555 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1556 if (ret != OMX_ErrorNone) {
1557 goto EXIT;
1558 }
1559 if (pOMXComponent->pComponentPrivate == NULL) {
1560 ret = OMX_ErrorBadParameter;
1561 goto EXIT;
1562 }
1563 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1564 if (pComponentConfigStructure == NULL) {
1565 ret = OMX_ErrorBadParameter;
1566 goto EXIT;
1567 }
1568 if (pExynosComponent->currentState == OMX_StateInvalid) {
1569 ret = OMX_ErrorInvalidState;
1570 goto EXIT;
1571 }
1572
1573 switch (nIndex) {
1574 default:
1575 ret = Exynos_OMX_VideoDecodeSetConfig(hComponent, nIndex, pComponentConfigStructure);
1576 break;
1577 }
1578
1579 EXIT:
1580 FunctionOut();
1581
1582 return ret;
1583 }
1584
1585 OMX_ERRORTYPE Exynos_H264Dec_GetExtensionIndex(
1586 OMX_IN OMX_HANDLETYPE hComponent,
1587 OMX_IN OMX_STRING cParameterName,
1588 OMX_OUT OMX_INDEXTYPE *pIndexType)
1589 {
1590 OMX_ERRORTYPE ret = OMX_ErrorNone;
1591 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1592 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1593
1594 FunctionIn();
1595
1596 if (hComponent == NULL) {
1597 ret = OMX_ErrorBadParameter;
1598 goto EXIT;
1599 }
1600 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
1601 ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE));
1602 if (ret != OMX_ErrorNone) {
1603 goto EXIT;
1604 }
1605 if (pOMXComponent->pComponentPrivate == NULL) {
1606 ret = OMX_ErrorBadParameter;
1607 goto EXIT;
1608 }
1609 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1610 if ((cParameterName == NULL) || (pIndexType == NULL)) {
1611 ret = OMX_ErrorBadParameter;
1612 goto EXIT;
1613 }
1614 if (pExynosComponent->currentState == OMX_StateInvalid) {
1615 ret = OMX_ErrorInvalidState;
1616 goto EXIT;
1617 }
1618
1619 #ifdef USE_S3D_SUPPORT
1620 if (Exynos_OSAL_Strcmp(cParameterName, EXYNOS_INDEX_PARAM_GET_S3D) == 0) {
1621 *pIndexType = OMX_IndexVendorS3DMode;
1622 ret = OMX_ErrorNone;
1623 goto EXIT;
1624 }
1625 #endif
1626
1627 ret = Exynos_OMX_VideoDecodeGetExtensionIndex(hComponent, cParameterName, pIndexType);
1628
1629 EXIT:
1630 FunctionOut();
1631
1632 return ret;
1633 }
1634
1635 OMX_ERRORTYPE Exynos_H264Dec_ComponentRoleEnum(
1636 OMX_HANDLETYPE hComponent,
1637 OMX_U8 *cRole,
1638 OMX_U32 nIndex)
1639 {
1640 OMX_ERRORTYPE ret = OMX_ErrorNone;
1641 OMX_COMPONENTTYPE *pOMXComponent = NULL;
1642 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
1643
1644 FunctionIn();
1645
1646 if ((hComponent == NULL) || (cRole == NULL)) {
1647 ret = OMX_ErrorBadParameter;
1648 goto EXIT;
1649 }
1650 if (nIndex == (MAX_COMPONENT_ROLE_NUM-1)) {
1651 Exynos_OSAL_Strcpy((char *)cRole, EXYNOS_OMX_COMPONENT_H264_DEC_ROLE);
1652 ret = OMX_ErrorNone;
1653 } else {
1654 ret = OMX_ErrorNoMore;
1655 }
1656
1657 EXIT:
1658 FunctionOut();
1659
1660 return ret;
1661 }
1662
1663 /* MFC Init */
1664 OMX_ERRORTYPE Exynos_H264Dec_Init(OMX_COMPONENTTYPE *pOMXComponent)
1665 {
1666 OMX_ERRORTYPE ret = OMX_ErrorNone;
1667 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1668 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1669 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1670 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1671 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
1672 OMX_PTR hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
1673
1674 ExynosVideoDecOps *pDecOps = NULL;
1675 ExynosVideoDecBufferOps *pInbufOps = NULL;
1676 ExynosVideoDecBufferOps *pOutbufOps = NULL;
1677
1678 CSC_METHOD csc_method = CSC_METHOD_SW;
1679 int i, plane;
1680
1681 FunctionIn();
1682
1683 pH264Dec->hMFCH264Handle.bConfiguredMFCSrc = OMX_FALSE;
1684 pH264Dec->hMFCH264Handle.bConfiguredMFCDst = OMX_FALSE;
1685 pExynosComponent->bUseFlagEOF = OMX_TRUE;
1686 pExynosComponent->bSaveFlagEOS = OMX_FALSE;
1687 pExynosComponent->bBehaviorEOS = OMX_FALSE;
1688
1689 /* H.264 Codec Open */
1690 ret = H264CodecOpen(pH264Dec);
1691 if (ret != OMX_ErrorNone) {
1692 goto EXIT;
1693 }
1694
1695 pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
1696 pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
1697 pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
1698
1699 pExynosInputPort->nPlaneCnt = MFC_DEFAULT_INPUT_BUFFER_PLANE;
1700 if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
1701 OMX_U32 nPlaneSize[MAX_BUFFER_PLANE] = {DEFAULT_MFC_INPUT_BUFFER_SIZE, 0, 0};
1702 Exynos_OSAL_SemaphoreCreate(&pExynosInputPort->codecSemID);
1703 Exynos_OSAL_QueueCreate(&pExynosInputPort->codecBufferQ, MAX_QUEUE_ELEMENTS);
1704
1705 ret = Exynos_Allocate_CodecBuffers(pOMXComponent, INPUT_PORT_INDEX, MFC_INPUT_BUFFER_NUM_MAX, nPlaneSize);
1706 if (ret != OMX_ErrorNone)
1707 goto EXIT;
1708
1709 for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++)
1710 Exynos_CodecBufferEnQueue(pExynosComponent, INPUT_PORT_INDEX, pVideoDec->pMFCDecInputBuffer[i]);
1711 } else if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
1712 /*************/
1713 /* TBD */
1714 /*************/
1715 /* Does not require any actions. */
1716 }
1717
1718 pExynosOutputPort->nPlaneCnt = MFC_DEFAULT_OUTPUT_BUFFER_PLANE;
1719 if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
1720 Exynos_OSAL_SemaphoreCreate(&pExynosOutputPort->codecSemID);
1721 Exynos_OSAL_QueueCreate(&pExynosOutputPort->codecBufferQ, MAX_QUEUE_ELEMENTS);
1722 } else if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
1723 /*************/
1724 /* TBD */
1725 /*************/
1726 /* Does not require any actions. */
1727 }
1728
1729 pH264Dec->bSourceStart = OMX_FALSE;
1730 Exynos_OSAL_SignalCreate(&pH264Dec->hSourceStartEvent);
1731 pH264Dec->bDestinationStart = OMX_FALSE;
1732 Exynos_OSAL_SignalCreate(&pH264Dec->hDestinationStartEvent);
1733
1734 Exynos_OSAL_Memset(pExynosComponent->timeStamp, -19771003, sizeof(OMX_TICKS) * MAX_TIMESTAMP);
1735 Exynos_OSAL_Memset(pExynosComponent->nFlags, 0, sizeof(OMX_U32) * MAX_FLAGS);
1736 pH264Dec->hMFCH264Handle.indexTimestamp = 0;
1737 pH264Dec->hMFCH264Handle.outputIndexTimestamp = 0;
1738
1739 pExynosComponent->getAllDelayBuffer = OMX_FALSE;
1740
1741 Exynos_OSAL_QueueCreate(&pH264Dec->bypassBufferInfoQ, QUEUE_ELEMENTS);
1742
1743 #ifdef USE_CSC_HW
1744 csc_method = CSC_METHOD_HW;
1745 #endif
1746 if (pVideoDec->bDRMPlayerMode == OMX_TRUE) {
1747 pVideoDec->csc_handle = csc_init(CSC_METHOD_HW);
1748 csc_set_hw_property(pVideoDec->csc_handle, CSC_HW_PROPERTY_FIXED_NODE, 2);
1749 csc_set_hw_property(pVideoDec->csc_handle, CSC_HW_PROPERTY_MODE_DRM, pVideoDec->bDRMPlayerMode);
1750 } else {
1751 pVideoDec->csc_handle = csc_init(csc_method);
1752 }
1753
1754 if (pVideoDec->csc_handle == NULL) {
1755 ret = OMX_ErrorInsufficientResources;
1756 goto EXIT;
1757 }
1758 pVideoDec->csc_set_format = OMX_FALSE;
1759
1760 EXIT:
1761 FunctionOut();
1762
1763 return ret;
1764 }
1765
1766 /* MFC Terminate */
1767 OMX_ERRORTYPE Exynos_H264Dec_Terminate(OMX_COMPONENTTYPE *pOMXComponent)
1768 {
1769 OMX_ERRORTYPE ret = OMX_ErrorNone;
1770 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1771 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1772 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1773 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1774 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1775 OMX_PTR hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
1776
1777 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
1778 ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
1779 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
1780
1781 int i, plane;
1782
1783 FunctionIn();
1784
1785 if (pVideoDec->csc_handle != NULL) {
1786 csc_deinit(pVideoDec->csc_handle);
1787 pVideoDec->csc_handle = NULL;
1788 }
1789
1790 Exynos_OSAL_QueueTerminate(&pH264Dec->bypassBufferInfoQ);
1791
1792 Exynos_OSAL_SignalTerminate(pH264Dec->hDestinationStartEvent);
1793 pH264Dec->hDestinationStartEvent = NULL;
1794 pH264Dec->bDestinationStart = OMX_FALSE;
1795 Exynos_OSAL_SignalTerminate(pH264Dec->hSourceStartEvent);
1796 pH264Dec->hSourceStartEvent = NULL;
1797 pH264Dec->bSourceStart = OMX_FALSE;
1798
1799 if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
1800 Exynos_Free_CodecBuffers(pOMXComponent, OUTPUT_PORT_INDEX);
1801 Exynos_OSAL_QueueTerminate(&pExynosOutputPort->codecBufferQ);
1802 Exynos_OSAL_SemaphoreTerminate(pExynosOutputPort->codecSemID);
1803 } else if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
1804 /*************/
1805 /* TBD */
1806 /*************/
1807 /* Does not require any actions. */
1808 }
1809
1810 if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
1811 Exynos_Free_CodecBuffers(pOMXComponent, INPUT_PORT_INDEX);
1812 Exynos_OSAL_QueueTerminate(&pExynosInputPort->codecBufferQ);
1813 Exynos_OSAL_SemaphoreTerminate(pExynosInputPort->codecSemID);
1814 } else if (pExynosInputPort->bufferProcessType & BUFFER_SHARE) {
1815 /*************/
1816 /* TBD */
1817 /*************/
1818 /* Does not require any actions. */
1819 }
1820 H264CodecClose(pH264Dec);
1821
1822 Exynos_ResetAllPortConfig(pOMXComponent);
1823
1824 EXIT:
1825 FunctionOut();
1826
1827 return ret;
1828 }
1829
1830 OMX_ERRORTYPE Exynos_H264Dec_SrcIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcInputData)
1831 {
1832 OMX_ERRORTYPE ret = OMX_ErrorNone;
1833 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1834 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1835 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
1836 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
1837 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1838 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1839
1840 OMX_BUFFERHEADERTYPE tempBufferHeader;
1841 void *pPrivate = NULL;
1842
1843 OMX_U32 oneFrameSize = pSrcInputData->dataLen;
1844 OMX_BOOL bInStartCode = OMX_FALSE;
1845
1846 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
1847 ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
1848 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
1849 ExynosVideoErrorType codecReturn = VIDEO_ERROR_NONE;
1850
1851 int i;
1852
1853 FunctionIn();
1854
1855 if (pH264Dec->hMFCH264Handle.bConfiguredMFCSrc == OMX_FALSE) {
1856 ret = H264CodecSrcSetup(pOMXComponent, pSrcInputData);
1857 goto EXIT;
1858 }
1859 if (pH264Dec->hMFCH264Handle.bConfiguredMFCDst == OMX_FALSE) {
1860 ret = H264CodecDstSetup(pOMXComponent);
1861 }
1862
1863 if (((pVideoDec->bDRMPlayerMode == OMX_TRUE) ||
1864 ((bInStartCode = Check_H264_StartCode(pSrcInputData->buffer.singlePlaneBuffer.dataBuffer, oneFrameSize)) == OMX_TRUE)) ||
1865 ((pSrcInputData->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS)) {
1866 pExynosComponent->timeStamp[pH264Dec->hMFCH264Handle.indexTimestamp] = pSrcInputData->timeStamp;
1867 pExynosComponent->nFlags[pH264Dec->hMFCH264Handle.indexTimestamp] = pSrcInputData->nFlags;
1868 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "input timestamp %lld us (%.2f secs), Tag: %d, nFlags: 0x%x", pSrcInputData->timeStamp, pSrcInputData->timeStamp / 1E6, pH264Dec->hMFCH264Handle.indexTimestamp, pSrcInputData->nFlags);
1869 pDecOps->Set_FrameTag(hMFCHandle, pH264Dec->hMFCH264Handle.indexTimestamp);
1870 pH264Dec->hMFCH264Handle.indexTimestamp++;
1871 pH264Dec->hMFCH264Handle.indexTimestamp %= MAX_TIMESTAMP;
1872 #ifdef USE_QOS_CTRL
1873 if ((pVideoDec->bQosChanged == OMX_TRUE) &&
1874 (pDecOps->Set_QosRatio != NULL)) {
1875 pDecOps->Set_QosRatio(hMFCHandle, pVideoDec->nQosRatio);
1876 pVideoDec->bQosChanged = OMX_FALSE;
1877 }
1878 #endif
1879 /* queue work for input buffer */
1880 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "oneFrameSize: %d, bufferHeader: 0x%x, dataBuffer: 0x%x", oneFrameSize, pSrcInputData->bufferHeader, pSrcInputData->buffer.singlePlaneBuffer.dataBuffer);
1881 OMX_U32 nAllocLen[MAX_BUFFER_PLANE] = {pSrcInputData->bufferHeader->nAllocLen, 0, 0};
1882
1883 if (pExynosInputPort->bufferProcessType == BUFFER_COPY) {
1884 tempBufferHeader.nFlags = pSrcInputData->nFlags;
1885 tempBufferHeader.nTimeStamp = pSrcInputData->timeStamp;
1886 pPrivate = (void *)&tempBufferHeader;
1887 } else {
1888 pPrivate = (void *)pSrcInputData->bufferHeader;
1889 }
1890 codecReturn = pInbufOps->ExtensionEnqueue(hMFCHandle,
1891 (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.dataBuffer,
1892 (unsigned char **)&pSrcInputData->buffer.singlePlaneBuffer.fd,
1893 (unsigned int *)nAllocLen, (unsigned int *)&oneFrameSize,
1894 pExynosInputPort->nPlaneCnt, pPrivate);
1895 if (codecReturn != VIDEO_ERROR_NONE) {
1896 ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
1897 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
1898 goto EXIT;
1899 }
1900 H264CodecStart(pOMXComponent, INPUT_PORT_INDEX);
1901 if (pH264Dec->bSourceStart == OMX_FALSE) {
1902 pH264Dec->bSourceStart = OMX_TRUE;
1903 Exynos_OSAL_SignalSet(pH264Dec->hSourceStartEvent);
1904 Exynos_OSAL_SleepMillisec(0);
1905 }
1906 if (pH264Dec->bDestinationStart == OMX_FALSE) {
1907 pH264Dec->bDestinationStart = OMX_TRUE;
1908 Exynos_OSAL_SignalSet(pH264Dec->hDestinationStartEvent);
1909 Exynos_OSAL_SleepMillisec(0);
1910 }
1911 } else if (bInStartCode == OMX_FALSE) {
1912 ret = OMX_ErrorCorruptedFrame;
1913 goto EXIT;
1914 }
1915
1916 ret = OMX_ErrorNone;
1917
1918 EXIT:
1919 FunctionOut();
1920
1921 return ret;
1922 }
1923
1924 OMX_ERRORTYPE Exynos_H264Dec_SrcOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcOutputData)
1925 {
1926 OMX_ERRORTYPE ret = OMX_ErrorNone;
1927 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1928 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1929 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
1930 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
1931 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
1932 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
1933 ExynosVideoDecBufferOps *pInbufOps = pH264Dec->hMFCH264Handle.pInbufOps;
1934 ExynosVideoBuffer *pVideoBuffer;
1935 ExynosVideoBuffer videoBuffer;
1936
1937 FunctionIn();
1938
1939 if (pInbufOps->ExtensionDequeue(hMFCHandle, &videoBuffer) == VIDEO_ERROR_NONE)
1940 pVideoBuffer = &videoBuffer;
1941 else
1942 pVideoBuffer = NULL;
1943
1944 pSrcOutputData->dataLen = 0;
1945 pSrcOutputData->usedDataLen = 0;
1946 pSrcOutputData->remainDataLen = 0;
1947 pSrcOutputData->nFlags = 0;
1948 pSrcOutputData->timeStamp = 0;
1949 pSrcOutputData->bufferHeader = NULL;
1950
1951 if (pVideoBuffer == NULL) {
1952 pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer = NULL;
1953 pSrcOutputData->allocSize = 0;
1954 pSrcOutputData->pPrivate = NULL;
1955 } else {
1956 pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer = pVideoBuffer->planes[0].addr;
1957 pSrcOutputData->buffer.singlePlaneBuffer.fd = pVideoBuffer->planes[0].fd;
1958 pSrcOutputData->allocSize = pVideoBuffer->planes[0].allocSize;
1959
1960 if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
1961 int i;
1962 for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) {
1963 if (pSrcOutputData->buffer.singlePlaneBuffer.dataBuffer ==
1964 pVideoDec->pMFCDecInputBuffer[i]->pVirAddr[0]) {
1965 pVideoDec->pMFCDecInputBuffer[i]->dataSize = 0;
1966 pSrcOutputData->pPrivate = pVideoDec->pMFCDecInputBuffer[i];
1967 break;
1968 }
1969 }
1970
1971 if (i >= MFC_INPUT_BUFFER_NUM_MAX) {
1972 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Can not find buffer");
1973 ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
1974 goto EXIT;
1975 }
1976 }
1977
1978 /* For Share Buffer */
1979 if (pExynosInputPort->bufferProcessType == BUFFER_SHARE)
1980 pSrcOutputData->bufferHeader = (OMX_BUFFERHEADERTYPE*)pVideoBuffer->pPrivate;
1981 }
1982
1983 ret = OMX_ErrorNone;
1984
1985 EXIT:
1986 FunctionOut();
1987
1988 return ret;
1989 }
1990
1991 OMX_ERRORTYPE Exynos_H264Dec_DstIn(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pDstInputData)
1992 {
1993 OMX_ERRORTYPE ret = OMX_ErrorNone;
1994 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
1995 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
1996 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
1997 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
1998 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
1999
2000 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
2001 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
2002 ExynosVideoErrorType codecReturn = VIDEO_ERROR_NONE;
2003
2004 OMX_U32 dataLen[MAX_BUFFER_PLANE] = {0, 0, 0};
2005 int i;
2006
2007 FunctionIn();
2008
2009 if (pDstInputData->buffer.multiPlaneBuffer.dataBuffer[0] == NULL) {
2010 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Failed to find input buffer");
2011 ret = OMX_ErrorBadParameter;
2012 goto EXIT;
2013 }
2014
2015 for (i = 0; i < pExynosOutputPort->nPlaneCnt; i++) {
2016 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s : %d => ADDR[%d]: 0x%x", __FUNCTION__, __LINE__, i,
2017 pDstInputData->buffer.multiPlaneBuffer.dataBuffer[i]);
2018 }
2019
2020 if ((pVideoDec->bReconfigDPB == OMX_TRUE) &&
2021 (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) &&
2022 (pExynosOutputPort->exceptionFlag == GENERAL_STATE)) {
2023 ret = H264CodecDstSetup(pOMXComponent);
2024 if (ret != OMX_ErrorNone)
2025 goto EXIT;
2026 pVideoDec->bReconfigDPB = OMX_FALSE;
2027 }
2028
2029 codecReturn = pOutbufOps->Enqueue(hMFCHandle, (unsigned char **)pDstInputData->buffer.multiPlaneBuffer.dataBuffer,
2030 (unsigned int *)dataLen, pExynosOutputPort->nPlaneCnt, pDstInputData->bufferHeader);
2031
2032 if (codecReturn != VIDEO_ERROR_NONE) {
2033 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "%s : %d", __FUNCTION__, __LINE__);
2034 ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
2035 goto EXIT;
2036 }
2037 H264CodecStart(pOMXComponent, OUTPUT_PORT_INDEX);
2038
2039 ret = OMX_ErrorNone;
2040
2041 EXIT:
2042 FunctionOut();
2043
2044 return ret;
2045 }
2046
2047 OMX_ERRORTYPE Exynos_H264Dec_DstOut(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pDstOutputData)
2048 {
2049 OMX_ERRORTYPE ret = OMX_ErrorNone;
2050 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2051 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
2052 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
2053 void *hMFCHandle = pH264Dec->hMFCH264Handle.hMFCHandle;
2054 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
2055 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
2056 ExynosVideoDecOps *pDecOps = pH264Dec->hMFCH264Handle.pDecOps;
2057 ExynosVideoDecBufferOps *pOutbufOps = pH264Dec->hMFCH264Handle.pOutbufOps;
2058 ExynosVideoBuffer *pVideoBuffer = NULL;
2059 ExynosVideoFrameStatusType displayStatus = VIDEO_FRAME_STATUS_UNKNOWN;
2060 ExynosVideoGeometry *bufferGeometry;
2061 DECODE_CODEC_EXTRA_BUFFERINFO *pBufferInfo = NULL;
2062 OMX_S32 indexTimestamp = 0;
2063 int plane;
2064
2065 FunctionIn();
2066
2067 if (pH264Dec->bDestinationStart == OMX_FALSE) {
2068 ret = OMX_ErrorNone;
2069 goto EXIT;
2070 }
2071
2072 while (1) {
2073 pVideoBuffer = pOutbufOps->Dequeue(hMFCHandle);
2074 if (pVideoBuffer == (ExynosVideoBuffer *)VIDEO_ERROR_DQBUF_EIO) {
2075 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "HW is not available");
2076 ret = OMX_ErrorHardware;
2077 goto EXIT;
2078 }
2079
2080 if (pVideoBuffer == NULL) {
2081 ret = OMX_ErrorNone;
2082 goto EXIT;
2083 }
2084 displayStatus = pVideoBuffer->displayStatus;
2085 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "displayStatus: 0x%x", displayStatus);
2086
2087 if ((displayStatus == VIDEO_FRAME_STATUS_DISPLAY_DECODING) ||
2088 (displayStatus == VIDEO_FRAME_STATUS_DISPLAY_ONLY) ||
2089 (displayStatus == VIDEO_FRAME_STATUS_CHANGE_RESOL) ||
2090 (displayStatus == VIDEO_FRAME_STATUS_DECODING_FINISHED) ||
2091 (displayStatus == VIDEO_FRAME_STATUS_ENABLED_S3D) ||
2092 (CHECK_PORT_BEING_FLUSHED(pExynosOutputPort))) {
2093 ret = OMX_ErrorNone;
2094 break;
2095 }
2096 }
2097
2098
2099 #ifdef USE_S3D_SUPPORT
2100 /* Check Whether frame packing information is available */
2101 if ((pH264Dec->hMFCH264Handle.S3DFPArgmtType == OMX_SEC_FPARGMT_INVALID) &&
2102 (pVideoDec->bThumbnailMode == OMX_FALSE) &&
2103 ((displayStatus == VIDEO_FRAME_STATUS_DISPLAY_ONLY) ||
2104 (displayStatus == VIDEO_FRAME_STATUS_DISPLAY_DECODING) ||
2105 (displayStatus == VIDEO_FRAME_STATUS_ENABLED_S3D))) {
2106 if (H264CodecCheckFramePacking(pOMXComponent) != OMX_TRUE) {
2107 ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
2108 goto EXIT;
2109 }
2110 }
2111 #endif
2112
2113 if ((pVideoDec->bThumbnailMode == OMX_FALSE) &&
2114 ((displayStatus == VIDEO_FRAME_STATUS_CHANGE_RESOL) ||
2115 (displayStatus == VIDEO_FRAME_STATUS_ENABLED_S3D))) {
2116 if (pVideoDec->bReconfigDPB != OMX_TRUE) {
2117 pExynosOutputPort->exceptionFlag = NEED_PORT_FLUSH;
2118 pVideoDec->bReconfigDPB = OMX_TRUE;
2119 H264CodecCheckResolutionChange(pOMXComponent);
2120 pVideoDec->csc_set_format = OMX_FALSE;
2121 #ifdef USE_S3D_SUPPORT
2122 pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_INVALID;
2123 #endif
2124 }
2125 ret = OMX_ErrorNone;
2126 goto EXIT;
2127 }
2128
2129 pH264Dec->hMFCH264Handle.outputIndexTimestamp++;
2130 pH264Dec->hMFCH264Handle.outputIndexTimestamp %= MAX_TIMESTAMP;
2131
2132 pDstOutputData->allocSize = pDstOutputData->dataLen = 0;
2133 for (plane = 0; plane < pExynosOutputPort->nPlaneCnt; plane++) {
2134 pDstOutputData->buffer.multiPlaneBuffer.dataBuffer[plane] = pVideoBuffer->planes[plane].addr;
2135 pDstOutputData->buffer.multiPlaneBuffer.fd[plane] = pVideoBuffer->planes[plane].fd;
2136 pDstOutputData->allocSize += pVideoBuffer->planes[plane].allocSize;
2137 pDstOutputData->dataLen += pVideoBuffer->planes[plane].dataSize;
2138 }
2139 pDstOutputData->usedDataLen = 0;
2140 pDstOutputData->pPrivate = pVideoBuffer;
2141 if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
2142 int i = 0;
2143 pDstOutputData->pPrivate = NULL;
2144 for (i = 0; i < MFC_OUTPUT_BUFFER_NUM_MAX; i++) {
2145 if (pDstOutputData->buffer.multiPlaneBuffer.dataBuffer[0] ==
2146 pVideoDec->pMFCDecOutputBuffer[i]->pVirAddr[0]) {
2147 pDstOutputData->pPrivate = pVideoDec->pMFCDecOutputBuffer[i];
2148 break;
2149 }
2150 }
2151
2152 if (pDstOutputData->pPrivate == NULL) {
2153 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Can not find buffer");
2154 ret = (OMX_ERRORTYPE)OMX_ErrorCodecDecode;
2155 goto EXIT;
2156 }
2157 }
2158
2159 /* For Share Buffer */
2160 pDstOutputData->bufferHeader = (OMX_BUFFERHEADERTYPE *)pVideoBuffer->pPrivate;
2161
2162 pBufferInfo = (DECODE_CODEC_EXTRA_BUFFERINFO *)pDstOutputData->extInfo;
2163 bufferGeometry = &pH264Dec->hMFCH264Handle.codecOutbufConf;
2164 pBufferInfo->imageWidth = bufferGeometry->nFrameWidth;
2165 pBufferInfo->imageHeight = bufferGeometry->nFrameHeight;
2166 switch (bufferGeometry->eColorFormat) {
2167 case VIDEO_COLORFORMAT_NV12:
2168 pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420SemiPlanar;
2169 break;
2170 #ifdef USE_DUALDPB_MODE
2171 case VIDEO_COLORFORMAT_I420:
2172 pBufferInfo->ColorFormat = OMX_COLOR_FormatYUV420Planar;
2173 break;
2174 case VIDEO_COLORFORMAT_YV12:
2175 pBufferInfo->ColorFormat = OMX_SEC_COLOR_FormatYVU420Planar;
2176 break;
2177 case VIDEO_COLORFORMAT_NV21:
2178 pBufferInfo->ColorFormat = OMX_SEC_COLOR_FormatNV21Linear;
2179 break;
2180 #endif
2181 case VIDEO_COLORFORMAT_NV12_TILED:
2182 default:
2183 pBufferInfo->ColorFormat = OMX_SEC_COLOR_FormatNV12Tiled;
2184 break;
2185 }
2186
2187 indexTimestamp = pDecOps->Get_FrameTag(hMFCHandle);
2188 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "out indexTimestamp: %d", indexTimestamp);
2189 if ((indexTimestamp < 0) || (indexTimestamp >= MAX_TIMESTAMP)) {
2190 if ((pExynosComponent->checkTimeStamp.needSetStartTimeStamp != OMX_TRUE) &&
2191 (pExynosComponent->checkTimeStamp.needCheckStartTimeStamp != OMX_TRUE)) {
2192 if (indexTimestamp == INDEX_AFTER_EOS) {
2193 pDstOutputData->timeStamp = 0x00;
2194 pDstOutputData->nFlags = 0x00;
2195 } else {
2196 pDstOutputData->timeStamp = pExynosComponent->timeStamp[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
2197 pDstOutputData->nFlags = pExynosComponent->nFlags[pH264Dec->hMFCH264Handle.outputIndexTimestamp];
2198 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "missing out indexTimestamp: %d", indexTimestamp);
2199 }
2200 } else {
2201 pDstOutputData->timeStamp = 0x00;
2202 pDstOutputData->nFlags = 0x00;
2203 }
2204 } else {
2205 /* For timestamp correction. if mfc support frametype detect */
2206 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "disp_pic_frame_type: %d", pVideoBuffer->frameType);
2207
2208 /* NEED TIMESTAMP REORDER */
2209 if (pVideoDec->bDTSMode == OMX_TRUE) {
2210 if ((pVideoBuffer->frameType == VIDEO_FRAME_I) ||
2211 ((pVideoBuffer->frameType == VIDEO_FRAME_OTHERS) &&
2212 ((pExynosComponent->nFlags[indexTimestamp] & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS)) ||
2213 (pExynosComponent->checkTimeStamp.needCheckStartTimeStamp == OMX_TRUE))
2214 pH264Dec->hMFCH264Handle.outputIndexTimestamp = indexTimestamp;
2215 else
2216 indexTimestamp = pH264Dec->hMFCH264Handle.outputIndexTimestamp;
2217 }
2218
2219 pDstOutputData->timeStamp = pExynosComponent->timeStamp[indexTimestamp];
2220 pDstOutputData->nFlags = pExynosComponent->nFlags[indexTimestamp];
2221
2222 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "timestamp %lld us (%.2f secs), indexTimestamp: %d, nFlags: 0x%x", pDstOutputData->timeStamp, pDstOutputData->timeStamp / 1E6, indexTimestamp, pDstOutputData->nFlags);
2223 }
2224
2225 if ((displayStatus == VIDEO_FRAME_STATUS_DECODING_FINISHED) ||
2226 ((pDstOutputData->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS)) {
2227 Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "displayStatus:%d, nFlags0x%x", displayStatus, pDstOutputData->nFlags);
2228 pDstOutputData->remainDataLen = 0;
2229
2230 if (((pDstOutputData->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) &&
2231 (pExynosComponent->bBehaviorEOS == OMX_TRUE)) {
2232 pDstOutputData->remainDataLen = bufferGeometry->nFrameWidth * bufferGeometry->nFrameHeight * 3 / 2;
2233 pExynosComponent->bBehaviorEOS = OMX_FALSE;
2234 }
2235 } else {
2236 pDstOutputData->remainDataLen = bufferGeometry->nFrameWidth * bufferGeometry->nFrameHeight * 3 / 2;
2237 }
2238
2239 ret = OMX_ErrorNone;
2240
2241 EXIT:
2242 FunctionOut();
2243
2244 return ret;
2245 }
2246
2247 OMX_ERRORTYPE Exynos_H264Dec_srcInputBufferProcess(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcInputData)
2248 {
2249 OMX_ERRORTYPE ret = OMX_ErrorNone;
2250 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2251 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
2252 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
2253
2254 FunctionIn();
2255
2256 if ((!CHECK_PORT_ENABLED(pExynosInputPort)) || (!CHECK_PORT_POPULATED(pExynosInputPort))) {
2257 ret = OMX_ErrorNone;
2258 goto EXIT;
2259 }
2260 if (OMX_FALSE == Exynos_Check_BufferProcess_State(pExynosComponent, INPUT_PORT_INDEX)) {
2261 ret = OMX_ErrorNone;
2262 goto EXIT;
2263 }
2264
2265 ret = Exynos_H264Dec_SrcIn(pOMXComponent, pSrcInputData);
2266 if ((ret != OMX_ErrorNone) &&
2267 (ret != OMX_ErrorInputDataDecodeYet) &&
2268 (ret != OMX_ErrorCorruptedFrame)) {
2269 pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent,
2270 pExynosComponent->callbackData,
2271 OMX_EventError, ret, 0, NULL);
2272 }
2273
2274 EXIT:
2275 FunctionOut();
2276
2277 return ret;
2278 }
2279
2280 OMX_ERRORTYPE Exynos_H264Dec_srcOutputBufferProcess(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pSrcOutputData)
2281 {
2282 OMX_ERRORTYPE ret = OMX_ErrorNone;
2283 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2284 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
2285 EXYNOS_OMX_BASEPORT *pExynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
2286
2287 FunctionIn();
2288
2289 if ((!CHECK_PORT_ENABLED(pExynosInputPort)) || (!CHECK_PORT_POPULATED(pExynosInputPort))) {
2290 ret = OMX_ErrorNone;
2291 goto EXIT;
2292 }
2293
2294 if (pExynosInputPort->bufferProcessType & BUFFER_COPY) {
2295 if (OMX_FALSE == Exynos_Check_BufferProcess_State(pExynosComponent, INPUT_PORT_INDEX)) {
2296 ret = OMX_ErrorNone;
2297 goto EXIT;
2298 }
2299 }
2300 if ((pH264Dec->bSourceStart == OMX_FALSE) &&
2301 (!CHECK_PORT_BEING_FLUSHED(pExynosInputPort))) {
2302 Exynos_OSAL_SignalWait(pH264Dec->hSourceStartEvent, DEF_MAX_WAIT_TIME);
2303 Exynos_OSAL_SignalReset(pH264Dec->hSourceStartEvent);
2304 }
2305
2306 ret = Exynos_H264Dec_SrcOut(pOMXComponent, pSrcOutputData);
2307 if ((ret != OMX_ErrorNone) && (pExynosComponent->currentState == OMX_StateExecuting)) {
2308 pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent,
2309 pExynosComponent->callbackData,
2310 OMX_EventError, ret, 0, NULL);
2311 }
2312
2313 EXIT:
2314 FunctionOut();
2315
2316 return ret;
2317 }
2318
2319 OMX_ERRORTYPE Exynos_H264Dec_dstInputBufferProcess(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pDstInputData)
2320 {
2321 OMX_ERRORTYPE ret = OMX_ErrorNone;
2322 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2323 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
2324 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
2325
2326 FunctionIn();
2327
2328 if ((!CHECK_PORT_ENABLED(pExynosOutputPort)) || (!CHECK_PORT_POPULATED(pExynosOutputPort))) {
2329 ret = OMX_ErrorNone;
2330 goto EXIT;
2331 }
2332 if (OMX_FALSE == Exynos_Check_BufferProcess_State(pExynosComponent, OUTPUT_PORT_INDEX)) {
2333 ret = OMX_ErrorNone;
2334 goto EXIT;
2335 }
2336 if (pExynosOutputPort->bufferProcessType & BUFFER_SHARE) {
2337 if ((pH264Dec->bDestinationStart == OMX_FALSE) &&
2338 (!CHECK_PORT_BEING_FLUSHED(pExynosOutputPort))) {
2339 Exynos_OSAL_SignalWait(pH264Dec->hDestinationStartEvent, DEF_MAX_WAIT_TIME);
2340 Exynos_OSAL_SignalReset(pH264Dec->hDestinationStartEvent);
2341 }
2342 if (Exynos_OSAL_GetElemNum(&pH264Dec->bypassBufferInfoQ) > 0) {
2343 BYPASS_BUFFER_INFO *pBufferInfo = (BYPASS_BUFFER_INFO *)Exynos_OSAL_Dequeue(&pH264Dec->bypassBufferInfoQ);
2344 if (pBufferInfo == NULL) {
2345 ret = OMX_ErrorUndefined;
2346 goto EXIT;
2347 }
2348
2349 pDstInputData->bufferHeader->nFlags = pBufferInfo->nFlags;
2350 pDstInputData->bufferHeader->nTimeStamp = pBufferInfo->timeStamp;
2351 Exynos_OMX_OutputBufferReturn(pOMXComponent, pDstInputData->bufferHeader);
2352 Exynos_OSAL_Free(pBufferInfo);
2353
2354 ret = OMX_ErrorNone;
2355 goto EXIT;
2356 }
2357 }
2358 if (pH264Dec->hMFCH264Handle.bConfiguredMFCDst == OMX_TRUE) {
2359 ret = Exynos_H264Dec_DstIn(pOMXComponent, pDstInputData);
2360 if (ret != OMX_ErrorNone) {
2361 pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent,
2362 pExynosComponent->callbackData,
2363 OMX_EventError, ret, 0, NULL);
2364 }
2365 }
2366
2367 EXIT:
2368 FunctionOut();
2369
2370 return ret;
2371 }
2372
2373 OMX_ERRORTYPE Exynos_H264Dec_dstOutputBufferProcess(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *pDstOutputData)
2374 {
2375 OMX_ERRORTYPE ret = OMX_ErrorNone;
2376 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2377 EXYNOS_H264DEC_HANDLE *pH264Dec = (EXYNOS_H264DEC_HANDLE *)((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle;
2378 EXYNOS_OMX_BASEPORT *pExynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
2379
2380 FunctionIn();
2381
2382 if ((!CHECK_PORT_ENABLED(pExynosOutputPort)) || (!CHECK_PORT_POPULATED(pExynosOutputPort))) {
2383 ret = OMX_ErrorNone;
2384 goto EXIT;
2385 }
2386 if (OMX_FALSE == Exynos_Check_BufferProcess_State(pExynosComponent, OUTPUT_PORT_INDEX)) {
2387 ret = OMX_ErrorNone;
2388 goto EXIT;
2389 }
2390
2391 if (pExynosOutputPort->bufferProcessType & BUFFER_COPY) {
2392 if ((pH264Dec->bDestinationStart == OMX_FALSE) &&
2393 (!CHECK_PORT_BEING_FLUSHED(pExynosOutputPort))) {
2394 Exynos_OSAL_SignalWait(pH264Dec->hDestinationStartEvent, DEF_MAX_WAIT_TIME);
2395 Exynos_OSAL_SignalReset(pH264Dec->hDestinationStartEvent);
2396 }
2397
2398 if (Exynos_OSAL_GetElemNum(&pH264Dec->bypassBufferInfoQ) > 0) {
2399 EXYNOS_OMX_DATABUFFER *dstOutputUseBuffer = &pExynosOutputPort->way.port2WayDataBuffer.outputDataBuffer;
2400 OMX_BUFFERHEADERTYPE *pOMXBuffer = NULL;
2401 BYPASS_BUFFER_INFO *pBufferInfo = NULL;
2402
2403 if (dstOutputUseBuffer->dataValid == OMX_FALSE) {
2404 pOMXBuffer = Exynos_OutputBufferGetQueue_Direct(pExynosComponent);
2405 if (pOMXBuffer == NULL) {
2406 ret = OMX_ErrorUndefined;
2407 goto EXIT;
2408 }
2409 } else {
2410 pOMXBuffer = dstOutputUseBuffer->bufferHeader;
2411 }
2412
2413 pBufferInfo = Exynos_OSAL_Dequeue(&pH264Dec->bypassBufferInfoQ);
2414 if (pBufferInfo == NULL) {
2415 ret = OMX_ErrorUndefined;
2416 goto EXIT;
2417 }
2418
2419 pOMXBuffer->nFlags = pBufferInfo->nFlags;
2420 pOMXBuffer->nTimeStamp = pBufferInfo->timeStamp;
2421 Exynos_OMX_OutputBufferReturn(pOMXComponent, pOMXBuffer);
2422 Exynos_OSAL_Free(pBufferInfo);
2423
2424 dstOutputUseBuffer->dataValid = OMX_FALSE;
2425
2426 ret = OMX_ErrorNone;
2427 goto EXIT;
2428 }
2429 }
2430 ret = Exynos_H264Dec_DstOut(pOMXComponent, pDstOutputData);
2431 if ((ret != OMX_ErrorNone) && (pExynosComponent->currentState == OMX_StateExecuting)) {
2432 pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent,
2433 pExynosComponent->callbackData,
2434 OMX_EventError, ret, 0, NULL);
2435 }
2436
2437 EXIT:
2438 FunctionOut();
2439
2440 return ret;
2441 }
2442
2443 OSCL_EXPORT_REF OMX_ERRORTYPE Exynos_OMX_ComponentInit(OMX_HANDLETYPE hComponent, OMX_STRING componentName)
2444 {
2445 OMX_ERRORTYPE ret = OMX_ErrorNone;
2446 OMX_COMPONENTTYPE *pOMXComponent = NULL;
2447 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
2448 EXYNOS_OMX_BASEPORT *pExynosPort = NULL;
2449 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
2450 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
2451 OMX_BOOL bDRMPlayerMode = OMX_FALSE;
2452 int i = 0;
2453
2454 FunctionIn();
2455
2456 if ((hComponent == NULL) || (componentName == NULL)) {
2457 ret = OMX_ErrorBadParameter;
2458 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorBadParameter, Line:%d", __LINE__);
2459 goto EXIT;
2460 }
2461 if (Exynos_OSAL_Strcmp(EXYNOS_OMX_COMPONENT_H264_DEC, componentName) == 0) {
2462 bDRMPlayerMode = OMX_FALSE;
2463 } else if (Exynos_OSAL_Strcmp(EXYNOS_OMX_COMPONENT_H264_DRM_DEC, componentName) == 0) {
2464 bDRMPlayerMode = OMX_TRUE;
2465 } else {
2466 ret = OMX_ErrorBadParameter;
2467 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorBadParameter, componentName:%s, Line:%d", componentName, __LINE__);
2468 goto EXIT;
2469 }
2470
2471 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
2472 ret = Exynos_OMX_VideoDecodeComponentInit(pOMXComponent);
2473 if (ret != OMX_ErrorNone) {
2474 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_Error, Line:%d", __LINE__);
2475 goto EXIT;
2476 }
2477 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2478 pExynosComponent->codecType = HW_VIDEO_DEC_CODEC;
2479
2480 pExynosComponent->componentName = (OMX_STRING)Exynos_OSAL_Malloc(MAX_OMX_COMPONENT_NAME_SIZE);
2481 if (pExynosComponent->componentName == NULL) {
2482 Exynos_OMX_VideoDecodeComponentDeinit(pOMXComponent);
2483 ret = OMX_ErrorInsufficientResources;
2484 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorInsufficientResources, Line:%d", __LINE__);
2485 goto EXIT;
2486 }
2487 Exynos_OSAL_Memset(pExynosComponent->componentName, 0, MAX_OMX_COMPONENT_NAME_SIZE);
2488
2489 pH264Dec = Exynos_OSAL_Malloc(sizeof(EXYNOS_H264DEC_HANDLE));
2490 if (pH264Dec == NULL) {
2491 Exynos_OMX_VideoDecodeComponentDeinit(pOMXComponent);
2492 ret = OMX_ErrorInsufficientResources;
2493 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorInsufficientResources, Line:%d", __LINE__);
2494 goto EXIT;
2495 }
2496 Exynos_OSAL_Memset(pH264Dec, 0, sizeof(EXYNOS_H264DEC_HANDLE));
2497 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
2498 pVideoDec->hCodecHandle = (OMX_HANDLETYPE)pH264Dec;
2499
2500 if (bDRMPlayerMode == OMX_TRUE)
2501 Exynos_OSAL_Strcpy(pExynosComponent->componentName, EXYNOS_OMX_COMPONENT_H264_DRM_DEC);
2502 else
2503 Exynos_OSAL_Strcpy(pExynosComponent->componentName, EXYNOS_OMX_COMPONENT_H264_DEC);
2504
2505 pVideoDec->bDRMPlayerMode = bDRMPlayerMode;
2506 #ifdef USE_S3D_SUPPORT
2507 pH264Dec->hMFCH264Handle.S3DFPArgmtType = OMX_SEC_FPARGMT_INVALID;
2508 #endif
2509
2510 /* Set componentVersion */
2511 pExynosComponent->componentVersion.s.nVersionMajor = VERSIONMAJOR_NUMBER;
2512 pExynosComponent->componentVersion.s.nVersionMinor = VERSIONMINOR_NUMBER;
2513 pExynosComponent->componentVersion.s.nRevision = REVISION_NUMBER;
2514 pExynosComponent->componentVersion.s.nStep = STEP_NUMBER;
2515 /* Set specVersion */
2516 pExynosComponent->specVersion.s.nVersionMajor = VERSIONMAJOR_NUMBER;
2517 pExynosComponent->specVersion.s.nVersionMinor = VERSIONMINOR_NUMBER;
2518 pExynosComponent->specVersion.s.nRevision = REVISION_NUMBER;
2519 pExynosComponent->specVersion.s.nStep = STEP_NUMBER;
2520
2521 /* Input port */
2522 pExynosPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX];
2523 pExynosPort->portDefinition.format.video.nFrameWidth = DEFAULT_FRAME_WIDTH;
2524 pExynosPort->portDefinition.format.video.nFrameHeight= DEFAULT_FRAME_HEIGHT;
2525 pExynosPort->portDefinition.format.video.nStride = 0; /*DEFAULT_FRAME_WIDTH;*/
2526 pExynosPort->portDefinition.format.video.nSliceHeight = 0;
2527 pExynosPort->portDefinition.nBufferSize = DEFAULT_VIDEO_INPUT_BUFFER_SIZE;
2528 pExynosPort->portDefinition.format.video.eCompressionFormat = OMX_VIDEO_CodingAVC;
2529 Exynos_OSAL_Memset(pExynosPort->portDefinition.format.video.cMIMEType, 0, MAX_OMX_MIMETYPE_SIZE);
2530 Exynos_OSAL_Strcpy(pExynosPort->portDefinition.format.video.cMIMEType, "video/avc");
2531 pExynosPort->portDefinition.format.video.pNativeRender = 0;
2532 pExynosPort->portDefinition.format.video.bFlagErrorConcealment = OMX_FALSE;
2533 pExynosPort->portDefinition.format.video.eColorFormat = OMX_COLOR_FormatUnused;
2534 pExynosPort->portDefinition.bEnabled = OMX_TRUE;
2535 pExynosPort->bufferProcessType = BUFFER_SHARE;
2536 if (bDRMPlayerMode == OMX_TRUE)
2537 pExynosPort->bufferProcessType = BUFFER_SHARE;
2538 pExynosPort->portWayType = WAY2_PORT;
2539
2540 /* Output port */
2541 pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX];
2542 pExynosPort->portDefinition.format.video.nFrameWidth = DEFAULT_FRAME_WIDTH;
2543 pExynosPort->portDefinition.format.video.nFrameHeight= DEFAULT_FRAME_HEIGHT;
2544 pExynosPort->portDefinition.format.video.nStride = 0; /*DEFAULT_FRAME_WIDTH;*/
2545 pExynosPort->portDefinition.format.video.nSliceHeight = 0;
2546 pExynosPort->portDefinition.nBufferSize = DEFAULT_VIDEO_OUTPUT_BUFFER_SIZE;
2547 pExynosPort->portDefinition.format.video.eCompressionFormat = OMX_VIDEO_CodingUnused;
2548 Exynos_OSAL_Memset(pExynosPort->portDefinition.format.video.cMIMEType, 0, MAX_OMX_MIMETYPE_SIZE);
2549 Exynos_OSAL_Strcpy(pExynosPort->portDefinition.format.video.cMIMEType, "raw/video");
2550 pExynosPort->portDefinition.format.video.pNativeRender = 0;
2551 pExynosPort->portDefinition.format.video.bFlagErrorConcealment = OMX_FALSE;
2552 pExynosPort->portDefinition.format.video.eColorFormat = OMX_COLOR_FormatYUV420Planar;
2553 pExynosPort->portDefinition.bEnabled = OMX_TRUE;
2554 pExynosPort->bufferProcessType = BUFFER_COPY | BUFFER_ANBSHARE;
2555 pExynosPort->portWayType = WAY2_PORT;
2556
2557 for(i = 0; i < ALL_PORT_NUM; i++) {
2558 INIT_SET_SIZE_VERSION(&pH264Dec->AVCComponent[i], OMX_VIDEO_PARAM_AVCTYPE);
2559 pH264Dec->AVCComponent[i].nPortIndex = i;
2560 pH264Dec->AVCComponent[i].eProfile = OMX_VIDEO_AVCProfileBaseline;
2561 pH264Dec->AVCComponent[i].eLevel = OMX_VIDEO_AVCLevel4;
2562 }
2563
2564 pOMXComponent->GetParameter = &Exynos_H264Dec_GetParameter;
2565 pOMXComponent->SetParameter = &Exynos_H264Dec_SetParameter;
2566 pOMXComponent->GetConfig = &Exynos_H264Dec_GetConfig;
2567 pOMXComponent->SetConfig = &Exynos_H264Dec_SetConfig;
2568 pOMXComponent->GetExtensionIndex = &Exynos_H264Dec_GetExtensionIndex;
2569 pOMXComponent->ComponentRoleEnum = &Exynos_H264Dec_ComponentRoleEnum;
2570 pOMXComponent->ComponentDeInit = &Exynos_OMX_ComponentDeinit;
2571
2572 pExynosComponent->exynos_codec_componentInit = &Exynos_H264Dec_Init;
2573 pExynosComponent->exynos_codec_componentTerminate = &Exynos_H264Dec_Terminate;
2574
2575 pVideoDec->exynos_codec_srcInputProcess = &Exynos_H264Dec_srcInputBufferProcess;
2576 pVideoDec->exynos_codec_srcOutputProcess = &Exynos_H264Dec_srcOutputBufferProcess;
2577 pVideoDec->exynos_codec_dstInputProcess = &Exynos_H264Dec_dstInputBufferProcess;
2578 pVideoDec->exynos_codec_dstOutputProcess = &Exynos_H264Dec_dstOutputBufferProcess;
2579
2580 pVideoDec->exynos_codec_start = &H264CodecStart;
2581 pVideoDec->exynos_codec_stop = &H264CodecStop;
2582 pVideoDec->exynos_codec_bufferProcessRun = &H264CodecOutputBufferProcessRun;
2583 pVideoDec->exynos_codec_enqueueAllBuffer = &H264CodecEnQueueAllBuffer;
2584
2585 pVideoDec->exynos_checkInputFrame = &Check_H264_Frame;
2586 pVideoDec->exynos_codec_getCodecInputPrivateData = &GetCodecInputPrivateData;
2587 pVideoDec->exynos_codec_getCodecOutputPrivateData = &GetCodecOutputPrivateData;
2588 pVideoDec->exynos_codec_reconfigAllBuffers = &H264CodecReconfigAllBuffers;
2589
2590 pVideoDec->hSharedMemory = Exynos_OSAL_SharedMemory_Open();
2591 if (pVideoDec->hSharedMemory == NULL) {
2592 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorInsufficientResources, Line:%d", __LINE__);
2593 Exynos_OSAL_Free(pH264Dec);
2594 pH264Dec = ((EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle)->hCodecHandle = NULL;
2595 Exynos_OMX_VideoDecodeComponentDeinit(pOMXComponent);
2596 ret = OMX_ErrorInsufficientResources;
2597 goto EXIT;
2598 }
2599
2600 pExynosComponent->currentState = OMX_StateLoaded;
2601
2602 ret = OMX_ErrorNone;
2603
2604 EXIT:
2605 FunctionOut();
2606
2607 return ret;
2608 }
2609
2610 OMX_ERRORTYPE Exynos_OMX_ComponentDeinit(OMX_HANDLETYPE hComponent)
2611 {
2612 OMX_ERRORTYPE ret = OMX_ErrorNone;
2613 OMX_COMPONENTTYPE *pOMXComponent = NULL;
2614 EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL;
2615 EXYNOS_OMX_VIDEODEC_COMPONENT *pVideoDec = NULL;
2616 EXYNOS_H264DEC_HANDLE *pH264Dec = NULL;
2617
2618 FunctionIn();
2619
2620 if (hComponent == NULL) {
2621 ret = OMX_ErrorBadParameter;
2622 goto EXIT;
2623 }
2624 pOMXComponent = (OMX_COMPONENTTYPE *)hComponent;
2625 pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate;
2626 pVideoDec = (EXYNOS_OMX_VIDEODEC_COMPONENT *)pExynosComponent->hComponentHandle;
2627
2628 Exynos_OSAL_SharedMemory_Close(pVideoDec->hSharedMemory);
2629
2630 Exynos_OSAL_Free(pExynosComponent->componentName);
2631 pExynosComponent->componentName = NULL;
2632
2633 pH264Dec = (EXYNOS_H264DEC_HANDLE *)pVideoDec->hCodecHandle;
2634 if (pH264Dec != NULL) {
2635 Exynos_OSAL_Free(pH264Dec);
2636 pH264Dec = pVideoDec->hCodecHandle = NULL;
2637 }
2638
2639 ret = Exynos_OMX_VideoDecodeComponentDeinit(pOMXComponent);
2640 if (ret != OMX_ErrorNone) {
2641 goto EXIT;
2642 }
2643
2644 ret = OMX_ErrorNone;
2645
2646 EXIT:
2647 FunctionOut();
2648
2649 return ret;
2650 }