Commit | Line | Data |
---|---|---|
20d3e6e3 JC |
1 | /* |
2 | * | |
38ef2572 | 3 | * Copyright 2012 Samsung Electronics S.LSI Co. LTD |
20d3e6e3 JC |
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_Venc.c | |
20 | * @brief | |
21 | * @author SeungBeom Kim (sbcrux.kim@samsung.com) | |
22 | * Yunji Kim (yunji.kim@samsung.com) | |
38ef2572 | 23 | * @version 2.0.0 |
20d3e6e3 | 24 | * @history |
38ef2572 | 25 | * 2012.02.20 : Create |
20d3e6e3 JC |
26 | */ |
27 | ||
28 | #include <stdio.h> | |
29 | #include <stdlib.h> | |
30 | #include <string.h> | |
31 | #include "Exynos_OMX_Macros.h" | |
32 | #include "Exynos_OSAL_Event.h" | |
33 | #include "Exynos_OMX_Venc.h" | |
38ef2572 | 34 | #include "Exynos_OMX_VencControl.h" |
20d3e6e3 JC |
35 | #include "Exynos_OMX_Basecomponent.h" |
36 | #include "Exynos_OSAL_Thread.h" | |
20d3e6e3 | 37 | #include "Exynos_OSAL_Semaphore.h" |
33d6044e | 38 | #include "Exynos_OSAL_SharedMemory.h" |
38ef2572 | 39 | #include "Exynos_OSAL_Mutex.h" |
20d3e6e3 JC |
40 | #include "Exynos_OSAL_ETC.h" |
41 | #include "csc.h" | |
42 | ||
43 | #ifdef USE_STOREMETADATA | |
33d6044e | 44 | #include <system/window.h> |
20d3e6e3 JC |
45 | #include "Exynos_OSAL_Android.h" |
46 | #endif | |
47 | ||
48 | #undef EXYNOS_LOG_TAG | |
49 | #define EXYNOS_LOG_TAG "EXYNOS_VIDEO_ENC" | |
50 | #define EXYNOS_LOG_OFF | |
38ef2572 | 51 | //#define EXYNOS_TRACE_ON |
20d3e6e3 JC |
52 | #include "Exynos_OSAL_Log.h" |
53 | ||
54 | ||
55 | inline void Exynos_UpdateFrameSize(OMX_COMPONENTTYPE *pOMXComponent) | |
56 | { | |
57 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
58 | EXYNOS_OMX_BASEPORT *exynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; | |
59 | EXYNOS_OMX_BASEPORT *exynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]; | |
60 | ||
61 | if ((exynosOutputPort->portDefinition.format.video.nFrameWidth != | |
62 | exynosInputPort->portDefinition.format.video.nFrameWidth) || | |
63 | (exynosOutputPort->portDefinition.format.video.nFrameHeight != | |
64 | exynosInputPort->portDefinition.format.video.nFrameHeight)) { | |
65 | OMX_U32 width = 0, height = 0; | |
66 | ||
67 | exynosOutputPort->portDefinition.format.video.nFrameWidth = | |
68 | exynosInputPort->portDefinition.format.video.nFrameWidth; | |
69 | exynosOutputPort->portDefinition.format.video.nFrameHeight = | |
70 | exynosInputPort->portDefinition.format.video.nFrameHeight; | |
71 | width = exynosOutputPort->portDefinition.format.video.nStride = | |
72 | exynosInputPort->portDefinition.format.video.nStride; | |
73 | height = exynosOutputPort->portDefinition.format.video.nSliceHeight = | |
74 | exynosInputPort->portDefinition.format.video.nSliceHeight; | |
75 | ||
76 | if (width && height) | |
77 | exynosOutputPort->portDefinition.nBufferSize = (width * height * 3) / 2; | |
78 | } | |
79 | ||
d03573a4 | 80 | return; |
20d3e6e3 JC |
81 | } |
82 | ||
38ef2572 | 83 | OMX_BOOL Exynos_Check_BufferProcess_State(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_U32 nPortIndex) |
20d3e6e3 | 84 | { |
38ef2572 | 85 | OMX_BOOL ret = OMX_FALSE; |
20d3e6e3 | 86 | |
20d3e6e3 | 87 | if ((pExynosComponent->currentState == OMX_StateExecuting) && |
38ef2572 | 88 | (pExynosComponent->pExynosPort[nPortIndex].portState == OMX_StateIdle) && |
20d3e6e3 | 89 | (pExynosComponent->transientState != EXYNOS_OMX_TransStateExecutingToIdle) && |
38ef2572 JC |
90 | (pExynosComponent->transientState != EXYNOS_OMX_TransStateIdleToExecuting)) { |
91 | ret = OMX_TRUE; | |
92 | } else { | |
93 | ret = OMX_FALSE; | |
20d3e6e3 JC |
94 | } |
95 | ||
20d3e6e3 JC |
96 | return ret; |
97 | } | |
98 | ||
38ef2572 | 99 | OMX_ERRORTYPE Exynos_Input_CodecBufferToData(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_PTR codecBuffer, EXYNOS_OMX_DATA *pData) |
20d3e6e3 | 100 | { |
38ef2572 JC |
101 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
102 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
91f44a5d | 103 | CODEC_ENC_BUFFER *pInputCodecBuffer = (CODEC_ENC_BUFFER*)codecBuffer; |
20d3e6e3 | 104 | |
91f44a5d SK |
105 | pData->buffer.multiPlaneBuffer.dataBuffer[0] = pInputCodecBuffer->pVirAddr[0]; |
106 | pData->buffer.multiPlaneBuffer.dataBuffer[1] = pInputCodecBuffer->pVirAddr[1]; | |
8ee7ad9c GH |
107 | pData->buffer.multiPlaneBuffer.fd[0] = pInputCodecBuffer->fd[0]; |
108 | pData->buffer.multiPlaneBuffer.fd[1] = pInputCodecBuffer->fd[1]; | |
91f44a5d SK |
109 | pData->allocSize = pInputCodecBuffer->bufferSize[0] + pInputCodecBuffer->bufferSize[1]; |
110 | pData->dataLen = pInputCodecBuffer->dataSize; | |
38ef2572 | 111 | pData->usedDataLen = 0; |
91f44a5d | 112 | pData->remainDataLen = pInputCodecBuffer->dataSize; |
20d3e6e3 | 113 | |
38ef2572 JC |
114 | pData->nFlags = 0; |
115 | pData->timeStamp = 0; | |
116 | pData->pPrivate = codecBuffer; | |
117 | pData->bufferHeader = NULL; | |
20d3e6e3 JC |
118 | |
119 | return ret; | |
120 | } | |
121 | ||
38ef2572 | 122 | OMX_ERRORTYPE Exynos_Output_CodecBufferToData(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_PTR codecBuffer, EXYNOS_OMX_DATA *pData) |
20d3e6e3 | 123 | { |
38ef2572 JC |
124 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
125 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
126 | OMX_PTR pSrcBuf; | |
127 | OMX_U32 allocSize; | |
20d3e6e3 | 128 | |
38ef2572 JC |
129 | pVideoEnc->exynos_codec_getCodecOutputPrivateData(codecBuffer, &pSrcBuf, &allocSize); |
130 | pData->buffer.singlePlaneBuffer.dataBuffer = pSrcBuf; | |
131 | pData->allocSize = allocSize; | |
132 | pData->dataLen = 0; | |
133 | pData->usedDataLen = 0; | |
134 | pData->remainDataLen = 0; | |
20d3e6e3 | 135 | |
38ef2572 JC |
136 | pData->nFlags = 0; |
137 | pData->timeStamp = 0; | |
138 | pData->pPrivate = codecBuffer; | |
139 | pData->bufferHeader = NULL; | |
20d3e6e3 JC |
140 | |
141 | return ret; | |
142 | } | |
143 | ||
38ef2572 | 144 | void Exynos_Wait_ProcessPause(EXYNOS_OMX_BASECOMPONENT *pExynosComponent, OMX_U32 nPortIndex) |
20d3e6e3 | 145 | { |
38ef2572 JC |
146 | EXYNOS_OMX_BASEPORT *exynosOMXInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; |
147 | EXYNOS_OMX_BASEPORT *exynosOMXOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]; | |
148 | EXYNOS_OMX_BASEPORT *exynosOMXPort = NULL; | |
20d3e6e3 JC |
149 | |
150 | FunctionIn(); | |
151 | ||
38ef2572 | 152 | exynosOMXPort = &pExynosComponent->pExynosPort[nPortIndex]; |
20d3e6e3 | 153 | |
38ef2572 JC |
154 | if (((pExynosComponent->currentState == OMX_StatePause) || |
155 | (pExynosComponent->currentState == OMX_StateIdle) || | |
156 | (pExynosComponent->transientState == EXYNOS_OMX_TransStateLoadedToIdle) || | |
157 | (pExynosComponent->transientState == EXYNOS_OMX_TransStateExecutingToIdle)) && | |
3e79a27e | 158 | (pExynosComponent->transientState != EXYNOS_OMX_TransStateIdleToLoaded) && |
38ef2572 JC |
159 | (!CHECK_PORT_BEING_FLUSHED(exynosOMXPort))) { |
160 | Exynos_OSAL_SignalWait(pExynosComponent->pExynosPort[nPortIndex].pauseEvent, DEF_MAX_WAIT_TIME); | |
161 | Exynos_OSAL_SignalReset(pExynosComponent->pExynosPort[nPortIndex].pauseEvent); | |
20d3e6e3 | 162 | } |
20d3e6e3 | 163 | |
38ef2572 | 164 | FunctionOut(); |
20d3e6e3 | 165 | |
38ef2572 | 166 | return; |
20d3e6e3 JC |
167 | } |
168 | ||
91f44a5d SK |
169 | OMX_BOOL Exynos_CSC_InputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *srcInputData) |
170 | { | |
171 | OMX_BOOL ret = OMX_FALSE; | |
172 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
173 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
174 | EXYNOS_OMX_BASEPORT *exynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; | |
175 | EXYNOS_OMX_DATABUFFER *inputUseBuffer = &exynosInputPort->way.port2WayDataBuffer.inputDataBuffer; | |
176 | OMX_U32 nFrameWidth = exynosInputPort->portDefinition.format.video.nFrameWidth; | |
177 | OMX_U32 nFrameHeight = exynosInputPort->portDefinition.format.video.nFrameHeight; | |
178 | OMX_COLOR_FORMATTYPE eColorFormat = exynosInputPort->portDefinition.format.video.eColorFormat; | |
179 | OMX_BYTE checkInputStream = NULL; | |
180 | OMX_BOOL flagEOS = OMX_FALSE; | |
181 | ||
182 | FunctionIn(); | |
183 | ||
184 | checkInputStream = inputUseBuffer->bufferHeader->pBuffer; | |
185 | ||
186 | CODEC_ENC_BUFFER *codecInputBuffer = (CODEC_ENC_BUFFER *)srcInputData->pPrivate; | |
187 | codecInputBuffer->dataSize = ((nFrameWidth * nFrameHeight) * 3) / 2; | |
188 | ||
189 | unsigned int csc_src_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420SemiPlanar); | |
190 | unsigned int csc_dst_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420SemiPlanar); | |
191 | CSC_METHOD csc_method = CSC_METHOD_SW; | |
192 | unsigned int cacheable = 1; | |
193 | ||
fe7c2607 GH |
194 | void *pSrcBuf[3] = {NULL, }; |
195 | void *pSrcFd[3] = {NULL, }; | |
196 | void *pDstBuf[3] = {NULL, }; | |
197 | void *pDstFd[3] = {NULL, }; | |
91f44a5d SK |
198 | |
199 | CSC_ERRORCODE cscRet = CSC_ErrorNone; | |
200 | ||
201 | pSrcBuf[0] = checkInputStream; | |
202 | pSrcBuf[1] = checkInputStream + (nFrameWidth * nFrameHeight); | |
203 | pSrcBuf[2] = checkInputStream + (((nFrameWidth * nFrameHeight) * 5) / 4); | |
204 | ||
205 | pDstBuf[0] = srcInputData->buffer.multiPlaneBuffer.dataBuffer[0]; | |
206 | pDstBuf[1] = srcInputData->buffer.multiPlaneBuffer.dataBuffer[1]; | |
207 | pDstBuf[2] = srcInputData->buffer.multiPlaneBuffer.dataBuffer[2]; | |
208 | ||
91f44a5d SK |
209 | #ifdef USE_METADATABUFFERTYPE |
210 | OMX_PTR ppBuf[MAX_BUFFER_PLANE]; | |
211 | ||
212 | /* kMetadataBufferTypeGrallocSource */ | |
213 | if (exynosInputPort->bStoreMetaData == OMX_TRUE) { | |
214 | /* ARGB8888 converted to YUV420SemiPlanar */ | |
215 | csc_src_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_Format32bitARGB8888); | |
216 | csc_dst_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420SemiPlanar); | |
217 | ||
218 | Exynos_OSAL_GetInfoFromMetaData((OMX_BYTE)inputUseBuffer->bufferHeader->pBuffer, ppBuf); | |
219 | if (eColorFormat == OMX_COLOR_FormatAndroidOpaque) { | |
220 | ExynosVideoPlane planes[MAX_BUFFER_PLANE]; | |
fe7c2607 | 221 | size_t i; |
91f44a5d | 222 | |
24eadba9 | 223 | Exynos_OSAL_LockANBHandle((OMX_U32)ppBuf[0], nFrameWidth, nFrameHeight, OMX_COLOR_FormatAndroidOpaque, planes); |
fe7c2607 GH |
224 | |
225 | #ifdef USE_CSC_GSCALER | |
226 | csc_method = CSC_METHOD_HW; | |
227 | #endif | |
228 | pSrcBuf[0] = planes[0].addr; | |
229 | pSrcFd[0] = (void *)planes[0].fd; | |
230 | for (i = 0; i < 3; i++) | |
231 | pDstFd[i] = (void *)srcInputData->buffer.multiPlaneBuffer.fd[i]; | |
91f44a5d SK |
232 | } |
233 | } else | |
234 | #endif | |
235 | { | |
91f44a5d SK |
236 | switch (eColorFormat) { |
237 | case OMX_COLOR_FormatYUV420Planar: | |
238 | /* YUV420Planar converted to YUV420Semiplanar (interleaved UV plane) as per MFC spec.*/ | |
239 | csc_src_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420Planar); | |
240 | csc_dst_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420SemiPlanar); | |
241 | break; | |
242 | case OMX_COLOR_FormatYUV420SemiPlanar: | |
243 | case OMX_SEC_COLOR_FormatNV12Tiled: | |
244 | case OMX_SEC_COLOR_FormatNV21Linear: | |
245 | /* Just copied to MFC input buffer */ | |
246 | csc_src_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420SemiPlanar); | |
247 | csc_dst_color_format = omx_2_hal_pixel_format((unsigned int)OMX_COLOR_FormatYUV420SemiPlanar); | |
248 | break; | |
249 | default: | |
250 | break; | |
251 | } | |
252 | } | |
253 | ||
fe7c2607 GH |
254 | csc_set_method( |
255 | pVideoEnc->csc_handle, | |
256 | csc_method); | |
91f44a5d SK |
257 | csc_set_src_format( |
258 | pVideoEnc->csc_handle, /* handle */ | |
259 | nFrameWidth, /* width */ | |
260 | nFrameHeight, /* height */ | |
261 | 0, /* crop_left */ | |
262 | 0, /* crop_right */ | |
263 | nFrameWidth, /* crop_width */ | |
264 | nFrameHeight, /* crop_height */ | |
265 | csc_src_color_format, /* color_format */ | |
266 | cacheable); /* cacheable */ | |
267 | csc_set_dst_format( | |
268 | pVideoEnc->csc_handle, /* handle */ | |
269 | nFrameWidth, /* width */ | |
270 | nFrameHeight, /* height */ | |
271 | 0, /* crop_left */ | |
272 | 0, /* crop_right */ | |
273 | nFrameWidth, /* crop_width */ | |
274 | nFrameHeight, /* crop_height */ | |
275 | csc_dst_color_format, /* color_format */ | |
276 | cacheable); /* cacheable */ | |
fe7c2607 GH |
277 | if (csc_method == CSC_METHOD_SW) { |
278 | csc_set_src_buffer( | |
279 | pVideoEnc->csc_handle, /* handle */ | |
280 | pSrcBuf); | |
281 | csc_set_dst_buffer( | |
282 | pVideoEnc->csc_handle, /* handle */ | |
283 | pDstBuf); | |
284 | } else { | |
285 | csc_set_src_buffer( | |
286 | pVideoEnc->csc_handle, /* handle */ | |
287 | pSrcFd); | |
288 | csc_set_dst_buffer( | |
289 | pVideoEnc->csc_handle, /* handle */ | |
290 | pDstFd); | |
291 | } | |
91f44a5d SK |
292 | cscRet = csc_convert(pVideoEnc->csc_handle); |
293 | if (cscRet != CSC_ErrorNone) | |
294 | ret = OMX_FALSE; | |
295 | else | |
296 | ret = OMX_TRUE; | |
297 | ||
298 | #ifdef USE_METADATABUFFERTYPE | |
299 | if (exynosInputPort->bStoreMetaData == OMX_TRUE) { | |
300 | Exynos_OSAL_UnlockANBHandle((OMX_U32)ppBuf[0]); | |
301 | } | |
302 | #endif | |
303 | ||
91f44a5d SK |
304 | EXIT: |
305 | FunctionOut(); | |
306 | ||
307 | return ret; | |
308 | } | |
309 | ||
38ef2572 | 310 | OMX_BOOL Exynos_Preprocessor_InputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *srcInputData) |
20d3e6e3 JC |
311 | { |
312 | OMX_BOOL ret = OMX_FALSE; | |
313 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
314 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
38ef2572 JC |
315 | EXYNOS_OMX_BASEPORT *exynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; |
316 | EXYNOS_OMX_DATABUFFER *inputUseBuffer = &exynosInputPort->way.port2WayDataBuffer.inputDataBuffer; | |
317 | OMX_U32 nFrameWidth = exynosInputPort->portDefinition.format.video.nFrameWidth; | |
318 | OMX_U32 nFrameHeight = exynosInputPort->portDefinition.format.video.nFrameHeight; | |
319 | OMX_COLOR_FORMATTYPE eColorFormat = exynosInputPort->portDefinition.format.video.eColorFormat; | |
320 | OMX_U32 copySize = 0; | |
321 | OMX_BYTE checkInputStream = NULL; | |
322 | OMX_U32 checkInputStreamLen = 0; | |
38ef2572 | 323 | OMX_BOOL flagEOS = OMX_FALSE; |
20d3e6e3 | 324 | |
38ef2572 | 325 | FunctionIn(); |
20d3e6e3 | 326 | |
38ef2572 JC |
327 | if ((exynosInputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { |
328 | if ((srcInputData->buffer.multiPlaneBuffer.dataBuffer[0] == NULL) || | |
329 | (srcInputData->pPrivate == NULL)) { | |
330 | ret = OMX_FALSE; | |
331 | goto EXIT; | |
20d3e6e3 | 332 | } |
38ef2572 | 333 | } |
20d3e6e3 | 334 | |
38ef2572 JC |
335 | if (inputUseBuffer->dataValid == OMX_TRUE) { |
336 | if (exynosInputPort->bufferProcessType == BUFFER_SHARE) { | |
337 | Exynos_Shared_BufferToData(inputUseBuffer, srcInputData, ONE_PLANE); | |
338 | #ifdef USE_METADATABUFFERTYPE | |
339 | if (exynosInputPort->bStoreMetaData == OMX_TRUE) { | |
91f44a5d SK |
340 | OMX_PTR ppBuf[MAX_BUFFER_PLANE]; |
341 | OMX_PTR allocSize[MAX_BUFFER_PLANE]; | |
33d6044e SK |
342 | int plane = 0; |
343 | if (eColorFormat == OMX_COLOR_FormatAndroidOpaque) { | |
344 | Exynos_OSAL_GetInfoFromMetaData((OMX_BYTE)inputUseBuffer->bufferHeader->pBuffer, ppBuf); | |
345 | ExynosVideoPlane planes[MAX_BUFFER_PLANE]; | |
346 | ||
347 | Exynos_OSAL_LockANBHandle((OMX_U32)ppBuf[0], nFrameWidth, nFrameHeight, OMX_COLOR_FormatYUV420SemiPlanar, planes); | |
348 | ||
349 | srcInputData->buffer.multiPlaneBuffer.fd[0] = planes[0].fd; | |
350 | srcInputData->buffer.multiPlaneBuffer.fd[1] = planes[1].fd; | |
351 | allocSize[0] = nFrameWidth * nFrameHeight; | |
352 | allocSize[1] = nFrameWidth * nFrameHeight >> 1; | |
353 | ||
354 | for (plane = 0; plane < MFC_INPUT_BUFFER_PLANE; plane++) { | |
91f44a5d | 355 | srcInputData->buffer.multiPlaneBuffer.dataBuffer[plane] = |
33d6044e SK |
356 | Exynos_OSAL_SharedMemory_IONToVirt(pVideoEnc->hSharedMemory, srcInputData->buffer.multiPlaneBuffer.fd[plane]); |
357 | if(srcInputData->buffer.multiPlaneBuffer.dataBuffer[plane] == NULL) { | |
358 | srcInputData->buffer.multiPlaneBuffer.dataBuffer[plane] = | |
359 | Exynos_OSAL_SharedMemory_Map(pVideoEnc->hSharedMemory, allocSize[plane], srcInputData->buffer.multiPlaneBuffer.fd[plane]); | |
360 | } | |
91f44a5d | 361 | } |
33d6044e SK |
362 | /* input buffers are 2 plane. */ |
363 | srcInputData->buffer.multiPlaneBuffer.dataBuffer[2] = NULL; | |
364 | srcInputData->buffer.multiPlaneBuffer.fd[2] = -1; | |
365 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s:%d YAddr: 0x%x CbCrAddr: 0x%x", __FUNCTION__, __LINE__, (unsigned int)ppBuf[0], (unsigned int)ppBuf[0]); | |
366 | } else { | |
367 | /* kMetadataBufferTypeCameraSource */ | |
368 | Exynos_OSAL_GetInfoFromMetaData((OMX_BYTE)inputUseBuffer->bufferHeader->pBuffer, ppBuf); | |
369 | srcInputData->buffer.multiPlaneBuffer.fd[0] = ppBuf[0]; | |
370 | srcInputData->buffer.multiPlaneBuffer.fd[1] = ppBuf[1]; | |
371 | allocSize[0] = nFrameWidth * nFrameHeight; | |
372 | allocSize[1] = nFrameWidth * nFrameHeight >> 1; | |
373 | ||
374 | for (plane = 0; plane < MFC_INPUT_BUFFER_PLANE; plane++) { | |
375 | srcInputData->buffer.multiPlaneBuffer.dataBuffer[plane] = | |
376 | Exynos_OSAL_SharedMemory_IONToVirt(pVideoEnc->hSharedMemory, srcInputData->buffer.multiPlaneBuffer.fd[plane]); | |
377 | if(srcInputData->buffer.multiPlaneBuffer.dataBuffer[plane] == NULL) { | |
378 | srcInputData->buffer.multiPlaneBuffer.dataBuffer[plane] = | |
379 | Exynos_OSAL_SharedMemory_Map(pVideoEnc->hSharedMemory, allocSize[plane], srcInputData->buffer.multiPlaneBuffer.fd[plane]); | |
380 | } | |
381 | } | |
382 | /* input buffers are 2 plane. */ | |
383 | srcInputData->buffer.multiPlaneBuffer.dataBuffer[2] = NULL; | |
384 | srcInputData->buffer.multiPlaneBuffer.fd[2] = -1; | |
385 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "%s:%d YAddr: 0x%x CbCrAddr: 0x%x", __FUNCTION__, __LINE__, (unsigned int)ppBuf[0], (unsigned int)ppBuf[0]); | |
91f44a5d | 386 | } |
20d3e6e3 | 387 | } |
38ef2572 | 388 | #endif |
38ef2572 JC |
389 | /* reset dataBuffer */ |
390 | Exynos_ResetDataBuffer(inputUseBuffer); | |
38ef2572 JC |
391 | } else if ((exynosInputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { |
392 | checkInputStream = inputUseBuffer->bufferHeader->pBuffer + inputUseBuffer->usedDataLen; | |
393 | checkInputStreamLen = inputUseBuffer->remainDataLen; | |
394 | ||
833233fa | 395 | pExynosComponent->bUseFlagEOF = OMX_TRUE; |
38ef2572 | 396 | |
833233fa SK |
397 | if (checkInputStreamLen == 0) { |
398 | inputUseBuffer->nFlags |= OMX_BUFFERFLAG_EOS; | |
399 | flagEOS = OMX_TRUE; | |
20d3e6e3 JC |
400 | } |
401 | ||
833233fa SK |
402 | copySize = checkInputStreamLen; |
403 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "exynos_checkInputFrame : OMX_TRUE"); | |
20d3e6e3 | 404 | |
38ef2572 | 405 | if (((srcInputData->allocSize) - (srcInputData->dataLen)) >= copySize) { |
ebd30f82 GH |
406 | ret = Exynos_CSC_InputData(pOMXComponent, srcInputData); |
407 | if (ret) { | |
408 | inputUseBuffer->dataLen -= copySize; | |
409 | inputUseBuffer->remainDataLen -= copySize; | |
410 | inputUseBuffer->usedDataLen += copySize; | |
411 | ||
412 | srcInputData->dataLen += copySize; | |
413 | srcInputData->remainDataLen += copySize; | |
414 | ||
415 | srcInputData->timeStamp = inputUseBuffer->timeStamp; | |
416 | srcInputData->nFlags = inputUseBuffer->nFlags; | |
417 | srcInputData->bufferHeader = inputUseBuffer->bufferHeader; | |
418 | } else { | |
419 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Exynos_CSC_InputData() failure"); | |
420 | pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent, | |
421 | pExynosComponent->callbackData, OMX_EventError, | |
422 | OMX_ErrorUndefined, 0, NULL ); | |
423 | } | |
38ef2572 JC |
424 | } else { |
425 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "input codec buffer is smaller than decoded input data size Out Length"); | |
426 | pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent, | |
427 | pExynosComponent->callbackData, | |
428 | OMX_EventError, OMX_ErrorUndefined, 0, NULL); | |
833233fa | 429 | ret = OMX_FALSE; |
20d3e6e3 JC |
430 | } |
431 | ||
38ef2572 JC |
432 | if (((exynosInputPort->bStoreMetaData == OMX_TRUE) && (eColorFormat == OMX_COLOR_FormatAndroidOpaque)) || |
433 | (exynosInputPort->bStoreMetaData == OMX_FALSE)) { | |
3e79a27e | 434 | Exynos_InputBufferReturn(pOMXComponent); |
20d3e6e3 | 435 | } else { |
38ef2572 | 436 | inputUseBuffer->dataValid = OMX_TRUE; |
20d3e6e3 | 437 | } |
20d3e6e3 JC |
438 | } |
439 | ||
38ef2572 | 440 | if ((srcInputData->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) { |
3e79a27e | 441 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "bSaveFlagEOS : OMX_TRUE"); |
38ef2572 JC |
442 | srcInputData->dataLen = 0; |
443 | srcInputData->remainDataLen = 0; | |
444 | pExynosComponent->bSaveFlagEOS = OMX_TRUE; | |
445 | } | |
446 | ||
833233fa SK |
447 | if (pExynosComponent->checkTimeStamp.needSetStartTimeStamp == OMX_TRUE) { |
448 | pExynosComponent->checkTimeStamp.needCheckStartTimeStamp = OMX_TRUE; | |
449 | pExynosComponent->checkTimeStamp.startTimeStamp = srcInputData->timeStamp; | |
450 | pExynosComponent->checkTimeStamp.nStartFlags = srcInputData->nFlags; | |
451 | pExynosComponent->checkTimeStamp.needSetStartTimeStamp = OMX_FALSE; | |
452 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "first frame timestamp after seeking %lld us (%.2f secs)", | |
453 | srcInputData->timeStamp, srcInputData->timeStamp / 1E6); | |
20d3e6e3 | 454 | } |
833233fa SK |
455 | |
456 | ret = OMX_TRUE; | |
20d3e6e3 JC |
457 | } |
458 | ||
38ef2572 JC |
459 | EXIT: |
460 | ||
461 | FunctionOut(); | |
20d3e6e3 | 462 | |
20d3e6e3 JC |
463 | return ret; |
464 | } | |
465 | ||
38ef2572 | 466 | OMX_BOOL Exynos_Postprocess_OutputData(OMX_COMPONENTTYPE *pOMXComponent, EXYNOS_OMX_DATA *dstOutputData) |
20d3e6e3 JC |
467 | { |
468 | OMX_BOOL ret = OMX_FALSE; | |
469 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
38ef2572 JC |
470 | EXYNOS_OMX_BASEPORT *exynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]; |
471 | EXYNOS_OMX_DATABUFFER *outputUseBuffer = &exynosOutputPort->way.port2WayDataBuffer.outputDataBuffer; | |
20d3e6e3 JC |
472 | OMX_U32 copySize = 0; |
473 | ||
38ef2572 JC |
474 | FunctionIn(); |
475 | ||
476 | if (exynosOutputPort->bufferProcessType == BUFFER_SHARE) { | |
477 | if (Exynos_Shared_DataToBuffer(dstOutputData, outputUseBuffer) == OMX_ErrorNone) | |
478 | outputUseBuffer->dataValid = OMX_TRUE; | |
479 | } | |
480 | ||
20d3e6e3 JC |
481 | if (outputUseBuffer->dataValid == OMX_TRUE) { |
482 | if (pExynosComponent->checkTimeStamp.needCheckStartTimeStamp == OMX_TRUE) { | |
38ef2572 | 483 | if (pExynosComponent->checkTimeStamp.startTimeStamp == dstOutputData->timeStamp){ |
20d3e6e3 JC |
484 | pExynosComponent->checkTimeStamp.startTimeStamp = -19761123; |
485 | pExynosComponent->checkTimeStamp.nStartFlags = 0x0; | |
486 | pExynosComponent->checkTimeStamp.needSetStartTimeStamp = OMX_FALSE; | |
487 | pExynosComponent->checkTimeStamp.needCheckStartTimeStamp = OMX_FALSE; | |
488 | } else { | |
0b9f280f | 489 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "garbage frame drop after flush"); |
20d3e6e3 JC |
490 | ret = OMX_TRUE; |
491 | goto EXIT; | |
492 | } | |
493 | } else if (pExynosComponent->checkTimeStamp.needSetStartTimeStamp == OMX_TRUE) { | |
20d3e6e3 | 494 | ret = OMX_TRUE; |
0b9f280f | 495 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "input buffer has not come after flush."); |
20d3e6e3 JC |
496 | goto EXIT; |
497 | } | |
498 | ||
38ef2572 JC |
499 | if ((exynosOutputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { |
500 | if (dstOutputData->remainDataLen <= (outputUseBuffer->allocSize - outputUseBuffer->dataLen)) { | |
501 | copySize = dstOutputData->remainDataLen; | |
502 | if (copySize > 0) | |
503 | Exynos_OSAL_Memcpy((outputUseBuffer->bufferHeader->pBuffer + outputUseBuffer->dataLen), | |
504 | (dstOutputData->buffer.singlePlaneBuffer.dataBuffer + dstOutputData->usedDataLen), | |
505 | copySize); | |
506 | outputUseBuffer->dataLen += copySize; | |
507 | outputUseBuffer->remainDataLen += copySize; | |
508 | outputUseBuffer->nFlags = dstOutputData->nFlags; | |
509 | outputUseBuffer->timeStamp = dstOutputData->timeStamp; | |
20d3e6e3 | 510 | |
38ef2572 | 511 | ret = OMX_TRUE; |
20d3e6e3 | 512 | |
38ef2572 JC |
513 | if ((outputUseBuffer->remainDataLen > 0) || |
514 | (outputUseBuffer->nFlags & OMX_BUFFERFLAG_EOS)) { | |
38ef2572 | 515 | Exynos_OutputBufferReturn(pOMXComponent); |
38ef2572 JC |
516 | } |
517 | } else { | |
518 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "output buffer is smaller than encoded data size Out Length"); | |
519 | pExynosComponent->pCallbacks->EventHandler((OMX_HANDLETYPE)pOMXComponent, | |
520 | pExynosComponent->callbackData, | |
521 | OMX_EventError, OMX_ErrorUndefined, 0, NULL); | |
522 | ret = OMX_FALSE; | |
38ef2572 JC |
523 | } |
524 | } else if (exynosOutputPort->bufferProcessType == BUFFER_SHARE) { | |
20d3e6e3 | 525 | if ((outputUseBuffer->remainDataLen > 0) || |
44025235 | 526 | ((outputUseBuffer->nFlags & OMX_BUFFERFLAG_EOS) == OMX_BUFFERFLAG_EOS) || |
38ef2572 | 527 | (CHECK_PORT_BEING_FLUSHED(exynosOutputPort))) |
20d3e6e3 | 528 | Exynos_OutputBufferReturn(pOMXComponent); |
38ef2572 JC |
529 | } |
530 | } else { | |
531 | ret = OMX_FALSE; | |
532 | } | |
533 | ||
534 | EXIT: | |
535 | FunctionOut(); | |
536 | ||
537 | return ret; | |
538 | } | |
539 | ||
33d6044e SK |
540 | #ifdef USE_METADATABUFFERTYPE |
541 | OMX_ERRORTYPE Exynos_OMX_ExtensionSetup(OMX_HANDLETYPE hComponent) | |
542 | { | |
543 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
544 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
545 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
546 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
547 | EXYNOS_OMX_BASEPORT *exynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; | |
548 | EXYNOS_OMX_DATABUFFER *srcInputUseBuffer = &exynosInputPort->way.port2WayDataBuffer.inputDataBuffer; | |
549 | EXYNOS_OMX_DATA *pSrcInputData = &exynosInputPort->processData; | |
550 | OMX_COLOR_FORMATTYPE eColorFormat = exynosInputPort->portDefinition.format.video.eColorFormat; | |
551 | ||
552 | int i = 0; | |
553 | OMX_PTR ppBuf[MAX_BUFFER_PLANE]; | |
554 | ||
555 | ||
556 | /* kMetadataBufferTypeGrallocSource */ | |
557 | if (exynosInputPort->bStoreMetaData == OMX_TRUE) { | |
558 | Exynos_OSAL_GetInfoFromMetaData((OMX_BYTE)srcInputUseBuffer->bufferHeader->pBuffer, ppBuf); | |
559 | if (eColorFormat == OMX_COLOR_FormatAndroidOpaque) { | |
560 | pVideoEnc->ANBColorFormat = Exynos_OSAL_GetANBColorFormat(ppBuf[0]); | |
561 | if ((pVideoEnc->ANBColorFormat == OMX_COLOR_FormatYUV420SemiPlanar) || | |
562 | (pVideoEnc->ANBColorFormat == OMX_SEC_COLOR_FormatNV12Tiled)) { | |
563 | exynosInputPort->bufferProcessType = BUFFER_SHARE; | |
564 | } else { | |
565 | exynosInputPort->bufferProcessType = BUFFER_COPY; | |
566 | } | |
567 | ||
568 | if ((exynosInputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { | |
569 | Exynos_OSAL_SemaphoreCreate(&exynosInputPort->codecSemID); | |
570 | Exynos_OSAL_QueueCreate(&exynosInputPort->codecBufferQ, MAX_QUEUE_ELEMENTS); | |
571 | ||
572 | for (i = 0; i < MFC_INPUT_BUFFER_NUM_MAX; i++) { | |
573 | pVideoEnc->pMFCEncInputBuffer[i] = Exynos_OSAL_Malloc(sizeof(CODEC_ENC_BUFFER)); | |
574 | /* Use ION Allocator */ | |
575 | /*Alloc Y-Buffer */ | |
576 | pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[0] = (void *)Exynos_OSAL_SharedMemory_Alloc(pVideoEnc->hSharedMemory, DEFAULT_MFC_INPUT_YBUFFER_SIZE, NORMAL_MEMORY); | |
577 | pVideoEnc->pMFCEncInputBuffer[i]->fd[0] = Exynos_OSAL_SharedMemory_VirtToION(pVideoEnc->hSharedMemory, pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[0]); | |
578 | pVideoEnc->pMFCEncInputBuffer[i]->bufferSize[0] = DEFAULT_MFC_INPUT_YBUFFER_SIZE; | |
579 | /*Alloc C-Buffer */ | |
580 | pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[1] = (void *)Exynos_OSAL_SharedMemory_Alloc(pVideoEnc->hSharedMemory, DEFAULT_MFC_INPUT_CBUFFER_SIZE, NORMAL_MEMORY); | |
581 | pVideoEnc->pMFCEncInputBuffer[i]->fd[1] = Exynos_OSAL_SharedMemory_VirtToION(pVideoEnc->hSharedMemory, pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[1]); | |
582 | pVideoEnc->pMFCEncInputBuffer[i]->bufferSize[1] = DEFAULT_MFC_INPUT_CBUFFER_SIZE; | |
583 | ||
584 | pVideoEnc->pMFCEncInputBuffer[i]->dataSize = 0; | |
585 | ||
586 | if ((pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[0] == NULL) || | |
587 | (pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[1] == NULL)) { | |
588 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Fail input buffer"); | |
589 | ret = OMX_ErrorInsufficientResources; | |
590 | goto EXIT; | |
591 | } | |
592 | ||
593 | /* MFC input buffers are 1 plane. */ | |
594 | pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[2] = NULL; | |
595 | pVideoEnc->pMFCEncInputBuffer[i]->fd[2] = -1; | |
596 | pVideoEnc->pMFCEncInputBuffer[i]->bufferSize[2] = 0; | |
597 | ||
2db7dad2 GH |
598 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoEnc->pMFCEncInputBuffer[%d]: 0x%x", i, pVideoEnc->pMFCEncInputBuffer[i]); |
599 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoEnc->pMFCEncInputBuffer[%d]->pVirAddr[0]: 0x%x", i, pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[0]); | |
600 | Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "pVideoEnc->pMFCEncInputBuffer[%d]->pVirAddr[1]: 0x%x", i, pVideoEnc->pMFCEncInputBuffer[i]->pVirAddr[1]); | |
33d6044e SK |
601 | |
602 | Exynos_CodecBufferEnQueue(pExynosComponent, INPUT_PORT_INDEX, pVideoEnc->pMFCEncInputBuffer[i]); | |
603 | } | |
604 | } else if (exynosInputPort->bufferProcessType == BUFFER_SHARE) { | |
605 | /*************/ | |
606 | /* TBD */ | |
607 | /*************/ | |
608 | /* Does not require any actions. */ | |
609 | } | |
610 | } | |
611 | } | |
612 | ||
613 | ||
614 | EXIT: | |
615 | ||
616 | return ret; | |
617 | } | |
618 | #endif | |
619 | ||
38ef2572 JC |
620 | OMX_ERRORTYPE Exynos_OMX_SrcInputBufferProcess(OMX_HANDLETYPE hComponent) |
621 | { | |
622 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
623 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
624 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
625 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
626 | EXYNOS_OMX_BASEPORT *exynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; | |
627 | EXYNOS_OMX_DATABUFFER *srcInputUseBuffer = &exynosInputPort->way.port2WayDataBuffer.inputDataBuffer; | |
628 | EXYNOS_OMX_DATA *pSrcInputData = &exynosInputPort->processData; | |
629 | OMX_BOOL bCheckInputData = OMX_FALSE; | |
630 | OMX_BOOL bValidCodecData = OMX_FALSE; | |
631 | ||
632 | FunctionIn(); | |
633 | ||
634 | while (!pVideoEnc->bExitBufferProcessThread) { | |
635 | Exynos_OSAL_SleepMillisec(0); | |
636 | Exynos_Wait_ProcessPause(pExynosComponent, INPUT_PORT_INDEX); | |
637 | ||
638 | while ((Exynos_Check_BufferProcess_State(pExynosComponent, INPUT_PORT_INDEX)) && | |
639 | (!pVideoEnc->bExitBufferProcessThread)) { | |
640 | Exynos_OSAL_SleepMillisec(0); | |
641 | ||
642 | if (CHECK_PORT_BEING_FLUSHED(exynosInputPort)) | |
643 | break; | |
644 | if (exynosInputPort->portState != OMX_StateIdle) | |
645 | break; | |
646 | ||
647 | Exynos_OSAL_MutexLock(srcInputUseBuffer->bufferMutex); | |
33d6044e SK |
648 | if (pVideoEnc->bFirstInput == OMX_FALSE) { |
649 | if ((exynosInputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { | |
650 | OMX_PTR codecBuffer; | |
651 | if ((pSrcInputData->buffer.multiPlaneBuffer.dataBuffer[0] == NULL) || (pSrcInputData->pPrivate == NULL)) { | |
652 | Exynos_CodecBufferDeQueue(pExynosComponent, INPUT_PORT_INDEX, &codecBuffer); | |
653 | if (codecBuffer != NULL) { | |
654 | Exynos_Input_CodecBufferToData(pExynosComponent, codecBuffer, pSrcInputData); | |
655 | } | |
656 | Exynos_OSAL_MutexUnlock(srcInputUseBuffer->bufferMutex); | |
657 | break; | |
38ef2572 | 658 | } |
38ef2572 | 659 | } |
38ef2572 | 660 | |
33d6044e SK |
661 | if (srcInputUseBuffer->dataValid == OMX_TRUE) { |
662 | bCheckInputData = Exynos_Preprocessor_InputData(pOMXComponent, pSrcInputData); | |
663 | } else { | |
664 | bCheckInputData = OMX_FALSE; | |
665 | } | |
38ef2572 | 666 | } |
38ef2572 JC |
667 | if ((bCheckInputData == OMX_FALSE) && |
668 | (!CHECK_PORT_BEING_FLUSHED(exynosInputPort))) { | |
669 | ret = Exynos_InputBufferGetQueue(pExynosComponent); | |
33d6044e | 670 | #ifdef USE_METADATABUFFERTYPE |
af4568d1 SK |
671 | if ((pVideoEnc->bFirstInput == OMX_TRUE) && |
672 | (!CHECK_PORT_BEING_FLUSHED(exynosInputPort))) { | |
33d6044e SK |
673 | Exynos_OMX_ExtensionSetup(hComponent); |
674 | pVideoEnc->bFirstInput = OMX_FALSE; | |
675 | } | |
676 | #endif | |
38ef2572 JC |
677 | Exynos_OSAL_MutexUnlock(srcInputUseBuffer->bufferMutex); |
678 | break; | |
679 | } | |
680 | ||
681 | if (CHECK_PORT_BEING_FLUSHED(exynosInputPort)) { | |
682 | Exynos_OSAL_MutexUnlock(srcInputUseBuffer->bufferMutex); | |
683 | break; | |
684 | } | |
685 | ||
686 | ret = pVideoEnc->exynos_codec_srcInputProcess(pOMXComponent, pSrcInputData); | |
687 | Exynos_ResetCodecData(pSrcInputData); | |
688 | Exynos_OSAL_MutexUnlock(srcInputUseBuffer->bufferMutex); | |
38ef2572 JC |
689 | if (ret == OMX_ErrorCodecInit) |
690 | pVideoEnc->bExitBufferProcessThread = OMX_TRUE; | |
691 | } | |
692 | } | |
693 | ||
694 | EXIT: | |
695 | ||
696 | FunctionOut(); | |
697 | ||
698 | return ret; | |
699 | } | |
700 | ||
701 | OMX_ERRORTYPE Exynos_OMX_SrcOutputBufferProcess(OMX_HANDLETYPE hComponent) | |
702 | { | |
703 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
704 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
705 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
706 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
707 | EXYNOS_OMX_BASEPORT *exynosInputPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; | |
708 | EXYNOS_OMX_DATABUFFER *srcOutputUseBuffer = &exynosInputPort->way.port2WayDataBuffer.outputDataBuffer; | |
709 | EXYNOS_OMX_DATA srcOutputData; | |
710 | ||
711 | FunctionIn(); | |
712 | ||
713 | while (!pVideoEnc->bExitBufferProcessThread) { | |
714 | Exynos_OSAL_SleepMillisec(0); | |
715 | ||
716 | while (!pVideoEnc->bExitBufferProcessThread) { | |
717 | if ((exynosInputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { | |
718 | if (Exynos_Check_BufferProcess_State(pExynosComponent, INPUT_PORT_INDEX) == OMX_FALSE) | |
719 | break; | |
720 | } | |
721 | Exynos_OSAL_SleepMillisec(0); | |
722 | ||
723 | if (CHECK_PORT_BEING_FLUSHED(exynosInputPort)) | |
724 | break; | |
725 | ||
726 | Exynos_OSAL_MutexLock(srcOutputUseBuffer->bufferMutex); | |
727 | ret = pVideoEnc->exynos_codec_srcOutputProcess(pOMXComponent, &srcOutputData); | |
20d3e6e3 | 728 | |
38ef2572 JC |
729 | if (ret == OMX_ErrorNone) { |
730 | if ((exynosInputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { | |
731 | OMX_PTR codecBuffer; | |
732 | codecBuffer = srcOutputData.pPrivate; | |
733 | if (codecBuffer != NULL) | |
734 | Exynos_CodecBufferEnQueue(pExynosComponent, INPUT_PORT_INDEX, codecBuffer); | |
735 | } | |
38ef2572 JC |
736 | if (exynosInputPort->bufferProcessType == BUFFER_SHARE) { |
737 | Exynos_Shared_DataToBuffer(&srcOutputData, srcOutputUseBuffer); | |
738 | Exynos_InputBufferReturn(pOMXComponent); | |
739 | } | |
740 | Exynos_ResetCodecData(&srcOutputData); | |
741 | } | |
742 | Exynos_OSAL_MutexUnlock(srcOutputUseBuffer->bufferMutex); | |
20d3e6e3 | 743 | } |
20d3e6e3 JC |
744 | } |
745 | ||
746 | EXIT: | |
38ef2572 JC |
747 | |
748 | FunctionOut(); | |
749 | ||
20d3e6e3 JC |
750 | return ret; |
751 | } | |
752 | ||
38ef2572 | 753 | OMX_ERRORTYPE Exynos_OMX_DstInputBufferProcess(OMX_HANDLETYPE hComponent) |
20d3e6e3 | 754 | { |
38ef2572 JC |
755 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
756 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
757 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
20d3e6e3 | 758 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; |
38ef2572 JC |
759 | EXYNOS_OMX_BASEPORT *exynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]; |
760 | EXYNOS_OMX_DATABUFFER *dstInputUseBuffer = &exynosOutputPort->way.port2WayDataBuffer.inputDataBuffer; | |
761 | EXYNOS_OMX_DATA dstInputData; | |
762 | ||
20d3e6e3 JC |
763 | FunctionIn(); |
764 | ||
38ef2572 | 765 | while (!pVideoEnc->bExitBufferProcessThread) { |
20d3e6e3 JC |
766 | Exynos_OSAL_SleepMillisec(0); |
767 | ||
38ef2572 JC |
768 | while ((Exynos_Check_BufferProcess_State(pExynosComponent, OUTPUT_PORT_INDEX)) && |
769 | (!pVideoEnc->bExitBufferProcessThread)) { | |
20d3e6e3 JC |
770 | Exynos_OSAL_SleepMillisec(0); |
771 | ||
38ef2572 JC |
772 | if ((CHECK_PORT_BEING_FLUSHED(exynosOutputPort)) || |
773 | (!CHECK_PORT_POPULATED(exynosOutputPort))) | |
774 | break; | |
775 | if (exynosOutputPort->portState != OMX_StateIdle) | |
776 | break; | |
777 | ||
778 | Exynos_OSAL_MutexLock(dstInputUseBuffer->bufferMutex); | |
779 | if ((exynosOutputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { | |
780 | OMX_PTR codecBuffer; | |
781 | ret = Exynos_CodecBufferDeQueue(pExynosComponent, OUTPUT_PORT_INDEX, &codecBuffer); | |
782 | if (ret != OMX_ErrorNone) { | |
783 | Exynos_OSAL_MutexUnlock(dstInputUseBuffer->bufferMutex); | |
20d3e6e3 JC |
784 | break; |
785 | } | |
38ef2572 | 786 | Exynos_Output_CodecBufferToData(pExynosComponent, codecBuffer, &dstInputData); |
20d3e6e3 JC |
787 | } |
788 | ||
38ef2572 JC |
789 | if (exynosOutputPort->bufferProcessType == BUFFER_SHARE) { |
790 | if ((dstInputUseBuffer->dataValid != OMX_TRUE) && | |
791 | (!CHECK_PORT_BEING_FLUSHED(exynosOutputPort))) { | |
792 | ret = Exynos_OutputBufferGetQueue(pExynosComponent); | |
793 | if (ret != OMX_ErrorNone) { | |
794 | Exynos_OSAL_MutexUnlock(dstInputUseBuffer->bufferMutex); | |
d03573a4 | 795 | break; |
20d3e6e3 | 796 | } |
38ef2572 JC |
797 | Exynos_Shared_BufferToData(dstInputUseBuffer, &dstInputData, ONE_PLANE); |
798 | Exynos_ResetDataBuffer(dstInputUseBuffer); | |
20d3e6e3 | 799 | } |
20d3e6e3 JC |
800 | } |
801 | ||
38ef2572 JC |
802 | if (CHECK_PORT_BEING_FLUSHED(exynosOutputPort)) { |
803 | Exynos_OSAL_MutexUnlock(dstInputUseBuffer->bufferMutex); | |
804 | break; | |
805 | } | |
806 | ret = pVideoEnc->exynos_codec_dstInputProcess(pOMXComponent, &dstInputData); | |
20d3e6e3 | 807 | |
38ef2572 JC |
808 | Exynos_ResetCodecData(&dstInputData); |
809 | Exynos_OSAL_MutexUnlock(dstInputUseBuffer->bufferMutex); | |
20d3e6e3 JC |
810 | } |
811 | } | |
812 | ||
813 | EXIT: | |
38ef2572 | 814 | |
20d3e6e3 JC |
815 | FunctionOut(); |
816 | ||
817 | return ret; | |
818 | } | |
819 | ||
38ef2572 | 820 | OMX_ERRORTYPE Exynos_OMX_DstOutputBufferProcess(OMX_HANDLETYPE hComponent) |
20d3e6e3 | 821 | { |
38ef2572 JC |
822 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
823 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
824 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
825 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
826 | EXYNOS_OMX_BASEPORT *exynosOutputPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]; | |
827 | EXYNOS_OMX_DATABUFFER *dstOutputUseBuffer = &exynosOutputPort->way.port2WayDataBuffer.outputDataBuffer; | |
828 | EXYNOS_OMX_DATA *pDstOutputData = &exynosOutputPort->processData; | |
829 | ||
20d3e6e3 JC |
830 | FunctionIn(); |
831 | ||
38ef2572 JC |
832 | while (!pVideoEnc->bExitBufferProcessThread) { |
833 | Exynos_OSAL_SleepMillisec(0); | |
834 | Exynos_Wait_ProcessPause(pExynosComponent, OUTPUT_PORT_INDEX); | |
20d3e6e3 | 835 | |
38ef2572 JC |
836 | while ((Exynos_Check_BufferProcess_State(pExynosComponent, OUTPUT_PORT_INDEX)) && |
837 | (!pVideoEnc->bExitBufferProcessThread)) { | |
838 | Exynos_OSAL_SleepMillisec(0); | |
20d3e6e3 | 839 | |
38ef2572 JC |
840 | if (CHECK_PORT_BEING_FLUSHED(exynosOutputPort)) |
841 | break; | |
20d3e6e3 | 842 | |
38ef2572 JC |
843 | Exynos_OSAL_MutexLock(dstOutputUseBuffer->bufferMutex); |
844 | if ((exynosOutputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { | |
845 | if ((dstOutputUseBuffer->dataValid != OMX_TRUE) && | |
846 | (!CHECK_PORT_BEING_FLUSHED(exynosOutputPort))) { | |
847 | ret = Exynos_OutputBufferGetQueue(pExynosComponent); | |
848 | if (ret != OMX_ErrorNone) { | |
849 | Exynos_OSAL_MutexUnlock(dstOutputUseBuffer->bufferMutex); | |
850 | break; | |
851 | } | |
852 | } | |
20d3e6e3 JC |
853 | } |
854 | ||
38ef2572 JC |
855 | if ((dstOutputUseBuffer->dataValid == OMX_TRUE) || |
856 | (exynosOutputPort->bufferProcessType == BUFFER_SHARE)) | |
857 | ret = pVideoEnc->exynos_codec_dstOutputProcess(pOMXComponent, pDstOutputData); | |
20d3e6e3 | 858 | |
38ef2572 JC |
859 | if (((ret == OMX_ErrorNone) && (dstOutputUseBuffer->dataValid == OMX_TRUE)) || |
860 | (exynosOutputPort->bufferProcessType == BUFFER_SHARE)) { | |
861 | Exynos_Postprocess_OutputData(pOMXComponent, pDstOutputData); | |
20d3e6e3 JC |
862 | } |
863 | ||
38ef2572 JC |
864 | if ((exynosOutputPort->bufferProcessType & BUFFER_COPY) == BUFFER_COPY) { |
865 | OMX_PTR codecBuffer; | |
38ef2572 JC |
866 | codecBuffer = pDstOutputData->pPrivate; |
867 | if (codecBuffer != NULL) { | |
868 | Exynos_CodecBufferEnQueue(pExynosComponent, OUTPUT_PORT_INDEX, codecBuffer); | |
869 | pDstOutputData->pPrivate = NULL; | |
870 | } | |
871 | } | |
20d3e6e3 | 872 | |
38ef2572 JC |
873 | /* reset outputData */ |
874 | Exynos_ResetCodecData(pDstOutputData); | |
875 | Exynos_OSAL_MutexUnlock(dstOutputUseBuffer->bufferMutex); | |
20d3e6e3 | 876 | } |
20d3e6e3 JC |
877 | } |
878 | ||
879 | EXIT: | |
38ef2572 | 880 | |
20d3e6e3 JC |
881 | FunctionOut(); |
882 | ||
883 | return ret; | |
884 | } | |
38ef2572 JC |
885 | |
886 | static OMX_ERRORTYPE Exynos_OMX_SrcInputProcessThread(OMX_PTR threadData) | |
20d3e6e3 | 887 | { |
38ef2572 JC |
888 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
889 | OMX_COMPONENTTYPE *pOMXComponent = NULL; | |
20d3e6e3 | 890 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL; |
38ef2572 | 891 | EXYNOS_OMX_MESSAGE *message = NULL; |
20d3e6e3 JC |
892 | |
893 | FunctionIn(); | |
894 | ||
38ef2572 | 895 | if (threadData == NULL) { |
20d3e6e3 JC |
896 | ret = OMX_ErrorBadParameter; |
897 | goto EXIT; | |
898 | } | |
38ef2572 | 899 | pOMXComponent = (OMX_COMPONENTTYPE *)threadData; |
20d3e6e3 JC |
900 | ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE)); |
901 | if (ret != OMX_ErrorNone) { | |
902 | goto EXIT; | |
903 | } | |
20d3e6e3 | 904 | pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; |
38ef2572 | 905 | Exynos_OMX_SrcInputBufferProcess(pOMXComponent); |
20d3e6e3 | 906 | |
38ef2572 | 907 | Exynos_OSAL_ThreadExit(NULL); |
20d3e6e3 | 908 | |
38ef2572 JC |
909 | EXIT: |
910 | FunctionOut(); | |
20d3e6e3 | 911 | |
38ef2572 JC |
912 | return ret; |
913 | } | |
20d3e6e3 | 914 | |
38ef2572 JC |
915 | static OMX_ERRORTYPE Exynos_OMX_SrcOutputProcessThread(OMX_PTR threadData) |
916 | { | |
917 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
918 | OMX_COMPONENTTYPE *pOMXComponent = NULL; | |
919 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL; | |
920 | EXYNOS_OMX_MESSAGE *message = NULL; | |
20d3e6e3 | 921 | |
38ef2572 | 922 | FunctionIn(); |
20d3e6e3 | 923 | |
38ef2572 JC |
924 | if (threadData == NULL) { |
925 | ret = OMX_ErrorBadParameter; | |
926 | goto EXIT; | |
20d3e6e3 | 927 | } |
38ef2572 JC |
928 | pOMXComponent = (OMX_COMPONENTTYPE *)threadData; |
929 | ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE)); | |
930 | if (ret != OMX_ErrorNone) { | |
931 | goto EXIT; | |
20d3e6e3 | 932 | } |
38ef2572 JC |
933 | pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; |
934 | Exynos_OMX_SrcOutputBufferProcess(pOMXComponent); | |
20d3e6e3 | 935 | |
38ef2572 | 936 | Exynos_OSAL_ThreadExit(NULL); |
20d3e6e3 JC |
937 | |
938 | EXIT: | |
939 | FunctionOut(); | |
940 | ||
941 | return ret; | |
942 | } | |
943 | ||
38ef2572 | 944 | static OMX_ERRORTYPE Exynos_OMX_DstInputProcessThread(OMX_PTR threadData) |
20d3e6e3 | 945 | { |
38ef2572 JC |
946 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
947 | OMX_COMPONENTTYPE *pOMXComponent = NULL; | |
20d3e6e3 | 948 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL; |
38ef2572 | 949 | EXYNOS_OMX_MESSAGE *message = NULL; |
20d3e6e3 JC |
950 | |
951 | FunctionIn(); | |
952 | ||
38ef2572 | 953 | if (threadData == NULL) { |
20d3e6e3 JC |
954 | ret = OMX_ErrorBadParameter; |
955 | goto EXIT; | |
956 | } | |
38ef2572 | 957 | pOMXComponent = (OMX_COMPONENTTYPE *)threadData; |
20d3e6e3 JC |
958 | ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE)); |
959 | if (ret != OMX_ErrorNone) { | |
960 | goto EXIT; | |
961 | } | |
20d3e6e3 | 962 | pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; |
38ef2572 | 963 | Exynos_OMX_DstInputBufferProcess(pOMXComponent); |
20d3e6e3 | 964 | |
38ef2572 | 965 | Exynos_OSAL_ThreadExit(NULL); |
20d3e6e3 JC |
966 | |
967 | EXIT: | |
968 | FunctionOut(); | |
969 | ||
970 | return ret; | |
971 | } | |
972 | ||
38ef2572 JC |
973 | static OMX_ERRORTYPE Exynos_OMX_DstOutputProcessThread(OMX_PTR threadData) |
974 | { | |
975 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
976 | OMX_COMPONENTTYPE *pOMXComponent = NULL; | |
20d3e6e3 | 977 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL; |
38ef2572 | 978 | EXYNOS_OMX_MESSAGE *message = NULL; |
20d3e6e3 JC |
979 | |
980 | FunctionIn(); | |
981 | ||
38ef2572 | 982 | if (threadData == NULL) { |
20d3e6e3 JC |
983 | ret = OMX_ErrorBadParameter; |
984 | goto EXIT; | |
985 | } | |
38ef2572 | 986 | pOMXComponent = (OMX_COMPONENTTYPE *)threadData; |
20d3e6e3 JC |
987 | ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE)); |
988 | if (ret != OMX_ErrorNone) { | |
989 | goto EXIT; | |
990 | } | |
20d3e6e3 | 991 | pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; |
38ef2572 | 992 | Exynos_OMX_DstOutputBufferProcess(pOMXComponent); |
20d3e6e3 | 993 | |
38ef2572 | 994 | Exynos_OSAL_ThreadExit(NULL); |
20d3e6e3 JC |
995 | |
996 | EXIT: | |
997 | FunctionOut(); | |
998 | ||
999 | return ret; | |
1000 | } | |
1001 | ||
38ef2572 | 1002 | OMX_ERRORTYPE Exynos_OMX_BufferProcess_Create(OMX_HANDLETYPE hComponent) |
20d3e6e3 | 1003 | { |
38ef2572 JC |
1004 | OMX_ERRORTYPE ret = OMX_ErrorNone; |
1005 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
1006 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
1007 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
20d3e6e3 JC |
1008 | |
1009 | FunctionIn(); | |
1010 | ||
38ef2572 JC |
1011 | pVideoEnc->bExitBufferProcessThread = OMX_FALSE; |
1012 | ||
1013 | ret = Exynos_OSAL_ThreadCreate(&pVideoEnc->hDstOutputThread, | |
1014 | Exynos_OMX_DstOutputProcessThread, | |
1015 | pOMXComponent); | |
1016 | if (ret == OMX_ErrorNone) | |
1017 | ret = Exynos_OSAL_ThreadCreate(&pVideoEnc->hSrcOutputThread, | |
1018 | Exynos_OMX_SrcOutputProcessThread, | |
1019 | pOMXComponent); | |
1020 | if (ret == OMX_ErrorNone) | |
1021 | ret = Exynos_OSAL_ThreadCreate(&pVideoEnc->hDstInputThread, | |
1022 | Exynos_OMX_DstInputProcessThread, | |
1023 | pOMXComponent); | |
1024 | if (ret == OMX_ErrorNone) | |
1025 | ret = Exynos_OSAL_ThreadCreate(&pVideoEnc->hSrcInputThread, | |
1026 | Exynos_OMX_SrcInputProcessThread, | |
1027 | pOMXComponent); | |
20d3e6e3 | 1028 | |
38ef2572 JC |
1029 | EXIT: |
1030 | FunctionOut(); | |
20d3e6e3 | 1031 | |
38ef2572 JC |
1032 | return ret; |
1033 | } | |
20d3e6e3 | 1034 | |
38ef2572 JC |
1035 | OMX_ERRORTYPE Exynos_OMX_BufferProcess_Terminate(OMX_HANDLETYPE hComponent) |
1036 | { | |
1037 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
1038 | OMX_COMPONENTTYPE *pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
1039 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
1040 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
1041 | OMX_S32 countValue = 0; | |
1042 | unsigned int i = 0; | |
1043 | ||
1044 | FunctionIn(); | |
1045 | ||
1046 | pVideoEnc->bExitBufferProcessThread = OMX_TRUE; | |
1047 | ||
1048 | Exynos_OSAL_Get_SemaphoreCount(pExynosComponent->pExynosPort[INPUT_PORT_INDEX].bufferSemID, &countValue); | |
1049 | if (countValue == 0) | |
1050 | Exynos_OSAL_SemaphorePost(pExynosComponent->pExynosPort[INPUT_PORT_INDEX].bufferSemID); | |
1051 | Exynos_OSAL_Get_SemaphoreCount(pExynosComponent->pExynosPort[INPUT_PORT_INDEX].codecSemID, &countValue); | |
1052 | if (countValue == 0) | |
1053 | Exynos_OSAL_SemaphorePost(pExynosComponent->pExynosPort[INPUT_PORT_INDEX].codecSemID); | |
1054 | Exynos_OSAL_SignalSet(pExynosComponent->pExynosPort[INPUT_PORT_INDEX].pauseEvent); | |
1055 | Exynos_OSAL_ThreadTerminate(pVideoEnc->hSrcInputThread); | |
1056 | pVideoEnc->hSrcInputThread = NULL; | |
1057 | ||
1058 | Exynos_OSAL_Get_SemaphoreCount(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX].bufferSemID, &countValue); | |
1059 | if (countValue == 0) | |
1060 | Exynos_OSAL_SemaphorePost(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX].bufferSemID); | |
1061 | Exynos_OSAL_Get_SemaphoreCount(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX].codecSemID, &countValue); | |
1062 | if (countValue == 0) | |
1063 | Exynos_OSAL_SemaphorePost(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX].codecSemID); | |
1064 | Exynos_OSAL_SignalSet(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX].pauseEvent); | |
1065 | Exynos_OSAL_ThreadTerminate(pVideoEnc->hDstInputThread); | |
1066 | pVideoEnc->hDstInputThread = NULL; | |
1067 | ||
38ef2572 JC |
1068 | pVideoEnc->exynos_codec_stop(pOMXComponent, INPUT_PORT_INDEX); |
1069 | pVideoEnc->exynos_codec_bufferProcessRun(pOMXComponent, INPUT_PORT_INDEX); | |
1070 | Exynos_OSAL_SignalSet(pExynosComponent->pExynosPort[INPUT_PORT_INDEX].pauseEvent); | |
1071 | Exynos_OSAL_ThreadTerminate(pVideoEnc->hSrcOutputThread); | |
1072 | pVideoEnc->hSrcOutputThread = NULL; | |
1073 | ||
38ef2572 JC |
1074 | pVideoEnc->exynos_codec_stop(pOMXComponent, OUTPUT_PORT_INDEX); |
1075 | pVideoEnc->exynos_codec_bufferProcessRun(pOMXComponent, INPUT_PORT_INDEX); | |
1076 | Exynos_OSAL_SignalSet(pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX].pauseEvent); | |
1077 | Exynos_OSAL_ThreadTerminate(pVideoEnc->hDstOutputThread); | |
1078 | pVideoEnc->hDstOutputThread = NULL; | |
20d3e6e3 JC |
1079 | |
1080 | EXIT: | |
1081 | FunctionOut(); | |
1082 | ||
1083 | return ret; | |
1084 | } | |
1085 | ||
1086 | OMX_ERRORTYPE Exynos_OMX_VideoEncodeComponentInit(OMX_IN OMX_HANDLETYPE hComponent) | |
1087 | { | |
1088 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
1089 | OMX_COMPONENTTYPE *pOMXComponent = NULL; | |
1090 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL; | |
1091 | EXYNOS_OMX_BASEPORT *pExynosPort = NULL; | |
1092 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = NULL; | |
1093 | ||
cf091479 GH |
1094 | CSC_METHOD csc_method = CSC_METHOD_SW; |
1095 | ||
20d3e6e3 JC |
1096 | FunctionIn(); |
1097 | ||
1098 | if (hComponent == NULL) { | |
1099 | ret = OMX_ErrorBadParameter; | |
1100 | goto EXIT; | |
1101 | } | |
1102 | pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
1103 | ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE)); | |
1104 | if (ret != OMX_ErrorNone) { | |
1105 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_Error, Line:%d", __LINE__); | |
1106 | goto EXIT; | |
1107 | } | |
1108 | ||
1109 | ret = Exynos_OMX_BaseComponent_Constructor(pOMXComponent); | |
1110 | if (ret != OMX_ErrorNone) { | |
1111 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_Error, Line:%d", __LINE__); | |
1112 | goto EXIT; | |
1113 | } | |
1114 | ||
1115 | ret = Exynos_OMX_Port_Constructor(pOMXComponent); | |
1116 | if (ret != OMX_ErrorNone) { | |
1117 | Exynos_OMX_BaseComponent_Destructor(pOMXComponent); | |
1118 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_Error, Line:%d", __LINE__); | |
1119 | goto EXIT; | |
1120 | } | |
1121 | ||
1122 | pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
1123 | ||
1124 | pVideoEnc = Exynos_OSAL_Malloc(sizeof(EXYNOS_OMX_VIDEOENC_COMPONENT)); | |
1125 | if (pVideoEnc == NULL) { | |
1126 | Exynos_OMX_BaseComponent_Destructor(pOMXComponent); | |
1127 | ret = OMX_ErrorInsufficientResources; | |
1128 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorInsufficientResources, Line:%d", __LINE__); | |
1129 | goto EXIT; | |
1130 | } | |
1131 | ||
1132 | Exynos_OSAL_Memset(pVideoEnc, 0, sizeof(EXYNOS_OMX_VIDEOENC_COMPONENT)); | |
1133 | pExynosComponent->hComponentHandle = (OMX_HANDLETYPE)pVideoEnc; | |
1134 | ||
1135 | pExynosComponent->bSaveFlagEOS = OMX_FALSE; | |
1136 | ||
33d6044e SK |
1137 | pVideoEnc->bFirstInput = OMX_FALSE; |
1138 | pVideoEnc->bFirstOutput = OMX_FALSE; | |
20d3e6e3 | 1139 | pVideoEnc->configChange = OMX_FALSE; |
38ef2572 JC |
1140 | pVideoEnc->quantization.nQpI = 4; // I frame quantization parameter |
1141 | pVideoEnc->quantization.nQpP = 5; // P frame quantization parameter | |
1142 | pVideoEnc->quantization.nQpB = 5; // B frame quantization parameter | |
1143 | ||
cf091479 GH |
1144 | pVideoEnc->csc_handle = csc_init(csc_method); |
1145 | if (pVideoEnc->csc_handle == NULL) { | |
1146 | Exynos_OSAL_Free(pVideoEnc); | |
1147 | Exynos_OMX_BaseComponent_Destructor(pOMXComponent); | |
1148 | ret = OMX_ErrorInsufficientResources; | |
1149 | Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_ErrorInsufficientResources, Line:%d", __LINE__); | |
1150 | goto EXIT; | |
1151 | } | |
1152 | pVideoEnc->csc_set_format = OMX_FALSE; | |
fe7c2607 GH |
1153 | #if defined(USE_CSC_GSCALER) |
1154 | csc_set_hw_property(pVideoEnc->csc_handle, CSC_HW_PROPERTY_FIXED_NODE, CSC_GSCALER_IDX); | |
1155 | #endif | |
cf091479 | 1156 | |
38ef2572 | 1157 | pExynosComponent->bMultiThreadProcess = OMX_TRUE; |
20d3e6e3 JC |
1158 | |
1159 | /* Input port */ | |
1160 | pExynosPort = &pExynosComponent->pExynosPort[INPUT_PORT_INDEX]; | |
1161 | pExynosPort->portDefinition.nBufferCountActual = MAX_VIDEO_INPUTBUFFER_NUM; | |
1162 | pExynosPort->portDefinition.nBufferCountMin = MAX_VIDEO_INPUTBUFFER_NUM; | |
1163 | pExynosPort->portDefinition.nBufferSize = 0; | |
1164 | pExynosPort->portDefinition.eDomain = OMX_PortDomainVideo; | |
1165 | ||
1166 | pExynosPort->portDefinition.format.video.cMIMEType = Exynos_OSAL_Malloc(MAX_OMX_MIMETYPE_SIZE); | |
1167 | Exynos_OSAL_Strcpy(pExynosPort->portDefinition.format.video.cMIMEType, "raw/video"); | |
1168 | pExynosPort->portDefinition.format.video.pNativeRender = 0; | |
1169 | pExynosPort->portDefinition.format.video.bFlagErrorConcealment = OMX_FALSE; | |
1170 | pExynosPort->portDefinition.format.video.eCompressionFormat = OMX_VIDEO_CodingUnused; | |
1171 | ||
1172 | pExynosPort->portDefinition.format.video.nFrameWidth = 0; | |
1173 | pExynosPort->portDefinition.format.video.nFrameHeight= 0; | |
1174 | pExynosPort->portDefinition.format.video.nStride = 0; | |
1175 | pExynosPort->portDefinition.format.video.nSliceHeight = 0; | |
1176 | pExynosPort->portDefinition.format.video.nBitrate = 64000; | |
1177 | pExynosPort->portDefinition.format.video.xFramerate = (15 << 16); | |
1178 | pExynosPort->portDefinition.format.video.eColorFormat = OMX_COLOR_FormatUnused; | |
1179 | pExynosPort->portDefinition.format.video.pNativeWindow = NULL; | |
1180 | pVideoEnc->eControlRate[INPUT_PORT_INDEX] = OMX_Video_ControlRateDisable; | |
1181 | ||
1182 | pExynosPort->bStoreMetaData = OMX_FALSE; | |
1183 | ||
1184 | /* Output port */ | |
1185 | pExynosPort = &pExynosComponent->pExynosPort[OUTPUT_PORT_INDEX]; | |
1186 | pExynosPort->portDefinition.nBufferCountActual = MAX_VIDEO_OUTPUTBUFFER_NUM; | |
1187 | pExynosPort->portDefinition.nBufferCountMin = MAX_VIDEO_OUTPUTBUFFER_NUM; | |
1188 | pExynosPort->portDefinition.nBufferSize = DEFAULT_VIDEO_OUTPUT_BUFFER_SIZE; | |
1189 | pExynosPort->portDefinition.eDomain = OMX_PortDomainVideo; | |
1190 | ||
1191 | pExynosPort->portDefinition.format.video.cMIMEType = Exynos_OSAL_Malloc(MAX_OMX_MIMETYPE_SIZE); | |
1192 | Exynos_OSAL_Strcpy(pExynosPort->portDefinition.format.video.cMIMEType, "raw/video"); | |
1193 | pExynosPort->portDefinition.format.video.pNativeRender = 0; | |
1194 | pExynosPort->portDefinition.format.video.bFlagErrorConcealment = OMX_FALSE; | |
1195 | pExynosPort->portDefinition.format.video.eCompressionFormat = OMX_VIDEO_CodingUnused; | |
1196 | ||
1197 | pExynosPort->portDefinition.format.video.nFrameWidth = 0; | |
1198 | pExynosPort->portDefinition.format.video.nFrameHeight= 0; | |
1199 | pExynosPort->portDefinition.format.video.nStride = 0; | |
1200 | pExynosPort->portDefinition.format.video.nSliceHeight = 0; | |
1201 | pExynosPort->portDefinition.format.video.nBitrate = 64000; | |
1202 | pExynosPort->portDefinition.format.video.xFramerate = (15 << 16); | |
1203 | pExynosPort->portDefinition.format.video.eColorFormat = OMX_COLOR_FormatUnused; | |
1204 | pExynosPort->portDefinition.format.video.pNativeWindow = NULL; | |
1205 | pVideoEnc->eControlRate[OUTPUT_PORT_INDEX] = OMX_Video_ControlRateDisable; | |
1206 | ||
1207 | pOMXComponent->UseBuffer = &Exynos_OMX_UseBuffer; | |
1208 | pOMXComponent->AllocateBuffer = &Exynos_OMX_AllocateBuffer; | |
1209 | pOMXComponent->FreeBuffer = &Exynos_OMX_FreeBuffer; | |
1210 | pOMXComponent->ComponentTunnelRequest = &Exynos_OMX_ComponentTunnelRequest; | |
1211 | ||
1212 | pExynosComponent->exynos_AllocateTunnelBuffer = &Exynos_OMX_AllocateTunnelBuffer; | |
1213 | pExynosComponent->exynos_FreeTunnelBuffer = &Exynos_OMX_FreeTunnelBuffer; | |
38ef2572 JC |
1214 | pExynosComponent->exynos_BufferProcessCreate = &Exynos_OMX_BufferProcess_Create; |
1215 | pExynosComponent->exynos_BufferProcessTerminate = &Exynos_OMX_BufferProcess_Terminate; | |
1216 | pExynosComponent->exynos_BufferFlush = &Exynos_OMX_BufferFlush; | |
20d3e6e3 JC |
1217 | |
1218 | EXIT: | |
1219 | FunctionOut(); | |
1220 | ||
1221 | return ret; | |
1222 | } | |
1223 | ||
1224 | OMX_ERRORTYPE Exynos_OMX_VideoEncodeComponentDeinit(OMX_IN OMX_HANDLETYPE hComponent) | |
1225 | { | |
1226 | OMX_ERRORTYPE ret = OMX_ErrorNone; | |
1227 | OMX_COMPONENTTYPE *pOMXComponent = NULL; | |
1228 | EXYNOS_OMX_BASECOMPONENT *pExynosComponent = NULL; | |
1229 | EXYNOS_OMX_BASEPORT *pExynosPort = NULL; | |
1230 | EXYNOS_OMX_VIDEOENC_COMPONENT *pVideoEnc = NULL; | |
1231 | int i = 0; | |
1232 | ||
1233 | FunctionIn(); | |
1234 | ||
1235 | if (hComponent == NULL) { | |
1236 | ret = OMX_ErrorBadParameter; | |
1237 | goto EXIT; | |
1238 | } | |
1239 | pOMXComponent = (OMX_COMPONENTTYPE *)hComponent; | |
1240 | ret = Exynos_OMX_Check_SizeVersion(pOMXComponent, sizeof(OMX_COMPONENTTYPE)); | |
1241 | if (ret != OMX_ErrorNone) { | |
1242 | goto EXIT; | |
1243 | } | |
1244 | ||
1245 | if (pOMXComponent->pComponentPrivate == NULL) { | |
1246 | ret = OMX_ErrorBadParameter; | |
1247 | goto EXIT; | |
1248 | } | |
1249 | pExynosComponent = (EXYNOS_OMX_BASECOMPONENT *)pOMXComponent->pComponentPrivate; | |
1250 | ||
1251 | pVideoEnc = (EXYNOS_OMX_VIDEOENC_COMPONENT *)pExynosComponent->hComponentHandle; | |
38ef2572 | 1252 | |
cf091479 GH |
1253 | if (pVideoEnc->csc_handle != NULL) { |
1254 | csc_deinit(pVideoEnc->csc_handle); | |
1255 | pVideoEnc->csc_handle = NULL; | |
1256 | } | |
1257 | ||
20d3e6e3 JC |
1258 | Exynos_OSAL_Free(pVideoEnc); |
1259 | pExynosComponent->hComponentHandle = pVideoEnc = NULL; | |
1260 | ||
1261 | for(i = 0; i < ALL_PORT_NUM; i++) { | |
1262 | pExynosPort = &pExynosComponent->pExynosPort[i]; | |
1263 | Exynos_OSAL_Free(pExynosPort->portDefinition.format.video.cMIMEType); | |
1264 | pExynosPort->portDefinition.format.video.cMIMEType = NULL; | |
1265 | } | |
1266 | ||
1267 | ret = Exynos_OMX_Port_Destructor(pOMXComponent); | |
1268 | ||
1269 | ret = Exynos_OMX_BaseComponent_Destructor(hComponent); | |
1270 | ||
1271 | EXIT: | |
1272 | FunctionOut(); | |
1273 | ||
1274 | return ret; | |
1275 | } |