1 /*--------------------------------------------------------------------------
2 Copyright (c) 2010-2014, The Linux Foundation. All rights reserved.
3
4 Redistribution and use in source and binary forms, with or without
5 modification, are permitted provided that the following conditions are met:
6 * Redistributions of source code must retain the above copyright
7 notice, this list of conditions and the following disclaimer.
8 * Redistributions in binary form must reproduce the above copyright
9 notice, this list of conditions and the following disclaimer in the
10 documentation and/or other materials provided with the distribution.
11 * Neither the name of The Linux Foundation nor
12 the names of its contributors may be used to endorse or promote
13 products derived from this software without specific prior written
14 permission.
15
16 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19 NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
20 CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21 EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22 PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
23 OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
24 WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
25 OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
26 ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 --------------------------------------------------------------------------*/
28 #include "omx_swvenc_hevc.h"
29 #include <string.h>
30 #include <stdio.h>
31 #include <media/hardware/HardwareAPI.h>
32 #include <gralloc_priv.h>
33 #include <media/msm_media_info.h>
34
35 /*----------------------------------------------------------------------------
36 * Preprocessor Definitions and Constants
37 * -------------------------------------------------------------------------*/
38
39 #define OMX_SPEC_VERSION 0x00000101
40 #define OMX_INIT_STRUCT(_s_, _name_) \
41 memset((_s_), 0x0, sizeof(_name_)); \
42 (_s_)->nSize = sizeof(_name_); \
43 (_s_)->nVersion.nVersion = OMX_SPEC_VERSION
44
45 extern int m_pipe;
46
47 // factory function executed by the core to create instances
get_omx_component_factory_fn(void)48 void *get_omx_component_factory_fn(void)
49 {
50 return(new omx_swvenc);
51 }
52
53 //constructor
54
omx_swvenc()55 omx_swvenc::omx_swvenc()
56 {
57 #ifdef _ANDROID_ICS_
58 meta_mode_enable = false;
59 memset(meta_buffer_hdr,0,sizeof(meta_buffer_hdr));
60 memset(meta_buffers,0,sizeof(meta_buffers));
61 memset(opaque_buffer_hdr,0,sizeof(opaque_buffer_hdr));
62 mUseProxyColorFormat = false;
63 get_syntaxhdr_enable = false;
64 #endif
65 char property_value[PROPERTY_VALUE_MAX] = {0};
66 property_get("vidc.debug.level", property_value, "0");
67 debug_level = atoi(property_value);
68 property_value[0] = '\0';
69 m_pSwVenc = NULL;
70 }
71
~omx_swvenc()72 omx_swvenc::~omx_swvenc()
73 {
74 get_syntaxhdr_enable = false;
75 //nothing to do
76 }
77
78 /* ======================================================================
79 FUNCTION
80 omx_swvenc::ComponentInit
81
82 DESCRIPTION
83 Initialize the component.
84
85 PARAMETERS
86 ctxt -- Context information related to the self.
87 id -- Event identifier. This could be any of the following:
88 1. Command completion event
89 2. Buffer done callback event
90 3. Frame done callback event
91
92 RETURN VALUE
93 None.
94
95 ========================================================================== */
component_init(OMX_STRING role)96 OMX_ERRORTYPE omx_swvenc::component_init(OMX_STRING role)
97 {
98
99 OMX_ERRORTYPE eRet = OMX_ErrorNone;
100
101 int fds[2];
102 int r;
103
104 OMX_VIDEO_CODINGTYPE codec_type;
105
106 DEBUG_PRINT_HIGH("omx_swvenc(): Inside component_init()");
107 // Copy the role information which provides the decoder m_nkind
108 strlcpy((char *)m_nkind,role,OMX_MAX_STRINGNAME_SIZE);
109 secure_session = false;
110
111 if (!strncmp((char *)m_nkind,"OMX.qti.video.encoder.hevc",\
112 OMX_MAX_STRINGNAME_SIZE)) {
113 strlcpy((char *)m_cRole, "video_encoder.hevc",\
114 OMX_MAX_STRINGNAME_SIZE);
115 codec_type = (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingHevc;
116 }
117 else {
118 DEBUG_PRINT_ERROR("ERROR: Unknown Component");
119 eRet = OMX_ErrorInvalidComponentName;
120 }
121
122
123 if (eRet != OMX_ErrorNone) {
124 return eRet;
125 }
126 #ifdef ENABLE_GET_SYNTAX_HDR
127 get_syntaxhdr_enable = true;
128 DEBUG_PRINT_HIGH("Get syntax header enabled");
129 #endif
130
131 OMX_INIT_STRUCT(&m_sParamHEVC, OMX_VIDEO_PARAM_HEVCTYPE);
132 m_sParamHEVC.eProfile = OMX_VIDEO_HEVCProfileMain;
133 m_sParamHEVC.eLevel = OMX_VIDEO_HEVCMainTierLevel3;
134
135 // Init for SWCodec
136 DEBUG_PRINT_HIGH("\n:Initializing SwVenc");
137 SWVENC_INITPARAMS swVencParameter;
138 memset(&swVencParameter, 0, sizeof(SWVENC_INITPARAMS));
139 swVencParameter.sDimensions.nWidth = 176;
140 swVencParameter.sDimensions.nHeight = 144;
141 swVencParameter.uProfile.eHevcProfile = SWVENC_HEVC_MAIN_PROFILE;
142 //sSwVencParameter.nNumWorkerThreads = 3;
143
144 m_callBackInfo.FillBufferDone = swvenc_fill_buffer_done_cb;
145 m_callBackInfo.EmptyBufferDone = swvenc_input_buffer_done_cb;
146 m_callBackInfo.HandleEvent = swvenc_handle_event_cb;
147 m_callBackInfo.pClientHandle = this;
148 SWVENC_STATUS sRet = SwVenc_Init(&swVencParameter, &m_callBackInfo, &m_pSwVenc);
149 if (sRet != SWVENC_S_SUCCESS)
150 {
151 DEBUG_PRINT_ERROR("ERROR: SwVenc_Init failed");
152 return OMX_ErrorInsufficientResources;
153 }
154
155
156 //Intialise the OMX layer variables
157 memset(&m_pCallbacks,0,sizeof(OMX_CALLBACKTYPE));
158
159 OMX_INIT_STRUCT(&m_sPortParam, OMX_PORT_PARAM_TYPE);
160 m_sPortParam.nPorts = 0x2;
161 m_sPortParam.nStartPortNumber = (OMX_U32) PORT_INDEX_IN;
162
163 OMX_INIT_STRUCT(&m_sPortParam_audio, OMX_PORT_PARAM_TYPE);
164 m_sPortParam_audio.nPorts = 0;
165 m_sPortParam_audio.nStartPortNumber = 0;
166
167 OMX_INIT_STRUCT(&m_sPortParam_img, OMX_PORT_PARAM_TYPE);
168 m_sPortParam_img.nPorts = 0;
169 m_sPortParam_img.nStartPortNumber = 0;
170
171 OMX_INIT_STRUCT(&m_sParamBitrate, OMX_VIDEO_PARAM_BITRATETYPE);
172 m_sParamBitrate.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
173 m_sParamBitrate.eControlRate = OMX_Video_ControlRateVariableSkipFrames;
174 m_sParamBitrate.nTargetBitrate = 64000;
175
176 OMX_INIT_STRUCT(&m_sConfigBitrate, OMX_VIDEO_CONFIG_BITRATETYPE);
177 m_sConfigBitrate.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
178 m_sConfigBitrate.nEncodeBitrate = 64000;
179
180 OMX_INIT_STRUCT(&m_sConfigFramerate, OMX_CONFIG_FRAMERATETYPE);
181 m_sConfigFramerate.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
182 m_sConfigFramerate.xEncodeFramerate = 30 << 16;
183
184 OMX_INIT_STRUCT(&m_sConfigIntraRefreshVOP, OMX_CONFIG_INTRAREFRESHVOPTYPE);
185 m_sConfigIntraRefreshVOP.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
186 m_sConfigIntraRefreshVOP.IntraRefreshVOP = OMX_FALSE;
187
188 OMX_INIT_STRUCT(&m_sConfigFrameRotation, OMX_CONFIG_ROTATIONTYPE);
189 m_sConfigFrameRotation.nPortIndex = (OMX_U32) PORT_INDEX_IN;
190 m_sConfigFrameRotation.nRotation = 0;
191
192 OMX_INIT_STRUCT(&m_sSessionQuantization, OMX_VIDEO_PARAM_QUANTIZATIONTYPE);
193 m_sSessionQuantization.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
194 m_sSessionQuantization.nQpI = 9;
195 m_sSessionQuantization.nQpP = 6;
196 m_sSessionQuantization.nQpB = 2;
197
198 OMX_INIT_STRUCT(&m_sSessionQPRange, OMX_QCOM_VIDEO_PARAM_QPRANGETYPE);
199 m_sSessionQPRange.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
200 m_sSessionQPRange.minQP = 2;
201 if (codec_type == OMX_VIDEO_CodingAVC)
202 m_sSessionQPRange.maxQP = 51;
203 else
204 m_sSessionQPRange.maxQP = 31;
205
206 OMX_INIT_STRUCT(&m_sAVCSliceFMO, OMX_VIDEO_PARAM_AVCSLICEFMO);
207 m_sAVCSliceFMO.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
208 m_sAVCSliceFMO.eSliceMode = OMX_VIDEO_SLICEMODE_AVCDefault;
209 m_sAVCSliceFMO.nNumSliceGroups = 0;
210 m_sAVCSliceFMO.nSliceGroupMapType = 0;
211 OMX_INIT_STRUCT(&m_sParamProfileLevel, OMX_VIDEO_PARAM_PROFILELEVELTYPE);
212 m_sParamProfileLevel.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
213
214 OMX_INIT_STRUCT(&m_sIntraperiod, QOMX_VIDEO_INTRAPERIODTYPE);
215 m_sIntraperiod.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
216 m_sIntraperiod.nPFrames = (m_sConfigFramerate.xEncodeFramerate * 2) - 1;
217
218 OMX_INIT_STRUCT(&m_sErrorCorrection, OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE);
219 m_sErrorCorrection.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
220 m_sErrorCorrection.bEnableDataPartitioning = OMX_FALSE;
221 m_sErrorCorrection.bEnableHEC = OMX_FALSE;
222 m_sErrorCorrection.bEnableResync = OMX_FALSE;
223 m_sErrorCorrection.bEnableRVLC = OMX_FALSE;
224 m_sErrorCorrection.nResynchMarkerSpacing = 0;
225
226 OMX_INIT_STRUCT(&m_sIntraRefresh, OMX_VIDEO_PARAM_INTRAREFRESHTYPE);
227 m_sIntraRefresh.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
228 m_sIntraRefresh.eRefreshMode = OMX_VIDEO_IntraRefreshMax;
229
230 // Initialize the video parameters for input port
231 OMX_INIT_STRUCT(&m_sInPortDef, OMX_PARAM_PORTDEFINITIONTYPE);
232 m_sInPortDef.nPortIndex= (OMX_U32) PORT_INDEX_IN;
233 m_sInPortDef.bEnabled = OMX_TRUE;
234 m_sInPortDef.bPopulated = OMX_FALSE;
235 m_sInPortDef.eDomain = OMX_PortDomainVideo;
236 m_sInPortDef.eDir = OMX_DirInput;
237 m_sInPortDef.format.video.cMIMEType = (char *)"YUV420";
238 m_sInPortDef.format.video.nFrameWidth = OMX_CORE_QCIF_WIDTH;
239 m_sInPortDef.format.video.nFrameHeight = OMX_CORE_QCIF_HEIGHT;
240 m_sInPortDef.format.video.nStride = OMX_CORE_QCIF_WIDTH;
241 m_sInPortDef.format.video.nSliceHeight = OMX_CORE_QCIF_HEIGHT;
242 m_sInPortDef.format.video.nBitrate = 64000;
243 m_sInPortDef.format.video.xFramerate = 15 << 16;
244 m_sInPortDef.format.video.eColorFormat = (OMX_COLOR_FORMATTYPE)
245 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
246 m_sInPortDef.format.video.eCompressionFormat = OMX_VIDEO_CodingUnused;
247
248 if (dev_get_buf_req(&m_sInPortDef.nBufferCountMin,
249 &m_sInPortDef.nBufferCountActual,
250 &m_sInPortDef.nBufferSize,
251 m_sInPortDef.nPortIndex) != true) {
252 eRet = OMX_ErrorUndefined;
253 }
254
255 // Initialize the video parameters for output port
256 OMX_INIT_STRUCT(&m_sOutPortDef, OMX_PARAM_PORTDEFINITIONTYPE);
257 m_sOutPortDef.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
258 m_sOutPortDef.bEnabled = OMX_TRUE;
259 m_sOutPortDef.bPopulated = OMX_FALSE;
260 m_sOutPortDef.eDomain = OMX_PortDomainVideo;
261 m_sOutPortDef.eDir = OMX_DirOutput;
262 m_sOutPortDef.format.video.nFrameWidth = OMX_CORE_QCIF_WIDTH;
263 m_sOutPortDef.format.video.nFrameHeight = OMX_CORE_QCIF_HEIGHT;
264 m_sOutPortDef.format.video.nBitrate = 64000;
265 m_sOutPortDef.format.video.xFramerate = 15 << 16;
266 m_sOutPortDef.format.video.eColorFormat = OMX_COLOR_FormatUnused;
267 if (codec_type == (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingHevc) {
268 m_sOutPortDef.format.video.eCompressionFormat = (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingHevc;
269 }
270 if (dev_get_buf_req(&m_sOutPortDef.nBufferCountMin,
271 &m_sOutPortDef.nBufferCountActual,
272 &m_sOutPortDef.nBufferSize,
273 m_sOutPortDef.nPortIndex) != true) {
274 eRet = OMX_ErrorUndefined;
275 }
276
277 // Initialize the video color format for input port
278 OMX_INIT_STRUCT(&m_sInPortFormat, OMX_VIDEO_PARAM_PORTFORMATTYPE);
279 m_sInPortFormat.nPortIndex = (OMX_U32) PORT_INDEX_IN;
280 m_sInPortFormat.nIndex = 0;
281 m_sInPortFormat.eColorFormat = (OMX_COLOR_FORMATTYPE)
282 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
283 m_sInPortFormat.eCompressionFormat = OMX_VIDEO_CodingUnused;
284
285
286 // Initialize the compression format for output port
287 OMX_INIT_STRUCT(&m_sOutPortFormat, OMX_VIDEO_PARAM_PORTFORMATTYPE);
288 m_sOutPortFormat.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
289 m_sOutPortFormat.nIndex = 0;
290 m_sOutPortFormat.eColorFormat = OMX_COLOR_FormatUnused;
291 if (codec_type == (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingHevc) {
292 m_sOutPortFormat.eCompressionFormat = (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingHevc;
293 };
294
295
296 // mandatory Indices for kronos test suite
297 OMX_INIT_STRUCT(&m_sPriorityMgmt, OMX_PRIORITYMGMTTYPE);
298
299 OMX_INIT_STRUCT(&m_sInBufSupplier, OMX_PARAM_BUFFERSUPPLIERTYPE);
300 m_sInBufSupplier.nPortIndex = (OMX_U32) PORT_INDEX_IN;
301
302 OMX_INIT_STRUCT(&m_sOutBufSupplier, OMX_PARAM_BUFFERSUPPLIERTYPE);
303 m_sOutBufSupplier.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
304
305
306 OMX_INIT_STRUCT(&m_sParamLTRMode, QOMX_VIDEO_PARAM_LTRMODE_TYPE);
307 m_sParamLTRMode.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
308 m_sParamLTRMode.eLTRMode = QOMX_VIDEO_LTRMode_Disable;
309
310 OMX_INIT_STRUCT(&m_sParamLTRCount, QOMX_VIDEO_PARAM_LTRCOUNT_TYPE);
311 m_sParamLTRCount.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
312 m_sParamLTRCount.nCount = 0;
313
314 OMX_INIT_STRUCT(&m_sConfigDeinterlace, OMX_VIDEO_CONFIG_DEINTERLACE);
315 m_sConfigDeinterlace.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
316 m_sConfigDeinterlace.nEnable = OMX_FALSE;
317
318 OMX_INIT_STRUCT(&m_sHierLayers, QOMX_VIDEO_HIERARCHICALLAYERS);
319 m_sHierLayers.nPortIndex = (OMX_U32) PORT_INDEX_OUT;
320 m_sHierLayers.nNumLayers = 0;
321 m_sHierLayers.eHierarchicalCodingType = QOMX_HIERARCHICALCODING_P;
322
323 m_state = OMX_StateLoaded;
324 m_sExtraData = 0;
325
326 if (eRet == OMX_ErrorNone) {
327 if (pipe(fds)) {
328 DEBUG_PRINT_ERROR("ERROR: pipe creation failed");
329 eRet = OMX_ErrorInsufficientResources;
330 } else {
331 if (fds[0] == 0 || fds[1] == 0) {
332 if (pipe(fds)) {
333 DEBUG_PRINT_ERROR("ERROR: pipe creation failed");
334 eRet = OMX_ErrorInsufficientResources;
335 }
336 }
337 if (eRet == OMX_ErrorNone) {
338 m_pipe_in = fds[0];
339 m_pipe_out = fds[1];
340 }
341 }
342 msg_thread_created = true;
343 r = pthread_create(&msg_thread_id,0, message_thread, this);
344 if (r < 0) {
345 eRet = OMX_ErrorInsufficientResources;
346 msg_thread_created = false;
347 }
348 }
349
350 DEBUG_PRINT_HIGH("Component_init return value = 0x%x", eRet);
351 return eRet;
352 }
353
354
355 /* ======================================================================
356 FUNCTION
357 omx_swvenc::Setparameter
358
359 DESCRIPTION
360 OMX Set Parameter method implementation.
361
362 PARAMETERS
363 <TBD>.
364
365 RETURN VALUE
366 OMX Error None if successful.
367
368 ========================================================================== */
set_parameter(OMX_IN OMX_HANDLETYPE hComp,OMX_IN OMX_INDEXTYPE paramIndex,OMX_IN OMX_PTR paramData)369 OMX_ERRORTYPE omx_swvenc::set_parameter(OMX_IN OMX_HANDLETYPE hComp,
370 OMX_IN OMX_INDEXTYPE paramIndex,
371 OMX_IN OMX_PTR paramData)
372 {
373 OMX_ERRORTYPE eRet = OMX_ErrorNone;
374
375
376 if (m_state == OMX_StateInvalid) {
377 DEBUG_PRINT_ERROR("ERROR: Set Param in Invalid State");
378 return OMX_ErrorInvalidState;
379 }
380 if (paramData == NULL) {
381 DEBUG_PRINT_ERROR("ERROR: Get Param in Invalid paramData");
382 return OMX_ErrorBadParameter;
383 }
384
385 /*set_parameter can be called in loaded state
386 or disabled port */
387 if (m_state == OMX_StateLoaded
388 || m_sInPortDef.bEnabled == OMX_FALSE
389 || m_sOutPortDef.bEnabled == OMX_FALSE) {
390 DEBUG_PRINT_LOW("Set Parameter called in valid state");
391 } else {
392 DEBUG_PRINT_ERROR("ERROR: Set Parameter called in Invalid State");
393 return OMX_ErrorIncorrectStateOperation;
394 }
395
396 switch ((int)paramIndex) {
397 case OMX_IndexParamPortDefinition:
398 {
399 OMX_PARAM_PORTDEFINITIONTYPE *portDefn;
400 portDefn = (OMX_PARAM_PORTDEFINITIONTYPE *) paramData;
401 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPortDefinition H= %d, W = %d",
402 (int)portDefn->format.video.nFrameHeight,
403 (int)portDefn->format.video.nFrameWidth);
404
405 SWVENC_PROP prop;
406 prop.ePropId = SWVENC_PROP_ID_DIMENSIONS;
407 prop.uProperty.sDimensions.nWidth = portDefn->format.video.nFrameWidth;
408 prop.uProperty.sDimensions.nHeight= portDefn->format.video.nFrameHeight;
409 SWVENC_STATUS status = SwVenc_SetProperty(m_pSwVenc,&prop);
410 if (status != SWVENC_S_SUCCESS) {
411 DEBUG_PRINT_ERROR("ERROR: (In_PORT) dimension not supported %d x %d",
412 portDefn->format.video.nFrameWidth, portDefn->format.video.nFrameHeight);
413 return OMX_ErrorUnsupportedSetting;
414 }
415
416 if (PORT_INDEX_IN == portDefn->nPortIndex) {
417 if (!dev_is_video_session_supported(portDefn->format.video.nFrameWidth,
418 portDefn->format.video.nFrameHeight)) {
419 DEBUG_PRINT_ERROR("video session not supported");
420 omx_report_unsupported_setting();
421 return OMX_ErrorUnsupportedSetting;
422 }
423 DEBUG_PRINT_LOW("i/p actual cnt requested = %u", portDefn->nBufferCountActual);
424 DEBUG_PRINT_LOW("i/p min cnt requested = %u", portDefn->nBufferCountMin);
425 DEBUG_PRINT_LOW("i/p buffersize requested = %u", portDefn->nBufferSize);
426 if (portDefn->nBufferCountMin > portDefn->nBufferCountActual) {
427 DEBUG_PRINT_ERROR("ERROR: (In_PORT) Min buffers (%u) > actual count (%u)",
428 portDefn->nBufferCountMin, portDefn->nBufferCountActual);
429 return OMX_ErrorUnsupportedSetting;
430 }
431
432 DEBUG_PRINT_LOW("i/p previous actual cnt = %u", m_sInPortDef.nBufferCountActual);
433 DEBUG_PRINT_LOW("i/p previous min cnt = %u", m_sInPortDef.nBufferCountMin);
434 memcpy(&m_sInPortDef, portDefn,sizeof(OMX_PARAM_PORTDEFINITIONTYPE));
435 DEBUG_PRINT_LOW("i/p COLOR FORMAT = %u", portDefn->format.video.eColorFormat);
436 #ifdef _ANDROID_ICS_
437 if (portDefn->format.video.eColorFormat ==
438 (OMX_COLOR_FORMATTYPE)QOMX_COLOR_FormatAndroidOpaque) {
439 m_sInPortDef.format.video.eColorFormat = (OMX_COLOR_FORMATTYPE)
440 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
441 if (!mUseProxyColorFormat) {
442 if (!c2d_conv.init()) {
443 DEBUG_PRINT_ERROR("C2D init failed");
444 return OMX_ErrorUnsupportedSetting;
445 }
446 DEBUG_PRINT_LOW("C2D init is successful");
447 }
448 mUseProxyColorFormat = true;
449 m_input_msg_id = OMX_COMPONENT_GENERATE_ETB_OPQ;
450 } else
451 mUseProxyColorFormat = false;
452 #endif
453 /*Query Input Buffer Requirements*/
454 dev_get_buf_req (&m_sInPortDef.nBufferCountMin,
455 &m_sInPortDef.nBufferCountActual,
456 &m_sInPortDef.nBufferSize,
457 m_sInPortDef.nPortIndex);
458
459 /*Query ouput Buffer Requirements*/
460 dev_get_buf_req (&m_sOutPortDef.nBufferCountMin,
461 &m_sOutPortDef.nBufferCountActual,
462 &m_sOutPortDef.nBufferSize,
463 m_sOutPortDef.nPortIndex);
464 m_sInPortDef.nBufferCountActual = portDefn->nBufferCountActual;
465 } else if (PORT_INDEX_OUT == portDefn->nPortIndex) {
466 DEBUG_PRINT_LOW("o/p actual cnt requested = %u", portDefn->nBufferCountActual);
467 DEBUG_PRINT_LOW("o/p min cnt requested = %u", portDefn->nBufferCountMin);
468 DEBUG_PRINT_LOW("o/p buffersize requested = %u", portDefn->nBufferSize);
469 if (portDefn->nBufferCountMin > portDefn->nBufferCountActual) {
470 DEBUG_PRINT_ERROR("ERROR: (Out_PORT) Min buffers (%u) > actual count (%u)",
471 portDefn->nBufferCountMin, portDefn->nBufferCountActual);
472 return OMX_ErrorUnsupportedSetting;
473 }
474
475 /*Query ouput Buffer Requirements*/
476 dev_get_buf_req(&m_sOutPortDef.nBufferCountMin,
477 &m_sOutPortDef.nBufferCountActual,
478 &m_sOutPortDef.nBufferSize,
479 m_sOutPortDef.nPortIndex);
480
481 memcpy(&m_sOutPortDef,portDefn,sizeof(struct OMX_PARAM_PORTDEFINITIONTYPE));
482 update_profile_level(); //framerate , bitrate
483
484 DEBUG_PRINT_LOW("o/p previous actual cnt = %u", m_sOutPortDef.nBufferCountActual);
485 DEBUG_PRINT_LOW("o/p previous min cnt = %u", m_sOutPortDef.nBufferCountMin);
486 m_sOutPortDef.nBufferCountActual = portDefn->nBufferCountActual;
487 } else {
488 DEBUG_PRINT_ERROR("ERROR: Set_parameter: Bad Port idx %d",
489 (int)portDefn->nPortIndex);
490 eRet = OMX_ErrorBadPortIndex;
491 }
492 m_sConfigFramerate.xEncodeFramerate = portDefn->format.video.xFramerate;
493 m_sConfigBitrate.nEncodeBitrate = portDefn->format.video.nBitrate;
494 m_sParamBitrate.nTargetBitrate = portDefn->format.video.nBitrate;
495 }
496 break;
497
498 case OMX_IndexParamVideoPortFormat:
499 {
500 OMX_VIDEO_PARAM_PORTFORMATTYPE *portFmt =
501 (OMX_VIDEO_PARAM_PORTFORMATTYPE *)paramData;
502 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoPortFormat %d",
503 portFmt->eColorFormat);
504 //set the driver with the corresponding values
505 if (PORT_INDEX_IN == portFmt->nPortIndex) {
506
507 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoPortFormat %d",
508 portFmt->eColorFormat);
509
510 SWVENC_PROP prop;
511 prop.uProperty.nFrameRate = portFmt->xFramerate;
512 prop.ePropId = SWVENC_PROP_ID_FRAMERATE;
513 SwVenc_SetProperty(m_pSwVenc, &prop);
514
515 update_profile_level(); //framerate
516
517 #ifdef _ANDROID_ICS_
518 if (portFmt->eColorFormat ==
519 (OMX_COLOR_FORMATTYPE)QOMX_COLOR_FormatAndroidOpaque) {
520 m_sInPortFormat.eColorFormat = (OMX_COLOR_FORMATTYPE)
521 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
522 if (!mUseProxyColorFormat) {
523 if (!c2d_conv.init()) {
524 DEBUG_PRINT_ERROR("C2D init failed");
525 return OMX_ErrorUnsupportedSetting;
526 }
527 DEBUG_PRINT_LOW("C2D init is successful");
528 }
529 mUseProxyColorFormat = true;
530 m_input_msg_id = OMX_COMPONENT_GENERATE_ETB_OPQ;
531 } else
532 #endif
533 {
534 m_sInPortFormat.eColorFormat = portFmt->eColorFormat;
535 m_input_msg_id = OMX_COMPONENT_GENERATE_ETB;
536 mUseProxyColorFormat = false;
537 }
538 m_sInPortFormat.xFramerate = portFmt->xFramerate;
539 }
540 //TODO if no use case for O/P port,delet m_sOutPortFormat
541 }
542 break;
543 case OMX_IndexParamVideoInit:
544 { //TODO, do we need this index set param
545 OMX_PORT_PARAM_TYPE* pParam = (OMX_PORT_PARAM_TYPE*)(paramData);
546 DEBUG_PRINT_LOW("Set OMX_IndexParamVideoInit called");
547 break;
548 }
549
550 case OMX_IndexParamVideoBitrate:
551 {
552 OMX_VIDEO_PARAM_BITRATETYPE* pParam = (OMX_VIDEO_PARAM_BITRATETYPE*)paramData;
553 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoBitrate");
554
555 SWVENC_PROP prop;
556 prop.uProperty.nFrameRate = pParam->nTargetBitrate;
557 prop.ePropId = SWVENC_PROP_ID_BITRATE;
558 SwVenc_SetProperty(m_pSwVenc, &prop);
559
560 prop.uProperty.nRcOn = pParam->eControlRate;
561 prop.ePropId = SWVENC_PROP_ID_RC_ON;
562 SwVenc_SetProperty(m_pSwVenc, &prop);
563
564 m_sParamBitrate.nTargetBitrate = pParam->nTargetBitrate;
565 m_sParamBitrate.eControlRate = pParam->eControlRate;
566 update_profile_level(); //bitrate
567 m_sConfigBitrate.nEncodeBitrate = pParam->nTargetBitrate;
568 m_sInPortDef.format.video.nBitrate = pParam->nTargetBitrate;
569 m_sOutPortDef.format.video.nBitrate = pParam->nTargetBitrate;
570 DEBUG_PRINT_LOW("bitrate = %u", m_sOutPortDef.format.video.nBitrate);
571 break;
572 }
573 case OMX_IndexParamVideoMpeg4:
574 case OMX_IndexParamVideoH263:
575 case OMX_IndexParamVideoAvc:
576 case (OMX_INDEXTYPE)OMX_IndexParamVideoVp8:
577 return OMX_ErrorUnsupportedSetting;
578 case (OMX_INDEXTYPE)OMX_IndexParamVideoHevc:
579 {
580 OMX_VIDEO_PARAM_HEVCTYPE* pParam = (OMX_VIDEO_PARAM_HEVCTYPE*)paramData;
581 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoHevc");
582 if (pParam->eProfile != OMX_VIDEO_HEVCProfileMain ||
583 (pParam->eLevel != OMX_VIDEO_HEVCMainTierLevel1 &&
584 pParam->eLevel != OMX_VIDEO_HEVCMainTierLevel2 &&
585 pParam->eLevel != OMX_VIDEO_HEVCMainTierLevel21 &&
586 pParam->eLevel != OMX_VIDEO_HEVCMainTierLevel3))
587 {
588 return OMX_ErrorBadParameter;
589 }
590 m_sParamHEVC.eProfile = OMX_VIDEO_HEVCProfileMain;
591 m_sParamHEVC.eLevel = pParam->eLevel;
592 break;
593 }
594 case OMX_IndexParamVideoProfileLevelCurrent:
595 {
596 OMX_VIDEO_PARAM_PROFILELEVELTYPE* pParam = (OMX_VIDEO_PARAM_PROFILELEVELTYPE*)paramData;
597 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoProfileLevelCurrent");
598
599 m_sParamProfileLevel.eProfile = pParam->eProfile;
600 m_sParamProfileLevel.eLevel = pParam->eLevel;
601
602 if (!strncmp((char *)m_nkind, "OMX.qti.video.encoder.hevc",\
603 OMX_MAX_STRINGNAME_SIZE)) {
604
605 // DEBUG_PRINT_LOW("HEVC profile = %d, level = %d");
606 }
607 break;
608 }
609 case OMX_IndexParamStandardComponentRole:
610 {
611 OMX_PARAM_COMPONENTROLETYPE *comp_role;
612 comp_role = (OMX_PARAM_COMPONENTROLETYPE *) paramData;
613 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamStandardComponentRole %s",
614 comp_role->cRole);
615
616 if ((m_state == OMX_StateLoaded)&&
617 !BITMASK_PRESENT(&m_flags,OMX_COMPONENT_IDLE_PENDING)) {
618 DEBUG_PRINT_LOW("Set Parameter called in valid state");
619 } else {
620 DEBUG_PRINT_ERROR("Set Parameter called in Invalid State");
621 return OMX_ErrorIncorrectStateOperation;
622 }
623
624 if (!strncmp((char*)m_nkind, "OMX.qti.video.encoder.hevc",OMX_MAX_STRINGNAME_SIZE)) {
625 if (!strncmp((char*)comp_role->cRole,"video_encoder.hevc",OMX_MAX_STRINGNAME_SIZE)) {
626 strlcpy((char*)m_cRole,"video_encoder.hevc",OMX_MAX_STRINGNAME_SIZE);
627 } else {
628 DEBUG_PRINT_ERROR("ERROR: Setparameter: unknown Index %s", comp_role->cRole);
629 eRet =OMX_ErrorUnsupportedSetting;
630 }
631 }
632 else {
633 DEBUG_PRINT_ERROR("ERROR: Setparameter: unknown param %s", m_nkind);
634 eRet = OMX_ErrorInvalidComponentName;
635 }
636 break;
637 }
638
639 case OMX_IndexParamPriorityMgmt:
640 {
641 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPriorityMgmt");
642 if (m_state != OMX_StateLoaded) {
643 DEBUG_PRINT_ERROR("ERROR: Set Parameter called in Invalid State");
644 return OMX_ErrorIncorrectStateOperation;
645 }
646 OMX_PRIORITYMGMTTYPE *priorityMgmtype = (OMX_PRIORITYMGMTTYPE*) paramData;
647 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPriorityMgmt %u",
648 priorityMgmtype->nGroupID);
649
650 DEBUG_PRINT_LOW("set_parameter: priorityMgmtype %u",
651 priorityMgmtype->nGroupPriority);
652
653 m_sPriorityMgmt.nGroupID = priorityMgmtype->nGroupID;
654 m_sPriorityMgmt.nGroupPriority = priorityMgmtype->nGroupPriority;
655
656 break;
657 }
658
659 case OMX_IndexParamCompBufferSupplier:
660 {
661 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamCompBufferSupplier");
662 OMX_PARAM_BUFFERSUPPLIERTYPE *bufferSupplierType = (OMX_PARAM_BUFFERSUPPLIERTYPE*) paramData;
663 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamCompBufferSupplier %d",
664 bufferSupplierType->eBufferSupplier);
665 if (bufferSupplierType->nPortIndex == 0 || bufferSupplierType->nPortIndex ==1)
666 m_sInBufSupplier.eBufferSupplier = bufferSupplierType->eBufferSupplier;
667
668 else
669
670 eRet = OMX_ErrorBadPortIndex;
671
672 break;
673
674 }
675 case OMX_IndexParamVideoQuantization:
676 {
677 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoQuantization");
678 OMX_VIDEO_PARAM_QUANTIZATIONTYPE *session_qp = (OMX_VIDEO_PARAM_QUANTIZATIONTYPE*) paramData;
679 if (session_qp->nPortIndex == PORT_INDEX_OUT) {
680 SWVENC_PROP prop;
681 prop.uProperty.nQp = session_qp->nQpI;
682 prop.ePropId = SWVENC_PROP_ID_QP;
683 SwVenc_SetProperty(m_pSwVenc, &prop);
684
685 m_sSessionQuantization.nQpI = session_qp->nQpI;
686 m_sSessionQuantization.nQpP = session_qp->nQpP;
687 } else {
688 DEBUG_PRINT_ERROR("ERROR: Unsupported port Index for Session QP setting");
689 eRet = OMX_ErrorBadPortIndex;
690 }
691 break;
692 }
693
694 case OMX_QcomIndexParamVideoQPRange:
695 {
696 DEBUG_PRINT_LOW("set_parameter: OMX_QcomIndexParamVideoQPRange");
697 OMX_QCOM_VIDEO_PARAM_QPRANGETYPE *qp_range = (OMX_QCOM_VIDEO_PARAM_QPRANGETYPE*) paramData;
698 if (qp_range->nPortIndex == PORT_INDEX_OUT) {
699 m_sSessionQPRange.minQP= qp_range->minQP;
700 m_sSessionQPRange.maxQP= qp_range->maxQP;
701 } else {
702 DEBUG_PRINT_ERROR("ERROR: Unsupported port Index for QP range setting");
703 eRet = OMX_ErrorBadPortIndex;
704 }
705 break;
706 }
707
708 case OMX_QcomIndexPortDefn:
709 {
710 OMX_QCOM_PARAM_PORTDEFINITIONTYPE* pParam =
711 (OMX_QCOM_PARAM_PORTDEFINITIONTYPE*)paramData;
712 DEBUG_PRINT_LOW("set_parameter: OMX_QcomIndexPortDefn");
713 if (pParam->nPortIndex == (OMX_U32)PORT_INDEX_IN) {
714 if (pParam->nMemRegion > OMX_QCOM_MemRegionInvalid &&
715 pParam->nMemRegion < OMX_QCOM_MemRegionMax) {
716 m_use_input_pmem = OMX_TRUE;
717 } else {
718 m_use_input_pmem = OMX_FALSE;
719 }
720 } else if (pParam->nPortIndex == (OMX_U32)PORT_INDEX_OUT) {
721 if (pParam->nMemRegion > OMX_QCOM_MemRegionInvalid &&
722 pParam->nMemRegion < OMX_QCOM_MemRegionMax) {
723 m_use_output_pmem = OMX_TRUE;
724 } else {
725 m_use_output_pmem = OMX_FALSE;
726 }
727 } else {
728 DEBUG_PRINT_ERROR("ERROR: SetParameter called on unsupported Port Index for QcomPortDefn");
729 return OMX_ErrorBadPortIndex;
730 }
731 break;
732 }
733
734 case OMX_IndexParamVideoErrorCorrection:
735 {
736 DEBUG_PRINT_LOW("OMX_IndexParamVideoErrorCorrection");
737 OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE* pParam =
738 (OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE*)paramData;
739 memcpy(&m_sErrorCorrection,pParam, sizeof(m_sErrorCorrection));
740 break;
741 }
742 case OMX_IndexParamVideoIntraRefresh:
743 {
744 DEBUG_PRINT_LOW("set_param:OMX_IndexParamVideoIntraRefresh");
745 OMX_VIDEO_PARAM_INTRAREFRESHTYPE* pParam =
746 (OMX_VIDEO_PARAM_INTRAREFRESHTYPE*)paramData;
747
748 memcpy(&m_sIntraRefresh, pParam, sizeof(m_sIntraRefresh));
749 break;
750 }
751
752 case OMX_QcomIndexParamVideoMetaBufferMode:
753 {
754 StoreMetaDataInBuffersParams *pParam =
755 (StoreMetaDataInBuffersParams*)paramData;
756 DEBUG_PRINT_HIGH("set_parameter:OMX_QcomIndexParamVideoMetaBufferMode: "
757 "port_index = %u, meta_mode = %d", pParam->nPortIndex, pParam->bStoreMetaData);
758 if (pParam->nPortIndex == PORT_INDEX_IN)
759 {
760 meta_mode_enable = pParam->bStoreMetaData;
761 }
762 else
763 {
764 if (pParam->bStoreMetaData)
765 {
766 DEBUG_PRINT_ERROR("set_parameter: metamode is "
767 "valid for input port only");
768 eRet = OMX_ErrorUnsupportedIndex;
769 }
770 }
771 }
772 break;
773 default:
774 {
775 DEBUG_PRINT_ERROR("ERROR: Setparameter: unknown param %d", paramIndex);
776 eRet = OMX_ErrorUnsupportedIndex;
777 break;
778 }
779 }
780 return eRet;
781 }
782
update_profile_level()783 bool omx_swvenc::update_profile_level()
784 {
785 if (!strncmp((char *)m_nkind, "OMX.qti.video.encoder.hevc",\
786 OMX_MAX_STRINGNAME_SIZE))
787 {
788 if (m_sParamHEVC.eProfile != OMX_VIDEO_HEVCProfileMain)
789 {
790 return false;
791 }
792 SWVENC_PROP prop;
793 prop.ePropId = SWVENC_PROP_ID_PROFILE;
794 prop.uProperty.nProfile = SWVENC_HEVC_MAIN_PROFILE;
795 if (SwVenc_SetProperty(m_pSwVenc, &prop) != SWVENC_S_SUCCESS)
796 {
797 DEBUG_PRINT_ERROR("ERROR: failed to set profile");
798 }
799
800 int level = 0;
801 if (m_sParamHEVC.eLevel == OMX_VIDEO_HEVCMainTierLevel1)
802 {
803 level = SWVENC_HEVC_LEVEL_1;
804 }
805 else if (m_sParamHEVC.eLevel == OMX_VIDEO_HEVCMainTierLevel2)
806 {
807 level = SWVENC_HEVC_LEVEL_2;
808 }
809 else if (m_sParamHEVC.eLevel == OMX_VIDEO_HEVCMainTierLevel21)
810 {
811 level = SWVENC_HEVC_LEVEL_2_1;
812 }
813 else if (m_sParamHEVC.eLevel == OMX_VIDEO_HEVCMainTierLevel3)
814 {
815 level = SWVENC_HEVC_LEVEL_3;
816 }
817
818 if (level)
819 {
820 prop.ePropId = SWVENC_PROP_ID_LEVEL;
821 prop.uProperty.nLevel = (SWVENC_HEVC_LEVEL)level;
822 if (SwVenc_SetProperty(m_pSwVenc, &prop) != SWVENC_S_SUCCESS)
823 {
824 DEBUG_PRINT_ERROR("ERROR: failed to set level %d", level);
825 }
826 }
827 }
828
829 return true;
830 }
831 /* ======================================================================
832 FUNCTION
833 omx_video::SetConfig
834
835 DESCRIPTION
836 OMX Set Config method implementation
837
838 PARAMETERS
839 <TBD>.
840
841 RETURN VALUE
842 OMX Error None if successful.
843 ========================================================================== */
set_config(OMX_IN OMX_HANDLETYPE hComp,OMX_IN OMX_INDEXTYPE configIndex,OMX_IN OMX_PTR configData)844 OMX_ERRORTYPE omx_swvenc::set_config(OMX_IN OMX_HANDLETYPE hComp,
845 OMX_IN OMX_INDEXTYPE configIndex,
846 OMX_IN OMX_PTR configData)
847 {
848 if (configData == NULL) {
849 DEBUG_PRINT_ERROR("ERROR: param is null");
850 return OMX_ErrorBadParameter;
851 }
852
853 if (m_state == OMX_StateInvalid) {
854 DEBUG_PRINT_ERROR("ERROR: config called in Invalid state");
855 return OMX_ErrorIncorrectStateOperation;
856 }
857
858 // params will be validated prior to venc_init
859 switch ((int)configIndex) {
860 case OMX_IndexConfigVideoBitrate:
861 {
862 OMX_VIDEO_CONFIG_BITRATETYPE* pParam =
863 reinterpret_cast<OMX_VIDEO_CONFIG_BITRATETYPE*>(configData);
864 DEBUG_PRINT_HIGH("set_config(): OMX_IndexConfigVideoBitrate (%u)", pParam->nEncodeBitrate);
865
866 if (pParam->nPortIndex == PORT_INDEX_OUT) {
867 SWVENC_PROP prop;
868 prop.uProperty.nBitrate = pParam->nEncodeBitrate;
869 prop.ePropId = SWVENC_PROP_ID_BITRATE;
870 SwVenc_SetProperty(m_pSwVenc, &prop);
871
872
873 m_sConfigBitrate.nEncodeBitrate = pParam->nEncodeBitrate;
874 m_sParamBitrate.nTargetBitrate = pParam->nEncodeBitrate;
875 m_sOutPortDef.format.video.nBitrate = pParam->nEncodeBitrate;
876 } else {
877 DEBUG_PRINT_ERROR("ERROR: Unsupported port index: %u", pParam->nPortIndex);
878 return OMX_ErrorBadPortIndex;
879 }
880 break;
881 }
882 case OMX_IndexConfigVideoFramerate:
883 {
884 OMX_CONFIG_FRAMERATETYPE* pParam =
885 reinterpret_cast<OMX_CONFIG_FRAMERATETYPE*>(configData);
886 DEBUG_PRINT_HIGH("set_config(): OMX_IndexConfigVideoFramerate (0x%x)", pParam->xEncodeFramerate);
887
888 if (pParam->nPortIndex == PORT_INDEX_OUT) {
889 SWVENC_PROP prop;
890 prop.uProperty.nFrameRate = pParam->xEncodeFramerate;
891 prop.ePropId = SWVENC_PROP_ID_FRAMERATE;
892 SwVenc_SetProperty(m_pSwVenc, &prop);
893
894 m_sConfigFramerate.xEncodeFramerate = pParam->xEncodeFramerate;
895 m_sOutPortDef.format.video.xFramerate = pParam->xEncodeFramerate;
896 m_sOutPortFormat.xFramerate = pParam->xEncodeFramerate;
897 } else {
898 DEBUG_PRINT_ERROR("ERROR: Unsupported port index: %u", pParam->nPortIndex);
899 return OMX_ErrorBadPortIndex;
900 }
901
902 break;
903 }
904 case QOMX_IndexConfigVideoIntraperiod:
905 {
906 QOMX_VIDEO_INTRAPERIODTYPE* pParam =
907 reinterpret_cast<QOMX_VIDEO_INTRAPERIODTYPE*>(configData);
908
909 DEBUG_PRINT_HIGH("set_config(): QOMX_IndexConfigVideoIntraperiod");
910 if (pParam->nPortIndex == PORT_INDEX_OUT) {
911 if (pParam->nBFrames > 0) {
912 DEBUG_PRINT_ERROR("B frames not supported");
913 return OMX_ErrorUnsupportedSetting;
914 }
915 DEBUG_PRINT_HIGH("Old: P/B frames = %u/%u, New: P/B frames = %u/%u",
916 m_sIntraperiod.nPFrames, m_sIntraperiod.nBFrames,
917 pParam->nPFrames, pParam->nBFrames);
918 if (m_sIntraperiod.nBFrames != pParam->nBFrames) {
919 DEBUG_PRINT_HIGH("Dynamically changing B-frames not supported");
920 return OMX_ErrorUnsupportedSetting;
921 }
922
923 SWVENC_PROP prop;
924 prop.uProperty.sIntraPeriod.pFrames = pParam->nPFrames;
925 prop.uProperty.sIntraPeriod.bFrames = pParam->nBFrames;
926 prop.ePropId = SWVENC_PROP_ID_INTRA_PERIOD;
927 SwVenc_SetProperty(m_pSwVenc, &prop);
928
929 m_sIntraperiod.nPFrames = pParam->nPFrames;
930 m_sIntraperiod.nBFrames = pParam->nBFrames;
931 m_sIntraperiod.nIDRPeriod = pParam->nIDRPeriod;
932 } else {
933 DEBUG_PRINT_ERROR("ERROR: (QOMX_IndexConfigVideoIntraperiod) Unsupported port index: %u", pParam->nPortIndex);
934 return OMX_ErrorBadPortIndex;
935 }
936
937 break;
938 }
939
940 case OMX_IndexConfigVideoIntraVOPRefresh:
941 {
942 OMX_CONFIG_INTRAREFRESHVOPTYPE* pParam =
943 reinterpret_cast<OMX_CONFIG_INTRAREFRESHVOPTYPE*>(configData);
944
945 DEBUG_PRINT_HIGH("set_config(): OMX_IndexConfigVideoIntraVOPRefresh");
946 if (pParam->nPortIndex == PORT_INDEX_OUT) {
947 SWVENC_PROP prop;
948 prop.ePropId = SWVENC_PROP_ID_IDR_INSERTION;
949 SwVenc_SetProperty(m_pSwVenc, &prop);
950 DEBUG_PRINT_HIGH("Setting SWVENC OMX_IndexConfigVideoIntraVOPRefresh");
951 m_sConfigIntraRefreshVOP.IntraRefreshVOP = pParam->IntraRefreshVOP;
952 } else {
953 DEBUG_PRINT_ERROR("ERROR: Unsupported port index: %u", pParam->nPortIndex);
954 return OMX_ErrorBadPortIndex;
955 }
956
957 break;
958 }
959 case OMX_QcomIndexConfigVideoFramePackingArrangement:
960 {
961 DEBUG_PRINT_HIGH("set_config(): OMX_QcomIndexConfigVideoFramePackingArrangement");
962 if (m_sOutPortFormat.eCompressionFormat == OMX_VIDEO_CodingAVC) {
963 OMX_QCOM_FRAME_PACK_ARRANGEMENT *configFmt =
964 (OMX_QCOM_FRAME_PACK_ARRANGEMENT *) configData;
965 extra_data_handle.set_frame_pack_data(configFmt);
966 } else {
967 DEBUG_PRINT_ERROR("ERROR: FramePackingData not supported for non AVC compression");
968 }
969 break;
970 }
971 default:
972 DEBUG_PRINT_ERROR("ERROR: unsupported index %d", (int) configIndex);
973 return OMX_ErrorUnsupportedSetting;
974 }
975
976 return OMX_ErrorNone;
977 }
978
979 /* ======================================================================
980 FUNCTION
981 omx_swvenc::ComponentDeInit
982
983 DESCRIPTION
984 Destroys the component and release memory allocated to the heap.
985
986 PARAMETERS
987 <TBD>.
988
989 RETURN VALUE
990 OMX Error None if everything successful.
991
992 ========================================================================== */
component_deinit(OMX_IN OMX_HANDLETYPE hComp)993 OMX_ERRORTYPE omx_swvenc::component_deinit(OMX_IN OMX_HANDLETYPE hComp)
994 {
995 OMX_U32 i = 0;
996 DEBUG_PRINT_HIGH("omx_swvenc(): Inside component_deinit()");
997 if (OMX_StateLoaded != m_state) {
998 DEBUG_PRINT_ERROR("WARNING:Rxd DeInit,OMX not in LOADED state %d",\
999 m_state);
1000 }
1001 if (m_out_mem_ptr) {
1002 DEBUG_PRINT_LOW("Freeing the Output Memory");
1003 for (i=0; i< m_sOutPortDef.nBufferCountActual; i++ ) {
1004 free_output_buffer (&m_out_mem_ptr[i]);
1005 }
1006 free(m_out_mem_ptr);
1007 m_out_mem_ptr = NULL;
1008 }
1009
1010 /*Check if the input buffers have to be cleaned up*/
1011 if (m_inp_mem_ptr
1012 #ifdef _ANDROID_ICS_
1013 && !meta_mode_enable
1014 #endif
1015 ) {
1016 DEBUG_PRINT_LOW("Freeing the Input Memory");
1017 for (i=0; i<m_sInPortDef.nBufferCountActual; i++ ) {
1018 free_input_buffer (&m_inp_mem_ptr[i]);
1019 }
1020
1021
1022 free(m_inp_mem_ptr);
1023 m_inp_mem_ptr = NULL;
1024 }
1025
1026 // Reset counters in mesg queues
1027 m_ftb_q.m_size=0;
1028 m_cmd_q.m_size=0;
1029 m_etb_q.m_size=0;
1030 m_ftb_q.m_read = m_ftb_q.m_write =0;
1031 m_cmd_q.m_read = m_cmd_q.m_write =0;
1032 m_etb_q.m_read = m_etb_q.m_write =0;
1033
1034 #ifdef _ANDROID_
1035 // Clear the strong reference
1036 DEBUG_PRINT_HIGH("Calling m_heap_ptr.clear()");
1037 m_heap_ptr.clear();
1038 #endif // _ANDROID_
1039
1040 DEBUG_PRINT_HIGH("Calling SwVenc_Stop()");
1041 SWVENC_STATUS ret = SwVenc_Stop(m_pSwVenc);
1042 if (ret != SWVENC_S_SUCCESS)
1043 {
1044 DEBUG_PRINT_ERROR("SwVenc_Stop Command failed in venc destructor");
1045 }
1046
1047 DEBUG_PRINT_HIGH("Deleting m_pSwVenc HANDLE[%p]", m_pSwVenc);
1048 SwVenc_DeInit(m_pSwVenc);
1049 m_pSwVenc = NULL;
1050
1051 DEBUG_PRINT_HIGH("omx_swvenc:Component Deinit");
1052 return OMX_ErrorNone;
1053 }
1054
1055
dev_stop(void)1056 OMX_U32 omx_swvenc::dev_stop( void)
1057 {
1058 SwVenc_Stop(m_pSwVenc);
1059 post_event (0,0,OMX_COMPONENT_GENERATE_STOP_DONE);
1060 return SWVENC_S_SUCCESS;
1061 }
1062
1063
dev_pause(void)1064 OMX_U32 omx_swvenc::dev_pause(void)
1065 {
1066 return SWVENC_S_SUCCESS;
1067 }
1068
dev_start(void)1069 OMX_U32 omx_swvenc::dev_start(void)
1070 {
1071 SwVenc_Start(m_pSwVenc);
1072 post_event (0,0,OMX_COMPONENT_GENERATE_START_DONE);
1073 return SWVENC_S_SUCCESS;
1074 }
1075
dev_flush(unsigned port)1076 OMX_U32 omx_swvenc::dev_flush(unsigned port)
1077 {
1078 if (port == PORT_INDEX_IN)
1079 {
1080 return SWVENC_S_EUNSUPPORTED;
1081 }
1082
1083 DEBUG_PRINT_HIGH("SwVenc_Flush port %d", port);
1084 return SwVenc_Flush(m_pSwVenc);
1085 }
1086
dev_resume(void)1087 OMX_U32 omx_swvenc::dev_resume(void)
1088 {
1089 return SWVENC_S_SUCCESS;
1090 }
1091
dev_start_done(void)1092 OMX_U32 omx_swvenc::dev_start_done(void)
1093 {
1094 return SWVENC_S_SUCCESS;
1095 }
1096
dev_set_message_thread_id(pthread_t tid)1097 OMX_U32 omx_swvenc::dev_set_message_thread_id(pthread_t tid)
1098 {
1099 return SWVENC_S_SUCCESS;
1100 }
1101
dev_use_buf(void * buf_addr,unsigned port,unsigned index)1102 bool omx_swvenc::dev_use_buf(void *buf_addr,unsigned port,unsigned index)
1103 {
1104 struct pmem* buf = (struct pmem*)buf_addr;
1105 if (port == PORT_INDEX_IN)
1106 {
1107 // m_pSwVencIpBuffer[index].nSize = buf->size;
1108 m_pSwVencIpBuffer[index].pBuffer = (unsigned char*)buf->buffer;
1109 m_pSwVencIpBuffer[index].pClientBufferData = (void*)index;
1110
1111 DEBUG_PRINT_LOW("dev_use_buf input %p, index %d userData %p",
1112 m_pSwVencIpBuffer[index].pBuffer, index, m_pSwVencIpBuffer[index].pClientBufferData);
1113 }
1114 else
1115 {
1116 m_pSwVencOpBuffer[index].nSize = buf->size;
1117 m_pSwVencOpBuffer[index].pBuffer = (unsigned char*)buf->buffer;
1118 m_pSwVencOpBuffer[index].pClientBufferData = (void*)index;
1119 DEBUG_PRINT_LOW("dev_use_buf output %p, index %d userData %p",
1120 m_pSwVencIpBuffer[index].pBuffer, index, m_pSwVencIpBuffer[index].pClientBufferData);
1121 }
1122 return true;
1123 }
1124
dev_free_buf(void * buf_addr,unsigned port)1125 bool omx_swvenc::dev_free_buf(void *buf_addr,unsigned port)
1126 {
1127 struct pmem* buf = (struct pmem*)buf_addr;
1128 int i = 0;
1129 if (port == PORT_INDEX_IN)
1130 {
1131 for (; i<32;i++)
1132 {
1133 if (m_pSwVencIpBuffer[i].pBuffer == buf->buffer)
1134 {
1135 m_pSwVencIpBuffer[i].pBuffer = NULL;
1136 // m_pSwVencIpBuffer[i].nSize = 0;
1137 }
1138 }
1139 }
1140 else
1141 {
1142 for (; i<32;i++)
1143 {
1144 if (m_pSwVencOpBuffer[i].pBuffer == buf->buffer)
1145 {
1146 m_pSwVencOpBuffer[i].pBuffer = NULL;
1147 m_pSwVencOpBuffer[i].nSize = 0;
1148 }
1149 }
1150 }
1151 return true;
1152 }
1153
dump_buffer(unsigned char * buffer,int stride,int scanlines,int width,int height)1154 void dump_buffer(unsigned char* buffer, int stride, int scanlines, int width, int height)
1155 {
1156 static FILE* pFile = NULL;
1157 static int count = 0;
1158 if (count++ >= 100) return;
1159
1160 if (pFile == NULL)
1161 {
1162 pFile = fopen("/data/input.yuv", "wb");
1163 }
1164 if (buffer)
1165 {
1166 char *temp = (char *)buffer;
1167 int i;
1168 int bytes_written = 0;
1169 int bytes = 0;
1170
1171 for (i = 0; i < height; i++) {
1172 bytes_written = fwrite(temp, width, 1, pFile);
1173 temp += stride;
1174 if (bytes_written >0)
1175 bytes += bytes_written * width;
1176 }
1177 temp = (char *)buffer + stride * scanlines;
1178 int stride_c = stride;
1179 for(i = 0; i < height/2; i++) {
1180 bytes_written = fwrite(temp, width, 1, pFile);
1181 temp += stride_c;
1182 if (bytes_written >0)
1183 bytes += bytes_written * width;
1184 }
1185
1186 DEBUG_PRINT_ERROR("stride %d, scanlines %d, frame_height %d bytes_written %d",
1187 stride, scanlines, height, bytes);
1188 }
1189 }
1190
1191 static FILE* gYUV = NULL;
1192
dev_empty_buf(void * buffer,void * pmem_data_buf,unsigned index,unsigned fd)1193 bool omx_swvenc::dev_empty_buf(void *buffer, void *pmem_data_buf,unsigned index,unsigned fd)
1194 {
1195 SWVENC_STATUS status;
1196 SWVENC_IPBUFFER ipbuffer;
1197 OMX_BUFFERHEADERTYPE *bufHdr = (OMX_BUFFERHEADERTYPE *)buffer;
1198
1199 if (meta_mode_enable)
1200 {
1201 unsigned int size = 0, offset = 0;
1202 encoder_media_buffer_type *meta_buf = NULL;
1203 meta_buf = (encoder_media_buffer_type *)bufHdr->pBuffer;
1204 if (meta_buf)
1205 {
1206 if (meta_buf->buffer_type == kMetadataBufferTypeCameraSource)
1207 {
1208 offset = meta_buf->meta_handle->data[1];
1209 size = meta_buf->meta_handle->data[2];
1210 }
1211 else if (meta_buf->buffer_type == kMetadataBufferTypeGrallocSource)
1212 {
1213 private_handle_t *handle = (private_handle_t *)meta_buf->meta_handle;
1214 size = handle->size;
1215 }
1216 }
1217
1218 ipbuffer.pBuffer = (unsigned char *)mmap(NULL, size, PROT_READ|PROT_WRITE,MAP_SHARED, fd, offset);
1219 ipbuffer.nFilledLen = size;
1220 DEBUG_PRINT_LOW("mapped meta buf fd %d size %d %p", fd, size, ipbuffer.pBuffer);
1221 }
1222 else
1223 {
1224 ipbuffer.pBuffer = bufHdr->pBuffer;
1225 ipbuffer.nFilledLen = bufHdr->nFilledLen;
1226 }
1227
1228 ipbuffer.nFlags = bufHdr->nFlags;
1229 ipbuffer.nIpTimestamp = bufHdr->nTimeStamp;
1230 ipbuffer.pClientBufferData = (unsigned char *)bufHdr;
1231
1232 DEBUG_PRINT_LOW("SwVenc_EmptyThisBuffer index %d pBuffer %p", index, ipbuffer.pBuffer);
1233 status = SwVenc_EmptyThisBuffer(m_pSwVenc, &ipbuffer);
1234
1235 if (status != SWVENC_S_SUCCESS)
1236 {
1237 DEBUG_PRINT_ERROR("SwVenc_EmptyThisBuffer failed");
1238 post_event ((unsigned int)buffer,0,OMX_COMPONENT_GENERATE_EBD);
1239 pending_output_buffers--;
1240 }
1241
1242 return status == SWVENC_S_SUCCESS;
1243 }
1244
dev_fill_buf(void * buffer,void * pmem_data_buf,unsigned index,unsigned fd)1245 bool omx_swvenc::dev_fill_buf(void *buffer, void *pmem_data_buf,unsigned index,unsigned fd)
1246 {
1247 SWVENC_STATUS status;
1248 OMX_BUFFERHEADERTYPE* bufHdr = (OMX_BUFFERHEADERTYPE*)buffer;
1249
1250 DEBUG_PRINT_LOW("SwVenc_FillThisBuffer index %d pBuffer %p pmem_data_buf %p",
1251 index, bufHdr->pBuffer, pmem_data_buf);
1252 status = SwVenc_FillThisBuffer(m_pSwVenc, &m_pSwVencOpBuffer[index]);
1253
1254 if (status != SWVENC_S_SUCCESS)
1255 {
1256 DEBUG_PRINT_ERROR("SwVenc_FillThisBuffer failed");
1257 post_event ((unsigned int)buffer,0,OMX_COMPONENT_GENERATE_FBD);
1258 pending_output_buffers--;
1259 }
1260
1261 return status == SWVENC_S_SUCCESS;
1262 }
1263
dev_get_seq_hdr(void * buffer,unsigned size,unsigned * hdrlen)1264 bool omx_swvenc::dev_get_seq_hdr(void *buffer, unsigned size, unsigned *hdrlen)
1265 {
1266 return false;
1267 }
1268
dev_get_capability_ltrcount(OMX_U32 * min,OMX_U32 * max,OMX_U32 * step_size)1269 bool omx_swvenc::dev_get_capability_ltrcount(OMX_U32 *min, OMX_U32 *max, OMX_U32 *step_size)
1270 {
1271 return true;
1272 }
1273
dev_loaded_start()1274 bool omx_swvenc::dev_loaded_start()
1275 {
1276 return true;
1277 }
1278
dev_loaded_stop()1279 bool omx_swvenc::dev_loaded_stop()
1280 {
1281 return true;
1282 }
1283
dev_loaded_start_done()1284 bool omx_swvenc::dev_loaded_start_done()
1285 {
1286 return true;
1287 }
1288
dev_loaded_stop_done()1289 bool omx_swvenc::dev_loaded_stop_done()
1290 {
1291 return true;
1292 }
1293
1294
dev_get_performance_level(OMX_U32 * perflevel)1295 bool omx_swvenc::dev_get_performance_level(OMX_U32 *perflevel)
1296 {
1297 DEBUG_PRINT_ERROR("Get performance level is not supported");
1298 return false;
1299 }
1300
dev_get_vui_timing_info(OMX_U32 * enabled)1301 bool omx_swvenc::dev_get_vui_timing_info(OMX_U32 *enabled)
1302 {
1303 DEBUG_PRINT_ERROR("Get vui timing information is not supported");
1304 return false;
1305 }
1306
dev_get_peak_bitrate(OMX_U32 * peakbitrate)1307 bool omx_swvenc::dev_get_peak_bitrate(OMX_U32 *peakbitrate)
1308 {
1309 DEBUG_PRINT_ERROR("Get peak bitrate is not supported");
1310 return false;
1311 }
1312
dev_get_buf_req(OMX_U32 * min_buff_count,OMX_U32 * actual_buff_count,OMX_U32 * buff_size,OMX_U32 port)1313 bool omx_swvenc::dev_get_buf_req(OMX_U32 *min_buff_count,
1314 OMX_U32 *actual_buff_count,
1315 OMX_U32 *buff_size,
1316 OMX_U32 port)
1317 {
1318 SWVENC_STATUS sRet = SWVENC_S_SUCCESS;
1319 SWVENC_PROP property;
1320 property.ePropId = (port == 0) ? SWVENC_PROP_ID_IPBUFFREQ : SWVENC_PROP_ID_OPBUFFREQ;
1321
1322 sRet = SwVenc_GetProperty(m_pSwVenc, &property);
1323 if (sRet == SWVENC_S_SUCCESS)
1324 {
1325 if (port == 0)
1326 {
1327 *min_buff_count = property.uProperty.sIpBuffReq.nMinCount;
1328 *buff_size = property.uProperty.sIpBuffReq.nSize;
1329 *actual_buff_count = property.uProperty.sIpBuffReq.nMinCount;
1330 DEBUG_PRINT_HIGH("SwVenc input buffer Size =%u Count = %u", *buff_size, *actual_buff_count);
1331 }
1332 else
1333 {
1334 *min_buff_count = property.uProperty.sOpBuffReq.nMinCount;
1335 *buff_size = property.uProperty.sOpBuffReq.nSize;
1336 *actual_buff_count = property.uProperty.sOpBuffReq.nMinCount;
1337 DEBUG_PRINT_HIGH("SwVenc output buffer Size =%u Count = %u", property.uProperty.sOpBuffReq.nSize, property.uProperty.sOpBuffReq.nMinCount);
1338 }
1339 }
1340
1341 return (sRet == SWVENC_S_SUCCESS);
1342 }
1343
dev_set_buf_req(OMX_U32 * min_buff_count,OMX_U32 * actual_buff_count,OMX_U32 * buff_size,OMX_U32 port)1344 bool omx_swvenc::dev_set_buf_req(OMX_U32 *min_buff_count,
1345 OMX_U32 *actual_buff_count,
1346 OMX_U32 *buff_size,
1347 OMX_U32 port)
1348 {
1349 SWVENC_PROP property;
1350 SWVENC_STATUS sRet = SWVENC_S_SUCCESS;
1351
1352 if (port != PORT_INDEX_IN || port != PORT_INDEX_OUT) return false;
1353 if (*min_buff_count > *actual_buff_count) return false;
1354
1355 if(port == PORT_INDEX_IN)
1356 {
1357 property.ePropId = SWVENC_PROP_ID_IPBUFFREQ;
1358 property.uProperty.sIpBuffReq.nSize = *buff_size;;
1359 property.uProperty.sIpBuffReq.nMaxCount = *actual_buff_count;
1360 property.uProperty.sIpBuffReq.nMinCount = *actual_buff_count;
1361 DEBUG_PRINT_HIGH("Set SwVenc input Buffer Size =%d Count = %d",property.uProperty.sIpBuffReq.nSize, *actual_buff_count);
1362 }
1363 else if (port == PORT_INDEX_OUT)
1364 {
1365 property.ePropId = SWVENC_PROP_ID_OPBUFFREQ;
1366 property.uProperty.sOpBuffReq.nSize = *buff_size;
1367 property.uProperty.sOpBuffReq.nMaxCount = *actual_buff_count;
1368 property.uProperty.sOpBuffReq.nMinCount = *actual_buff_count;
1369 DEBUG_PRINT_HIGH("Set SwVenc output Buffer Size =%d and Count = %d",property.uProperty.sOpBuffReq.nSize, *actual_buff_count);
1370 }
1371
1372 sRet = SwVenc_SetProperty(m_pSwVenc, &property);
1373 if (sRet != SWVENC_S_SUCCESS)
1374 {
1375 DEBUG_PRINT_ERROR("Set buffer requirements from ARM codec failed");
1376 }
1377
1378 return sRet == SWVENC_S_SUCCESS;
1379 }
1380
dev_is_video_session_supported(OMX_U32 width,OMX_U32 height)1381 bool omx_swvenc::dev_is_video_session_supported(OMX_U32 width, OMX_U32 height)
1382 {
1383 if (width > 1280 || height > 720) return false;
1384 return true;
1385 }
1386
1387
dev_handle_extradata(void * buffer,int index)1388 int omx_swvenc::dev_handle_extradata(void *buffer, int index)
1389 {
1390 return SWVENC_S_EUNSUPPORTED;
1391 }
1392
dev_set_format(int color)1393 int omx_swvenc::dev_set_format(int color)
1394 {
1395 return SWVENC_S_SUCCESS;
1396 }
1397
dev_color_align(OMX_BUFFERHEADERTYPE * buffer,OMX_U32 width,OMX_U32 height)1398 bool omx_swvenc::dev_color_align(OMX_BUFFERHEADERTYPE *buffer,
1399 OMX_U32 width, OMX_U32 height)
1400 {
1401 if(secure_session) {
1402 DEBUG_PRINT_ERROR("Cannot align colors in secure session.");
1403 return OMX_FALSE;
1404 }
1405 return true;
1406 }
1407
is_secure_session()1408 bool omx_swvenc::is_secure_session()
1409 {
1410 return secure_session;
1411 }
1412
dev_get_output_log_flag()1413 bool omx_swvenc::dev_get_output_log_flag()
1414 {
1415 return false;
1416 }
1417
dev_output_log_buffers(const char * buffer,int bufferlen)1418 int omx_swvenc::dev_output_log_buffers(const char *buffer, int bufferlen)
1419 {
1420 return 0;
1421 }
1422
dev_extradata_log_buffers(char * buffer)1423 int omx_swvenc::dev_extradata_log_buffers(char *buffer)
1424 {
1425 return 0;
1426 }
1427
swvenc_input_buffer_done_cb(SWVENC_HANDLE pSwEnc,SWVENC_IPBUFFER * pIpBuffer,void * pClientHandle)1428 SWVENC_STATUS omx_swvenc::swvenc_input_buffer_done_cb
1429 (
1430 SWVENC_HANDLE pSwEnc,
1431 SWVENC_IPBUFFER *pIpBuffer,
1432 void *pClientHandle
1433 )
1434 {
1435 SWVENC_STATUS eRet = SWVENC_S_SUCCESS;
1436 omx_swvenc *omx = reinterpret_cast<omx_swvenc*>(pClientHandle);
1437
1438 if (pIpBuffer == NULL)
1439 {
1440 eRet = SWVENC_S_EFAIL;
1441 }
1442 else
1443 {
1444 omx->swvenc_input_buffer_done(pIpBuffer);
1445 }
1446
1447 return eRet;
1448 }
1449
swvenc_input_buffer_done(SWVENC_IPBUFFER * pIpBuffer)1450 void omx_swvenc::swvenc_input_buffer_done(SWVENC_IPBUFFER *pIpBuffer)
1451 {
1452 OMX_BUFFERHEADERTYPE *bufHdr = (OMX_BUFFERHEADERTYPE *)pIpBuffer->pClientBufferData;
1453
1454 if (meta_mode_enable)
1455 {
1456 omx_release_meta_buffer(bufHdr);
1457
1458 // fd is not dupped, nothing needs to be done here
1459 munmap(pIpBuffer->pBuffer, pIpBuffer->nFilledLen);
1460 }
1461
1462 DEBUG_PRINT_LOW("swvenc_empty_buffer_done bufHdr %p pBuffer %p = %p nFilledLen %d nFlags %x",
1463 bufHdr, bufHdr->pBuffer, pIpBuffer->pBuffer, pIpBuffer->nFilledLen, pIpBuffer->nFlags);
1464
1465 post_event((unsigned int)(bufHdr), SWVENC_S_SUCCESS, OMX_COMPONENT_GENERATE_EBD);
1466 }
1467
swvenc_fill_buffer_done_cb(SWVENC_HANDLE pSwEnc,SWVENC_OPBUFFER * m_pSWVencOpBuffer,void * pClientHandle)1468 SWVENC_STATUS omx_swvenc::swvenc_fill_buffer_done_cb
1469 (
1470 SWVENC_HANDLE pSwEnc,
1471 SWVENC_OPBUFFER *m_pSWVencOpBuffer,
1472 void *pClientHandle
1473 )
1474 {
1475 SWVENC_STATUS eRet = SWVENC_S_SUCCESS;
1476 omx_swvenc *omx = reinterpret_cast<omx_swvenc*>(pClientHandle);
1477
1478 if (m_pSWVencOpBuffer == NULL)
1479 {
1480 eRet = SWVENC_S_EFAIL;
1481 }
1482 else
1483 {
1484 omx->swvenc_fill_buffer_done(m_pSWVencOpBuffer);
1485 }
1486 return eRet;
1487 }
1488
swvenc_fill_buffer_done(SWVENC_OPBUFFER * pOpBuffer)1489 void omx_swvenc::swvenc_fill_buffer_done(SWVENC_OPBUFFER *pOpBuffer)
1490 {
1491 int index = (int)pOpBuffer->pClientBufferData;
1492 OMX_BUFFERHEADERTYPE *bufHdr = m_out_mem_ptr + index;
1493
1494 bufHdr->nOffset = 0;
1495 bufHdr->nFilledLen = pOpBuffer->nFilledLen;
1496 bufHdr->nFlags = pOpBuffer->nFlags;
1497 bufHdr->nTimeStamp = pOpBuffer->nOpTimestamp;
1498
1499 if (bufHdr->nFlags & OMX_BUFFERFLAG_EOS)
1500 {
1501 DEBUG_PRINT_ERROR("swvenc output EOS reached\n");
1502 }
1503
1504 /*Use buffer case*/
1505 if (output_use_buffer && !m_use_output_pmem &&
1506 !output_flush_progress && pOpBuffer->nFilledLen)
1507 {
1508 DEBUG_PRINT_LOW("memcpy for o/p Heap UseBuffer size %d", pOpBuffer->nFilledLen);
1509 memcpy(bufHdr->pBuffer, pOpBuffer->pBuffer, pOpBuffer->nFilledLen);
1510 }
1511
1512 DEBUG_PRINT_LOW("swvenc_fill_buffer_done bufHdr %p pBuffer %p = %p idx %d nFilledLen %d nFlags %x\n",
1513 bufHdr, bufHdr->pBuffer, pOpBuffer->pBuffer, index, pOpBuffer->nFilledLen, pOpBuffer->nFlags);
1514 post_event((unsigned int)bufHdr, SWVENC_S_SUCCESS, OMX_COMPONENT_GENERATE_FBD);
1515 }
1516
swvenc_handle_event_cb(SWVENC_HANDLE pSwEnc,SWVENC_EVENTHANDLER * pEventHandler,void * pClientHandle)1517 SWVENC_STATUS omx_swvenc::swvenc_handle_event_cb
1518 (
1519 SWVENC_HANDLE pSwEnc,
1520 SWVENC_EVENTHANDLER* pEventHandler,
1521 void *pClientHandle
1522 )
1523 {
1524 omx_swvenc *omx = reinterpret_cast<omx_swvenc*>(pClientHandle);
1525 omx->swvenc_handle_event(pEventHandler);
1526 return SWVENC_S_SUCCESS;
1527 }
1528
swvenc_handle_event(SWVENC_EVENTHANDLER * pEvent)1529 void omx_swvenc::swvenc_handle_event(SWVENC_EVENTHANDLER *pEvent)
1530 {
1531 switch(pEvent->eEvent)
1532 {
1533 case SWVENC_FLUSH_DONE:
1534 DEBUG_PRINT_HIGH("SWVENC_FLUSH_DONE input_flush_progress %d output_flush_progress %d\n",
1535 input_flush_progress, output_flush_progress);
1536 if (input_flush_progress)
1537 {
1538 post_event ((unsigned)NULL, SWVENC_S_SUCCESS, OMX_COMPONENT_GENERATE_EVENT_INPUT_FLUSH);
1539 }
1540 if (output_flush_progress)
1541 {
1542 post_event ((unsigned)NULL, SWVENC_S_SUCCESS, OMX_COMPONENT_GENERATE_EVENT_OUTPUT_FLUSH);
1543 }
1544 break;
1545 case SWVENC_ERROR:
1546 break;
1547
1548 default:
1549 break;
1550 }
1551
1552 }
1553
1554
1555