blob: 0f8e99857a750948ca628d614f765eb2ae42c848 [file] [log] [blame]
Shalaj Jain273b3e02012-06-22 19:08:03 -07001/*--------------------------------------------------------------------------
Maheshwar Ajja507d6552014-01-03 14:54:29 +05302Copyright (c) 2010 - 2014, The Linux Foundation. All rights reserved.
Shalaj Jain273b3e02012-06-22 19:08:03 -07003
4Redistribution and use in source and binary forms, with or without
5modification, 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.
Vinay Kaliae4a7d9d2013-01-21 10:16:33 -080011 * Neither the name of The Linux Foundation nor
Shalaj Jain273b3e02012-06-22 19:08:03 -070012 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
16THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
20CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
23OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
24WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
25OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
26ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27--------------------------------------------------------------------------*/
28
29/*============================================================================
30 O p e n M A X w r a p p e r s
31 O p e n M A X C o r e
32
33*//** @file omx_vdec.cpp
34 This module contains the implementation of the OpenMAX core & component.
35
36*//*========================================================================*/
37
38//////////////////////////////////////////////////////////////////////////////
39// Include Files
40//////////////////////////////////////////////////////////////////////////////
41
42#include <string.h>
43#include <pthread.h>
44#include <sys/prctl.h>
45#include <stdlib.h>
46#include <unistd.h>
47#include <errno.h>
48#include "omx_vdec.h"
49#include <fcntl.h>
50#include <limits.h>
Deva Ramasubramanian15bbc1c2013-05-13 16:05:03 -070051#include <stdlib.h>
Arun Menonbdb80b02013-08-12 17:45:54 -070052#include <media/hardware/HardwareAPI.h>
Vinay Kaliada8f3cf2012-12-21 18:26:21 -080053#include <media/msm_media_info.h>
Shalaj Jain273b3e02012-06-22 19:08:03 -070054
55#ifndef _ANDROID_
56#include <sys/ioctl.h>
57#include <sys/mman.h>
58#endif //_ANDROID_
59
60#ifdef _ANDROID_
61#include <cutils/properties.h>
62#undef USE_EGL_IMAGE_GPU
63#endif
64
Vinay Kalia0e75e9a2012-09-27 15:41:53 -070065#include <qdMetaData.h>
Shalaj Jain273b3e02012-06-22 19:08:03 -070066
67#ifdef _ANDROID_
68#include "DivXDrmDecrypt.h"
69#endif //_ANDROID_
70
Arun Menon45346052013-11-13 12:40:08 -080071#ifdef METADATA_FOR_DYNAMIC_MODE
Arun Menon9af783f2013-10-22 12:57:14 -070072#include "QComOMXMetadata.h"
73#endif
74
Shalaj Jain273b3e02012-06-22 19:08:03 -070075#ifdef USE_EGL_IMAGE_GPU
76#include <EGL/egl.h>
77#include <EGL/eglQCOM.h>
78#define EGL_BUFFER_HANDLE_QCOM 0x4F00
79#define EGL_BUFFER_OFFSET_QCOM 0x4F01
80#endif
Vinay Kalia21649b32013-03-18 17:28:07 -070081
Jayasena Sangaraboina51230642013-08-21 18:02:13 -070082#define BUFFER_LOG_LOC "/data/misc/media"
83
Shalaj Jain273b3e02012-06-22 19:08:03 -070084#ifdef OUTPUT_EXTRADATA_LOG
85FILE *outputExtradataFile;
Deva Ramasubramanianee6f1f42014-01-31 12:49:18 -080086char output_extradata_filename [] = "/data/misc/extradata";
Shalaj Jain273b3e02012-06-22 19:08:03 -070087#endif
88
89#define DEFAULT_FPS 30
90#define MAX_INPUT_ERROR DEFAULT_FPS
91#define MAX_SUPPORTED_FPS 120
Deepak Vermaa2efdb12013-12-26 12:30:05 +053092#define DEFAULT_WIDTH_ALIGNMENT 128
93#define DEFAULT_HEIGHT_ALIGNMENT 32
Shalaj Jain273b3e02012-06-22 19:08:03 -070094
95#define VC1_SP_MP_START_CODE 0xC5000000
96#define VC1_SP_MP_START_CODE_MASK 0xFF000000
97#define VC1_AP_SEQ_START_CODE 0x0F010000
98#define VC1_STRUCT_C_PROFILE_MASK 0xF0
99#define VC1_STRUCT_B_LEVEL_MASK 0xE0000000
100#define VC1_SIMPLE_PROFILE 0
101#define VC1_MAIN_PROFILE 1
102#define VC1_ADVANCE_PROFILE 3
103#define VC1_SIMPLE_PROFILE_LOW_LEVEL 0
104#define VC1_SIMPLE_PROFILE_MED_LEVEL 2
105#define VC1_STRUCT_C_LEN 4
106#define VC1_STRUCT_C_POS 8
107#define VC1_STRUCT_A_POS 12
108#define VC1_STRUCT_B_POS 24
109#define VC1_SEQ_LAYER_SIZE 36
Vinay Kaliab09886c2012-08-20 11:27:25 -0700110#define POLL_TIMEOUT 0x7fffffff
Shalaj Jain273b3e02012-06-22 19:08:03 -0700111
112#define MEM_DEVICE "/dev/ion"
113#define MEM_HEAP_ID ION_CP_MM_HEAP_ID
114
115#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -0700116extern "C" {
117#include<utils/Log.h>
118}
Shalaj Jain273b3e02012-06-22 19:08:03 -0700119#endif//_ANDROID_
120
Vinay Kalia53fa6832012-10-11 17:55:30 -0700121#define SZ_4K 0x1000
122#define SZ_1M 0x100000
123
Shalaj Jain273b3e02012-06-22 19:08:03 -0700124#define Log2(number, power) { OMX_U32 temp = number; power = 0; while( (0 == (temp & 0x1)) && power < 16) { temp >>=0x1; power++; } }
125#define Q16ToFraction(q,num,den) { OMX_U32 power; Log2(q,power); num = q >> power; den = 0x1 << (16 - power); }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -0700126#define EXTRADATA_IDX(__num_planes) (__num_planes - 1)
127
Vinay Kaliadb90f8c2012-11-19 18:57:56 -0800128#define DEFAULT_EXTRADATA (OMX_INTERLACE_EXTRADATA)
Jia Meng3a3c6492013-12-19 17:16:52 +0800129#define DEFAULT_CONCEAL_COLOR "32896" //0x8080, black by default
Jayasena Sangaraboinac4dfc282013-08-08 12:41:39 -0700130
131int debug_level = PRIO_ERROR;
132
Deepak Vermaa2efdb12013-12-26 12:30:05 +0530133static OMX_U32 maxSmoothStreamingWidth = 1920;
134static OMX_U32 maxSmoothStreamingHeight = 1088;
Praveen Chavancf924182013-12-06 23:16:23 -0800135
Shalaj Jain273b3e02012-06-22 19:08:03 -0700136void* async_message_thread (void *input)
137{
Arun Menon906de572013-06-18 17:01:40 -0700138 OMX_BUFFERHEADERTYPE *buffer;
139 struct v4l2_plane plane[VIDEO_MAX_PLANES];
140 struct pollfd pfd;
141 struct v4l2_buffer v4l2_buf;
142 memset((void *)&v4l2_buf,0,sizeof(v4l2_buf));
143 struct v4l2_event dqevent;
144 omx_vdec *omx = reinterpret_cast<omx_vdec*>(input);
145 pfd.events = POLLIN | POLLRDNORM | POLLOUT | POLLWRNORM | POLLRDBAND | POLLPRI;
146 pfd.fd = omx->drv_ctx.video_driver_fd;
147 int error_code = 0,rc=0,bytes_read = 0,bytes_written = 0;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700148 DEBUG_PRINT_HIGH("omx_vdec: Async thread start");
Arun Menon906de572013-06-18 17:01:40 -0700149 prctl(PR_SET_NAME, (unsigned long)"VideoDecCallBackThread", 0, 0, 0);
150 while (1) {
151 rc = poll(&pfd, 1, POLL_TIMEOUT);
152 if (!rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700153 DEBUG_PRINT_ERROR("Poll timedout");
Arun Menon906de572013-06-18 17:01:40 -0700154 break;
155 } else if (rc < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700156 DEBUG_PRINT_ERROR("Error while polling: %d", rc);
Arun Menon906de572013-06-18 17:01:40 -0700157 break;
158 }
159 if ((pfd.revents & POLLIN) || (pfd.revents & POLLRDNORM)) {
160 struct vdec_msginfo vdec_msg;
161 v4l2_buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
162 v4l2_buf.memory = V4L2_MEMORY_USERPTR;
163 v4l2_buf.length = omx->drv_ctx.num_planes;
164 v4l2_buf.m.planes = plane;
165 while (!ioctl(pfd.fd, VIDIOC_DQBUF, &v4l2_buf)) {
166 vdec_msg.msgcode=VDEC_MSG_RESP_OUTPUT_BUFFER_DONE;
167 vdec_msg.status_code=VDEC_S_SUCCESS;
168 vdec_msg.msgdata.output_frame.client_data=(void*)&v4l2_buf;
169 vdec_msg.msgdata.output_frame.len=plane[0].bytesused;
170 vdec_msg.msgdata.output_frame.bufferaddr=(void*)plane[0].m.userptr;
171 vdec_msg.msgdata.output_frame.time_stamp= ((uint64_t)v4l2_buf.timestamp.tv_sec * (uint64_t)1000000) +
172 (uint64_t)v4l2_buf.timestamp.tv_usec;
173 if (vdec_msg.msgdata.output_frame.len) {
174 vdec_msg.msgdata.output_frame.framesize.left = plane[0].reserved[2];
175 vdec_msg.msgdata.output_frame.framesize.top = plane[0].reserved[3];
176 vdec_msg.msgdata.output_frame.framesize.right = plane[0].reserved[4];
177 vdec_msg.msgdata.output_frame.framesize.bottom = plane[0].reserved[5];
178 }
179 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700180 DEBUG_PRINT_HIGH("async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700181 break;
182 }
183 }
184 }
185 if ((pfd.revents & POLLOUT) || (pfd.revents & POLLWRNORM)) {
186 struct vdec_msginfo vdec_msg;
187 v4l2_buf.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
188 v4l2_buf.memory = V4L2_MEMORY_USERPTR;
189 v4l2_buf.length = 1;
190 v4l2_buf.m.planes = plane;
191 while (!ioctl(pfd.fd, VIDIOC_DQBUF, &v4l2_buf)) {
192 vdec_msg.msgcode=VDEC_MSG_RESP_INPUT_BUFFER_DONE;
193 vdec_msg.status_code=VDEC_S_SUCCESS;
194 vdec_msg.msgdata.input_frame_clientdata=(void*)&v4l2_buf;
195 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700196 DEBUG_PRINT_HIGH("async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700197 break;
198 }
199 }
200 }
201 if (pfd.revents & POLLPRI) {
202 rc = ioctl(pfd.fd, VIDIOC_DQEVENT, &dqevent);
203 if (dqevent.type == V4L2_EVENT_MSM_VIDC_PORT_SETTINGS_CHANGED_INSUFFICIENT ) {
204 struct vdec_msginfo vdec_msg;
205 vdec_msg.msgcode=VDEC_MSG_EVT_CONFIG_CHANGED;
206 vdec_msg.status_code=VDEC_S_SUCCESS;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700207 DEBUG_PRINT_HIGH("VIDC Port Reconfig recieved insufficient");
Arun Menon906de572013-06-18 17:01:40 -0700208 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700209 DEBUG_PRINT_HIGH("async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700210 break;
211 }
212 } else if (dqevent.type == V4L2_EVENT_MSM_VIDC_FLUSH_DONE) {
213 struct vdec_msginfo vdec_msg;
214 vdec_msg.msgcode=VDEC_MSG_RESP_FLUSH_INPUT_DONE;
215 vdec_msg.status_code=VDEC_S_SUCCESS;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700216 DEBUG_PRINT_HIGH("VIDC Input Flush Done Recieved");
Arun Menon906de572013-06-18 17:01:40 -0700217 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700218 DEBUG_PRINT_HIGH("async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700219 break;
220 }
221 vdec_msg.msgcode=VDEC_MSG_RESP_FLUSH_OUTPUT_DONE;
222 vdec_msg.status_code=VDEC_S_SUCCESS;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700223 DEBUG_PRINT_HIGH("VIDC Output Flush Done Recieved");
Arun Menon906de572013-06-18 17:01:40 -0700224 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700225 DEBUG_PRINT_HIGH("async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700226 break;
227 }
228 } else if (dqevent.type == V4L2_EVENT_MSM_VIDC_CLOSE_DONE) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700229 DEBUG_PRINT_HIGH("VIDC Close Done Recieved and async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700230 break;
231 } else if (dqevent.type == V4L2_EVENT_MSM_VIDC_SYS_ERROR) {
232 struct vdec_msginfo vdec_msg;
233 vdec_msg.msgcode=VDEC_MSG_EVT_HW_ERROR;
234 vdec_msg.status_code=VDEC_S_SUCCESS;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700235 DEBUG_PRINT_HIGH("SYS Error Recieved");
Arun Menon906de572013-06-18 17:01:40 -0700236 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700237 DEBUG_PRINT_HIGH("async_message_thread Exited");
Arun Menon906de572013-06-18 17:01:40 -0700238 break;
239 }
Arun Menon45346052013-11-13 12:40:08 -0800240 } else if (dqevent.type == V4L2_EVENT_MSM_VIDC_RELEASE_BUFFER_REFERENCE) {
Arun Menonbdb80b02013-08-12 17:45:54 -0700241 unsigned int *ptr = (unsigned int *)dqevent.u.data;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700242 DEBUG_PRINT_LOW("REFERENCE RELEASE EVENT RECVD fd = %d offset = %d", ptr[0], ptr[1]);
Arun Menonbdb80b02013-08-12 17:45:54 -0700243 omx->buf_ref_remove(ptr[0], ptr[1]);
244 } else if (dqevent.type == V4L2_EVENT_MSM_VIDC_RELEASE_UNQUEUED_BUFFER) {
245 unsigned int *ptr = (unsigned int *)dqevent.u.data;
246 struct vdec_msginfo vdec_msg;
247
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700248 DEBUG_PRINT_LOW("Release unqueued buffer event recvd fd = %d offset = %d", ptr[0], ptr[1]);
Arun Menonbdb80b02013-08-12 17:45:54 -0700249
250 v4l2_buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
251 v4l2_buf.memory = V4L2_MEMORY_USERPTR;
252 v4l2_buf.length = omx->drv_ctx.num_planes;
253 v4l2_buf.m.planes = plane;
254 v4l2_buf.index = ptr[5];
255 v4l2_buf.flags = 0;
256
257 vdec_msg.msgcode = VDEC_MSG_RESP_OUTPUT_BUFFER_DONE;
258 vdec_msg.status_code = VDEC_S_SUCCESS;
259 vdec_msg.msgdata.output_frame.client_data = (void*)&v4l2_buf;
260 vdec_msg.msgdata.output_frame.len = 0;
261 vdec_msg.msgdata.output_frame.bufferaddr = (void*)ptr[2];
262 vdec_msg.msgdata.output_frame.time_stamp = ((uint64_t)ptr[3] * (uint64_t)1000000) +
263 (uint64_t)ptr[4];
264 if (omx->async_message_process(input,&vdec_msg) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700265 DEBUG_PRINT_HIGH("async_message_thread Exitedn");
Arun Menonbdb80b02013-08-12 17:45:54 -0700266 break;
267 }
268 }
Arun Menonbdb80b02013-08-12 17:45:54 -0700269 else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700270 DEBUG_PRINT_HIGH("VIDC Some Event recieved");
Arun Menon906de572013-06-18 17:01:40 -0700271 continue;
272 }
273 }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -0700274 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700275 DEBUG_PRINT_HIGH("omx_vdec: Async thread stop");
Arun Menon906de572013-06-18 17:01:40 -0700276 return NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700277}
278
279void* message_thread(void *input)
280{
Arun Menon906de572013-06-18 17:01:40 -0700281 omx_vdec* omx = reinterpret_cast<omx_vdec*>(input);
282 unsigned char id;
283 int n;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700284
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700285 DEBUG_PRINT_HIGH("omx_vdec: message thread start");
Arun Menon906de572013-06-18 17:01:40 -0700286 prctl(PR_SET_NAME, (unsigned long)"VideoDecMsgThread", 0, 0, 0);
287 while (1) {
Shalaj Jain273b3e02012-06-22 19:08:03 -0700288
Arun Menon906de572013-06-18 17:01:40 -0700289 n = read(omx->m_pipe_in, &id, 1);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700290
Arun Menon906de572013-06-18 17:01:40 -0700291 if (0 == n) {
292 break;
293 }
294
295 if (1 == n) {
296 omx->process_event_cb(omx, id);
297 }
298 if ((n < 0) && (errno != EINTR)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700299 DEBUG_PRINT_LOW("ERROR: read from pipe failed, ret %d errno %d", n, errno);
Arun Menon906de572013-06-18 17:01:40 -0700300 break;
301 }
Shalaj Jain273b3e02012-06-22 19:08:03 -0700302 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700303 DEBUG_PRINT_HIGH("omx_vdec: message thread stop");
Arun Menon906de572013-06-18 17:01:40 -0700304 return 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700305}
306
307void post_message(omx_vdec *omx, unsigned char id)
308{
Arun Menon906de572013-06-18 17:01:40 -0700309 int ret_value;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700310 DEBUG_PRINT_LOW("omx_vdec: post_message %d pipe out%d", id,omx->m_pipe_out);
Arun Menon906de572013-06-18 17:01:40 -0700311 ret_value = write(omx->m_pipe_out, &id, 1);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700312 DEBUG_PRINT_LOW("post_message to pipe done %d",ret_value);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700313}
314
315// omx_cmd_queue destructor
316omx_vdec::omx_cmd_queue::~omx_cmd_queue()
317{
Arun Menon906de572013-06-18 17:01:40 -0700318 // Nothing to do
Shalaj Jain273b3e02012-06-22 19:08:03 -0700319}
320
321// omx cmd queue constructor
322omx_vdec::omx_cmd_queue::omx_cmd_queue(): m_read(0),m_write(0),m_size(0)
323{
324 memset(m_q,0,sizeof(omx_event)*OMX_CORE_CONTROL_CMDQ_SIZE);
325}
326
327// omx cmd queue insert
328bool omx_vdec::omx_cmd_queue::insert_entry(unsigned p1, unsigned p2, unsigned id)
329{
Arun Menon906de572013-06-18 17:01:40 -0700330 bool ret = true;
331 if (m_size < OMX_CORE_CONTROL_CMDQ_SIZE) {
332 m_q[m_write].id = id;
333 m_q[m_write].param1 = p1;
334 m_q[m_write].param2 = p2;
335 m_write++;
336 m_size ++;
337 if (m_write >= OMX_CORE_CONTROL_CMDQ_SIZE) {
338 m_write = 0;
339 }
340 } else {
341 ret = false;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700342 DEBUG_PRINT_ERROR("ERROR: %s()::Command Queue Full", __func__);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700343 }
Arun Menon906de572013-06-18 17:01:40 -0700344 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700345}
346
347// omx cmd queue pop
348bool omx_vdec::omx_cmd_queue::pop_entry(unsigned *p1, unsigned *p2, unsigned *id)
349{
Arun Menon906de572013-06-18 17:01:40 -0700350 bool ret = true;
351 if (m_size > 0) {
352 *id = m_q[m_read].id;
353 *p1 = m_q[m_read].param1;
354 *p2 = m_q[m_read].param2;
355 // Move the read pointer ahead
356 ++m_read;
357 --m_size;
358 if (m_read >= OMX_CORE_CONTROL_CMDQ_SIZE) {
359 m_read = 0;
360 }
361 } else {
362 ret = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700363 }
Arun Menon906de572013-06-18 17:01:40 -0700364 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700365}
366
367// Retrieve the first mesg type in the queue
368unsigned omx_vdec::omx_cmd_queue::get_q_msg_type()
369{
370 return m_q[m_read].id;
371}
372
373#ifdef _ANDROID_
374omx_vdec::ts_arr_list::ts_arr_list()
375{
Arun Menon906de572013-06-18 17:01:40 -0700376 //initialize timestamps array
377 memset(m_ts_arr_list, 0, ( sizeof(ts_entry) * MAX_NUM_INPUT_OUTPUT_BUFFERS) );
Shalaj Jain273b3e02012-06-22 19:08:03 -0700378}
379omx_vdec::ts_arr_list::~ts_arr_list()
380{
Arun Menon906de572013-06-18 17:01:40 -0700381 //free m_ts_arr_list?
Shalaj Jain273b3e02012-06-22 19:08:03 -0700382}
383
384bool omx_vdec::ts_arr_list::insert_ts(OMX_TICKS ts)
385{
Arun Menon906de572013-06-18 17:01:40 -0700386 bool ret = true;
387 bool duplicate_ts = false;
388 int idx = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700389
Arun Menon906de572013-06-18 17:01:40 -0700390 //insert at the first available empty location
391 for ( ; idx < MAX_NUM_INPUT_OUTPUT_BUFFERS; idx++) {
392 if (!m_ts_arr_list[idx].valid) {
393 //found invalid or empty entry, save timestamp
394 m_ts_arr_list[idx].valid = true;
395 m_ts_arr_list[idx].timestamp = ts;
396 DEBUG_PRINT_LOW("Insert_ts(): Inserting TIMESTAMP (%lld) at idx (%d)",
397 ts, idx);
398 break;
399 }
Shalaj Jain273b3e02012-06-22 19:08:03 -0700400 }
Shalaj Jain273b3e02012-06-22 19:08:03 -0700401
Arun Menon906de572013-06-18 17:01:40 -0700402 if (idx == MAX_NUM_INPUT_OUTPUT_BUFFERS) {
403 DEBUG_PRINT_LOW("Timestamp array list is FULL. Unsuccessful insert");
404 ret = false;
405 }
406 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700407}
408
409bool omx_vdec::ts_arr_list::pop_min_ts(OMX_TICKS &ts)
410{
Arun Menon906de572013-06-18 17:01:40 -0700411 bool ret = true;
412 int min_idx = -1;
413 OMX_TICKS min_ts = 0;
414 int idx = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700415
Arun Menon906de572013-06-18 17:01:40 -0700416 for ( ; idx < MAX_NUM_INPUT_OUTPUT_BUFFERS; idx++) {
Shalaj Jain273b3e02012-06-22 19:08:03 -0700417
Arun Menon906de572013-06-18 17:01:40 -0700418 if (m_ts_arr_list[idx].valid) {
419 //found valid entry, save index
420 if (min_idx < 0) {
421 //first valid entry
422 min_ts = m_ts_arr_list[idx].timestamp;
423 min_idx = idx;
424 } else if (m_ts_arr_list[idx].timestamp < min_ts) {
425 min_ts = m_ts_arr_list[idx].timestamp;
426 min_idx = idx;
427 }
428 }
429
Shalaj Jain273b3e02012-06-22 19:08:03 -0700430 }
431
Arun Menon906de572013-06-18 17:01:40 -0700432 if (min_idx < 0) {
433 //no valid entries found
434 DEBUG_PRINT_LOW("Timestamp array list is empty. Unsuccessful pop");
435 ts = 0;
436 ret = false;
437 } else {
438 ts = m_ts_arr_list[min_idx].timestamp;
439 m_ts_arr_list[min_idx].valid = false;
440 DEBUG_PRINT_LOW("Pop_min_ts:Timestamp (%lld), index(%d)",
441 ts, min_idx);
442 }
Shalaj Jain273b3e02012-06-22 19:08:03 -0700443
Arun Menon906de572013-06-18 17:01:40 -0700444 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700445
446}
447
448
449bool omx_vdec::ts_arr_list::reset_ts_list()
450{
Arun Menon906de572013-06-18 17:01:40 -0700451 bool ret = true;
452 int idx = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700453
Arun Menon906de572013-06-18 17:01:40 -0700454 DEBUG_PRINT_LOW("reset_ts_list(): Resetting timestamp array list");
455 for ( ; idx < MAX_NUM_INPUT_OUTPUT_BUFFERS; idx++) {
456 m_ts_arr_list[idx].valid = false;
457 }
458 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700459}
460#endif
461
462// factory function executed by the core to create instances
463void *get_omx_component_factory_fn(void)
464{
Arun Menon906de572013-06-18 17:01:40 -0700465 return (new omx_vdec);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700466}
467
468#ifdef _ANDROID_
469#ifdef USE_ION
470VideoHeap::VideoHeap(int devicefd, size_t size, void* base,
Arun Menon906de572013-06-18 17:01:40 -0700471 struct ion_handle *handle, int ionMapfd)
Shalaj Jain273b3e02012-06-22 19:08:03 -0700472{
Arun Menon906de572013-06-18 17:01:40 -0700473 // ionInit(devicefd, base, size, 0 , MEM_DEVICE,handle,ionMapfd);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700474}
475#else
476VideoHeap::VideoHeap(int fd, size_t size, void* base)
477{
478 // dup file descriptor, map once, use pmem
479 init(dup(fd), base, size, 0 , MEM_DEVICE);
480}
481#endif
482#endif // _ANDROID_
483/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -0700484 FUNCTION
485 omx_vdec::omx_vdec
Shalaj Jain273b3e02012-06-22 19:08:03 -0700486
Arun Menon906de572013-06-18 17:01:40 -0700487 DESCRIPTION
488 Constructor
Shalaj Jain273b3e02012-06-22 19:08:03 -0700489
Arun Menon906de572013-06-18 17:01:40 -0700490 PARAMETERS
491 None
Shalaj Jain273b3e02012-06-22 19:08:03 -0700492
Arun Menon906de572013-06-18 17:01:40 -0700493 RETURN VALUE
494 None.
495 ========================================================================== */
Deva Ramasubramanian5c241242013-02-19 17:25:30 -0800496omx_vdec::omx_vdec(): m_error_propogated(false),
Arun Menon906de572013-06-18 17:01:40 -0700497 m_state(OMX_StateInvalid),
498 m_app_data(NULL),
499 m_inp_mem_ptr(NULL),
500 m_out_mem_ptr(NULL),
501 m_inp_err_count(0),
502 input_flush_progress (false),
503 output_flush_progress (false),
504 input_use_buffer (false),
505 output_use_buffer (false),
506 ouput_egl_buffers(false),
507 m_use_output_pmem(OMX_FALSE),
508 m_out_mem_region_smi(OMX_FALSE),
509 m_out_pvt_entry_pmem(OMX_FALSE),
510 pending_input_buffers(0),
511 pending_output_buffers(0),
512 m_out_bm_count(0),
513 m_inp_bm_count(0),
514 m_inp_bPopulated(OMX_FALSE),
515 m_out_bPopulated(OMX_FALSE),
516 m_flags(0),
Shalaj Jain273b3e02012-06-22 19:08:03 -0700517#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -0700518 m_heap_ptr(NULL),
Shalaj Jain273b3e02012-06-22 19:08:03 -0700519#endif
Arun Menon906de572013-06-18 17:01:40 -0700520 m_inp_bEnabled(OMX_TRUE),
521 m_out_bEnabled(OMX_TRUE),
522 m_in_alloc_cnt(0),
523 m_platform_list(NULL),
524 m_platform_entry(NULL),
525 m_pmem_info(NULL),
526 arbitrary_bytes (true),
527 psource_frame (NULL),
528 pdest_frame (NULL),
529 m_inp_heap_ptr (NULL),
530 m_phdr_pmem_ptr(NULL),
531 m_heap_inp_bm_count (0),
532 codec_type_parse ((codec_type)0),
533 first_frame_meta (true),
534 frame_count (0),
535 nal_count (0),
536 nal_length(0),
537 look_ahead_nal (false),
538 first_frame(0),
539 first_buffer(NULL),
540 first_frame_size (0),
541 m_device_file_ptr(NULL),
542 m_vc1_profile((vc1_profile_type)0),
Arun Menon906de572013-06-18 17:01:40 -0700543 h264_last_au_ts(LLONG_MAX),
544 h264_last_au_flags(0),
Surajit Podderd2644d52013-08-28 17:59:06 +0530545 m_disp_hor_size(0),
546 m_disp_vert_size(0),
Arun Menon906de572013-06-18 17:01:40 -0700547 prev_ts(LLONG_MAX),
548 rst_prev_ts(true),
549 frm_int(0),
Arun Menon906de572013-06-18 17:01:40 -0700550 in_reconfig(false),
551 m_display_id(NULL),
552 h264_parser(NULL),
553 client_extradata(0),
554 m_reject_avc_1080p_mp (0),
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +0530555 m_other_extradata(NULL),
Shalaj Jain273b3e02012-06-22 19:08:03 -0700556#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -0700557 m_enable_android_native_buffers(OMX_FALSE),
558 m_use_android_native_buffers(OMX_FALSE),
559 iDivXDrmDecrypt(NULL),
Shalaj Jain273b3e02012-06-22 19:08:03 -0700560#endif
Arun Menon906de572013-06-18 17:01:40 -0700561 m_desc_buffer_ptr(NULL),
562 secure_mode(false),
Surajit Podderd2644d52013-08-28 17:59:06 +0530563 m_profile(0),
vivek mehtaa75c69f2014-01-10 21:50:37 -0800564 client_set_fps(false),
565 m_last_rendered_TS(-1)
Shalaj Jain273b3e02012-06-22 19:08:03 -0700566{
Arun Menon906de572013-06-18 17:01:40 -0700567 /* Assumption is that , to begin with , we have all the frames with decoder */
568 DEBUG_PRINT_HIGH("In OMX vdec Constructor");
Jayasena Sangaraboina51230642013-08-21 18:02:13 -0700569 memset(&m_debug,0,sizeof(m_debug));
Shalaj Jain273b3e02012-06-22 19:08:03 -0700570#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -0700571 char property_value[PROPERTY_VALUE_MAX] = {0};
Jayasena Sangaraboinac4dfc282013-08-08 12:41:39 -0700572 property_get("vidc.debug.level", property_value, "0");
573 debug_level = atoi(property_value);
574 property_value[0] = '\0';
575
Jayasena Sangaraboina51230642013-08-21 18:02:13 -0700576 DEBUG_PRINT_HIGH("In OMX vdec Constructor");
577
Arun Menon906de572013-06-18 17:01:40 -0700578 property_get("vidc.dec.debug.perf", property_value, "0");
579 perf_flag = atoi(property_value);
580 if (perf_flag) {
581 DEBUG_PRINT_HIGH("vidc.dec.debug.perf is %d", perf_flag);
582 dec_time.start();
583 proc_frms = latency = 0;
584 }
585 prev_n_filled_len = 0;
586 property_value[0] = '\0';
587 property_get("vidc.dec.debug.ts", property_value, "0");
588 m_debug_timestamp = atoi(property_value);
589 DEBUG_PRINT_HIGH("vidc.dec.debug.ts value is %d",m_debug_timestamp);
590 if (m_debug_timestamp) {
591 time_stamp_dts.set_timestamp_reorder_mode(true);
592 time_stamp_dts.enable_debug_print(true);
593 }
Shalaj Jain273b3e02012-06-22 19:08:03 -0700594
Arun Menon906de572013-06-18 17:01:40 -0700595 property_value[0] = '\0';
596 property_get("vidc.dec.debug.concealedmb", property_value, "0");
597 m_debug_concealedmb = atoi(property_value);
598 DEBUG_PRINT_HIGH("vidc.dec.debug.concealedmb value is %d",m_debug_concealedmb);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700599
Arun Menon906de572013-06-18 17:01:40 -0700600 property_value[0] = '\0';
601 property_get("vidc.dec.profile.check", property_value, "0");
602 m_reject_avc_1080p_mp = atoi(property_value);
603 DEBUG_PRINT_HIGH("vidc.dec.profile.check value is %d",m_reject_avc_1080p_mp);
Rajeshwar Kurapatye0e7d0c2013-07-30 19:46:26 +0530604
Jayasena Sangaraboina51230642013-08-21 18:02:13 -0700605 property_value[0] = '\0';
606 property_get("vidc.dec.log.in", property_value, "0");
607 m_debug.in_buffer_log = atoi(property_value);
608
609 property_value[0] = '\0';
610 property_get("vidc.dec.log.out", property_value, "0");
611 m_debug.out_buffer_log = atoi(property_value);
612 sprintf(m_debug.log_loc, "%s", BUFFER_LOG_LOC);
613
614 property_value[0] = '\0';
615 property_get("vidc.log.loc", property_value, "");
616 if (*property_value)
617 strlcpy(m_debug.log_loc, property_value, PROPERTY_VALUE_MAX);
vivek mehta79cff222014-01-22 12:17:07 -0800618
619 property_value[0] = '\0';
620 property_get("vidc.dec.120fps.enabled", property_value, "0");
621
622 //if this feature is not enabled then reset this value -ve
623 if(atoi(property_value)) {
624 DEBUG_PRINT_LOW("feature 120 FPS decode enabled");
625 m_last_rendered_TS = 0;
626 }
627
Shalaj Jain273b3e02012-06-22 19:08:03 -0700628#endif
Arun Menon906de572013-06-18 17:01:40 -0700629 memset(&m_cmp,0,sizeof(m_cmp));
630 memset(&m_cb,0,sizeof(m_cb));
631 memset (&drv_ctx,0,sizeof(drv_ctx));
632 memset (&h264_scratch,0,sizeof (OMX_BUFFERHEADERTYPE));
633 memset (m_hwdevice_name,0,sizeof(m_hwdevice_name));
634 memset(m_demux_offsets, 0, ( sizeof(OMX_U32) * 8192) );
635 m_demux_entries = 0;
636 msg_thread_id = 0;
637 async_thread_id = 0;
638 msg_thread_created = false;
639 async_thread_created = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700640#ifdef _ANDROID_ICS_
Arun Menon906de572013-06-18 17:01:40 -0700641 memset(&native_buffer, 0 ,(sizeof(struct nativebuffer) * MAX_NUM_INPUT_OUTPUT_BUFFERS));
Shalaj Jain273b3e02012-06-22 19:08:03 -0700642#endif
Arun Menon906de572013-06-18 17:01:40 -0700643 memset(&drv_ctx.extradata_info, 0, sizeof(drv_ctx.extradata_info));
Maheshwar Ajjad2df2182013-10-24 19:20:34 +0530644 memset(&m_frame_pack_arrangement, 0, sizeof(OMX_QCOM_FRAME_PACK_ARRANGEMENT));
Arun Menon906de572013-06-18 17:01:40 -0700645 drv_ctx.timestamp_adjust = false;
646 drv_ctx.video_driver_fd = -1;
647 m_vendor_config.pData = NULL;
648 pthread_mutex_init(&m_lock, NULL);
649 pthread_mutex_init(&c_lock, NULL);
650 sem_init(&m_cmd_lock,0,0);
651 streaming[CAPTURE_PORT] =
652 streaming[OUTPUT_PORT] = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700653#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -0700654 char extradata_value[PROPERTY_VALUE_MAX] = {0};
655 property_get("vidc.dec.debug.extradata", extradata_value, "0");
656 m_debug_extradata = atoi(extradata_value);
657 DEBUG_PRINT_HIGH("vidc.dec.debug.extradata value is %d",m_debug_extradata);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700658#endif
Arun Menon906de572013-06-18 17:01:40 -0700659 m_fill_output_msg = OMX_COMPONENT_GENERATE_FTB;
660 client_buffers.set_vdec_client(this);
Arun Menonbdb80b02013-08-12 17:45:54 -0700661 dynamic_buf_mode = false;
662 out_dynamic_list = NULL;
Praveen Chavane78460c2013-12-06 23:16:04 -0800663 is_down_scalar_enabled = false;
Praveen Chavancf924182013-12-06 23:16:23 -0800664 m_smoothstreaming_mode = false;
665 m_smoothstreaming_width = 0;
666 m_smoothstreaming_height = 0;
Deepak Vermaa2efdb12013-12-26 12:30:05 +0530667 is_q6_platform = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700668}
669
Vinay Kalia85793762012-06-14 19:12:34 -0700670static const int event_type[] = {
Arun Menon906de572013-06-18 17:01:40 -0700671 V4L2_EVENT_MSM_VIDC_FLUSH_DONE,
672 V4L2_EVENT_MSM_VIDC_PORT_SETTINGS_CHANGED_SUFFICIENT,
673 V4L2_EVENT_MSM_VIDC_PORT_SETTINGS_CHANGED_INSUFFICIENT,
Arun Menonbdb80b02013-08-12 17:45:54 -0700674 V4L2_EVENT_MSM_VIDC_RELEASE_BUFFER_REFERENCE,
675 V4L2_EVENT_MSM_VIDC_RELEASE_UNQUEUED_BUFFER,
Arun Menon906de572013-06-18 17:01:40 -0700676 V4L2_EVENT_MSM_VIDC_CLOSE_DONE,
677 V4L2_EVENT_MSM_VIDC_SYS_ERROR
Vinay Kalia85793762012-06-14 19:12:34 -0700678};
679
680static OMX_ERRORTYPE subscribe_to_events(int fd)
681{
Arun Menon906de572013-06-18 17:01:40 -0700682 OMX_ERRORTYPE eRet = OMX_ErrorNone;
683 struct v4l2_event_subscription sub;
684 int array_sz = sizeof(event_type)/sizeof(int);
685 int i,rc;
686 if (fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700687 DEBUG_PRINT_ERROR("Invalid input: %d", fd);
Arun Menon906de572013-06-18 17:01:40 -0700688 return OMX_ErrorBadParameter;
689 }
Vinay Kalia85793762012-06-14 19:12:34 -0700690
Arun Menon906de572013-06-18 17:01:40 -0700691 for (i = 0; i < array_sz; ++i) {
692 memset(&sub, 0, sizeof(sub));
693 sub.type = event_type[i];
694 rc = ioctl(fd, VIDIOC_SUBSCRIBE_EVENT, &sub);
695 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700696 DEBUG_PRINT_ERROR("Failed to subscribe event: 0x%x", sub.type);
Arun Menon906de572013-06-18 17:01:40 -0700697 break;
698 }
699 }
700 if (i < array_sz) {
701 for (--i; i >=0 ; i--) {
702 memset(&sub, 0, sizeof(sub));
703 sub.type = event_type[i];
704 rc = ioctl(fd, VIDIOC_UNSUBSCRIBE_EVENT, &sub);
705 if (rc)
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700706 DEBUG_PRINT_ERROR("Failed to unsubscribe event: 0x%x", sub.type);
Arun Menon906de572013-06-18 17:01:40 -0700707 }
708 eRet = OMX_ErrorNotImplemented;
709 }
710 return eRet;
Vinay Kalia85793762012-06-14 19:12:34 -0700711}
712
713
714static OMX_ERRORTYPE unsubscribe_to_events(int fd)
715{
Arun Menon906de572013-06-18 17:01:40 -0700716 OMX_ERRORTYPE eRet = OMX_ErrorNone;
717 struct v4l2_event_subscription sub;
718 int array_sz = sizeof(event_type)/sizeof(int);
719 int i,rc;
720 if (fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700721 DEBUG_PRINT_ERROR("Invalid input: %d", fd);
Arun Menon906de572013-06-18 17:01:40 -0700722 return OMX_ErrorBadParameter;
723 }
Vinay Kalia85793762012-06-14 19:12:34 -0700724
Arun Menon906de572013-06-18 17:01:40 -0700725 for (i = 0; i < array_sz; ++i) {
726 memset(&sub, 0, sizeof(sub));
727 sub.type = event_type[i];
728 rc = ioctl(fd, VIDIOC_UNSUBSCRIBE_EVENT, &sub);
729 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700730 DEBUG_PRINT_ERROR("Failed to unsubscribe event: 0x%x", sub.type);
Arun Menon906de572013-06-18 17:01:40 -0700731 break;
732 }
733 }
734 return eRet;
Vinay Kalia85793762012-06-14 19:12:34 -0700735}
Shalaj Jain273b3e02012-06-22 19:08:03 -0700736
737/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -0700738 FUNCTION
739 omx_vdec::~omx_vdec
Shalaj Jain273b3e02012-06-22 19:08:03 -0700740
Arun Menon906de572013-06-18 17:01:40 -0700741 DESCRIPTION
742 Destructor
Shalaj Jain273b3e02012-06-22 19:08:03 -0700743
Arun Menon906de572013-06-18 17:01:40 -0700744 PARAMETERS
745 None
Shalaj Jain273b3e02012-06-22 19:08:03 -0700746
Arun Menon906de572013-06-18 17:01:40 -0700747 RETURN VALUE
748 None.
749 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -0700750omx_vdec::~omx_vdec()
751{
Arun Menon906de572013-06-18 17:01:40 -0700752 m_pmem_info = NULL;
753 struct v4l2_decoder_cmd dec;
754 DEBUG_PRINT_HIGH("In OMX vdec Destructor");
755 if (m_pipe_in) close(m_pipe_in);
756 if (m_pipe_out) close(m_pipe_out);
757 m_pipe_in = -1;
758 m_pipe_out = -1;
759 DEBUG_PRINT_HIGH("Waiting on OMX Msg Thread exit");
760 if (msg_thread_created)
761 pthread_join(msg_thread_id,NULL);
762 DEBUG_PRINT_HIGH("Waiting on OMX Async Thread exit");
763 dec.cmd = V4L2_DEC_CMD_STOP;
764 if (drv_ctx.video_driver_fd >=0 ) {
765 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_DECODER_CMD, &dec))
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700766 DEBUG_PRINT_ERROR("STOP Command failed");
Arun Menon906de572013-06-18 17:01:40 -0700767 }
768 if (async_thread_created)
769 pthread_join(async_thread_id,NULL);
770 unsubscribe_to_events(drv_ctx.video_driver_fd);
771 close(drv_ctx.video_driver_fd);
772 pthread_mutex_destroy(&m_lock);
773 pthread_mutex_destroy(&c_lock);
774 sem_destroy(&m_cmd_lock);
775 if (perf_flag) {
776 DEBUG_PRINT_HIGH("--> TOTAL PROCESSING TIME");
777 dec_time.end();
778 }
779 DEBUG_PRINT_HIGH("Exit OMX vdec Destructor");
Shalaj Jain273b3e02012-06-22 19:08:03 -0700780}
781
Arun Menon906de572013-06-18 17:01:40 -0700782int release_buffers(omx_vdec* obj, enum vdec_buffer buffer_type)
783{
784 struct v4l2_requestbuffers bufreq;
785 int rc = 0;
786 if (buffer_type == VDEC_BUFFER_TYPE_OUTPUT) {
787 bufreq.memory = V4L2_MEMORY_USERPTR;
788 bufreq.count = 0;
789 bufreq.type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
790 rc = ioctl(obj->drv_ctx.video_driver_fd,VIDIOC_REQBUFS, &bufreq);
Surajit Podder12aefac2013-08-06 18:43:32 +0530791 } else if(buffer_type == VDEC_BUFFER_TYPE_INPUT) {
792 bufreq.memory = V4L2_MEMORY_USERPTR;
793 bufreq.count = 0;
794 bufreq.type=V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
795 rc = ioctl(obj->drv_ctx.video_driver_fd,VIDIOC_REQBUFS, &bufreq);
Arun Menon906de572013-06-18 17:01:40 -0700796 }
797 return rc;
Vinay Kaliafeef7032012-09-25 19:23:33 -0700798}
799
Shalaj Jain273b3e02012-06-22 19:08:03 -0700800/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -0700801 FUNCTION
802 omx_vdec::OMXCntrlProcessMsgCb
Shalaj Jain273b3e02012-06-22 19:08:03 -0700803
Arun Menon906de572013-06-18 17:01:40 -0700804 DESCRIPTION
805 IL Client callbacks are generated through this routine. The decoder
806 provides the thread context for this routine.
Shalaj Jain273b3e02012-06-22 19:08:03 -0700807
Arun Menon906de572013-06-18 17:01:40 -0700808 PARAMETERS
809 ctxt -- Context information related to the self.
810 id -- Event identifier. This could be any of the following:
811 1. Command completion event
812 2. Buffer done callback event
813 3. Frame done callback event
Shalaj Jain273b3e02012-06-22 19:08:03 -0700814
Arun Menon906de572013-06-18 17:01:40 -0700815 RETURN VALUE
816 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -0700817
Arun Menon906de572013-06-18 17:01:40 -0700818 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -0700819void omx_vdec::process_event_cb(void *ctxt, unsigned char id)
820{
Arun Menon906de572013-06-18 17:01:40 -0700821 signed p1; // Parameter - 1
822 signed p2; // Parameter - 2
823 unsigned ident;
824 unsigned qsize=0; // qsize
825 omx_vdec *pThis = (omx_vdec *) ctxt;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700826
Arun Menon906de572013-06-18 17:01:40 -0700827 if (!pThis) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700828 DEBUG_PRINT_ERROR("ERROR: %s()::Context is incorrect, bailing out",
Arun Menon906de572013-06-18 17:01:40 -0700829 __func__);
830 return;
Shalaj Jain273b3e02012-06-22 19:08:03 -0700831 }
832
Arun Menon906de572013-06-18 17:01:40 -0700833 // Protect the shared queue data structure
834 do {
835 /*Read the message id's from the queue*/
836 pthread_mutex_lock(&pThis->m_lock);
837 qsize = pThis->m_cmd_q.m_size;
838 if (qsize) {
839 pThis->m_cmd_q.pop_entry((unsigned *)&p1, (unsigned *)&p2, &ident);
Shalaj Jain273b3e02012-06-22 19:08:03 -0700840 }
Arun Menon906de572013-06-18 17:01:40 -0700841
842 if (qsize == 0 && pThis->m_state != OMX_StatePause) {
843 qsize = pThis->m_ftb_q.m_size;
844 if (qsize) {
845 pThis->m_ftb_q.pop_entry((unsigned *)&p1, (unsigned *)&p2, &ident);
846 }
Shalaj Jain273b3e02012-06-22 19:08:03 -0700847 }
Arun Menon906de572013-06-18 17:01:40 -0700848
849 if (qsize == 0 && pThis->m_state != OMX_StatePause) {
850 qsize = pThis->m_etb_q.m_size;
851 if (qsize) {
852 pThis->m_etb_q.pop_entry((unsigned *)&p1, (unsigned *)&p2, &ident);
853 }
854 }
855 pthread_mutex_unlock(&pThis->m_lock);
856
857 /*process message if we have one*/
858 if (qsize > 0) {
859 id = ident;
860 switch (id) {
861 case OMX_COMPONENT_GENERATE_EVENT:
862 if (pThis->m_cb.EventHandler) {
863 switch (p1) {
864 case OMX_CommandStateSet:
865 pThis->m_state = (OMX_STATETYPE) p2;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700866 DEBUG_PRINT_HIGH("OMX_CommandStateSet complete, m_state = %d",
Arun Menon906de572013-06-18 17:01:40 -0700867 pThis->m_state);
868 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
869 OMX_EventCmdComplete, p1, p2, NULL);
870 break;
871
872 case OMX_EventError:
873 if (p2 == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700874 DEBUG_PRINT_ERROR("OMX_EventError: p2 is OMX_StateInvalid");
Arun Menon906de572013-06-18 17:01:40 -0700875 pThis->m_state = (OMX_STATETYPE) p2;
876 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
877 OMX_EventError, OMX_ErrorInvalidState, p2, NULL);
878 } else if (p2 == OMX_ErrorHardware) {
879 pThis->omx_report_error();
880 } else {
881 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
882 OMX_EventError, p2, (OMX_U32)NULL, NULL );
883 }
884 break;
885
886 case OMX_CommandPortDisable:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700887 DEBUG_PRINT_HIGH("OMX_CommandPortDisable complete for port [%d]", p2);
Arun Menon906de572013-06-18 17:01:40 -0700888 if (BITMASK_PRESENT(&pThis->m_flags,
889 OMX_COMPONENT_OUTPUT_FLUSH_IN_DISABLE_PENDING)) {
890 BITMASK_SET(&pThis->m_flags, OMX_COMPONENT_DISABLE_OUTPUT_DEFERRED);
891 break;
892 }
893 if (p2 == OMX_CORE_OUTPUT_PORT_INDEX) {
894 OMX_ERRORTYPE eRet = OMX_ErrorNone;
895 pThis->stream_off(OMX_CORE_OUTPUT_PORT_INDEX);
896 if (release_buffers(pThis, VDEC_BUFFER_TYPE_OUTPUT))
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700897 DEBUG_PRINT_HIGH("Failed to release output buffers");
Arun Menon906de572013-06-18 17:01:40 -0700898 OMX_ERRORTYPE eRet1 = pThis->get_buffer_req(&pThis->drv_ctx.op_buf);
899 pThis->in_reconfig = false;
900 if (eRet != OMX_ErrorNone) {
901 DEBUG_PRINT_ERROR("set_buffer_req failed eRet = %d",eRet);
902 pThis->omx_report_error();
903 break;
904 }
905 }
906 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
907 OMX_EventCmdComplete, p1, p2, NULL );
908 break;
909 case OMX_CommandPortEnable:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700910 DEBUG_PRINT_HIGH("OMX_CommandPortEnable complete for port [%d]", p2);
Arun Menon906de572013-06-18 17:01:40 -0700911 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,\
912 OMX_EventCmdComplete, p1, p2, NULL );
913 break;
914
915 default:
916 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
917 OMX_EventCmdComplete, p1, p2, NULL );
918 break;
919
920 }
921 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700922 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
Arun Menon906de572013-06-18 17:01:40 -0700923 }
924 break;
925 case OMX_COMPONENT_GENERATE_ETB_ARBITRARY:
926 if (pThis->empty_this_buffer_proxy_arbitrary((OMX_HANDLETYPE)p1,\
927 (OMX_BUFFERHEADERTYPE *)p2) != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700928 DEBUG_PRINT_ERROR("empty_this_buffer_proxy_arbitrary failure");
Arun Menon906de572013-06-18 17:01:40 -0700929 pThis->omx_report_error ();
930 }
931 break;
932 case OMX_COMPONENT_GENERATE_ETB:
933 if (pThis->empty_this_buffer_proxy((OMX_HANDLETYPE)p1,\
934 (OMX_BUFFERHEADERTYPE *)p2) != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700935 DEBUG_PRINT_ERROR("empty_this_buffer_proxy failure");
Arun Menon906de572013-06-18 17:01:40 -0700936 pThis->omx_report_error ();
937 }
938 break;
939
940 case OMX_COMPONENT_GENERATE_FTB:
941 if ( pThis->fill_this_buffer_proxy((OMX_HANDLETYPE)p1,\
942 (OMX_BUFFERHEADERTYPE *)p2) != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700943 DEBUG_PRINT_ERROR("fill_this_buffer_proxy failure");
Arun Menon906de572013-06-18 17:01:40 -0700944 pThis->omx_report_error ();
945 }
946 break;
947
948 case OMX_COMPONENT_GENERATE_COMMAND:
949 pThis->send_command_proxy(&pThis->m_cmp,(OMX_COMMANDTYPE)p1,\
950 (OMX_U32)p2,(OMX_PTR)NULL);
951 break;
952
953 case OMX_COMPONENT_GENERATE_EBD:
954
955 if (p2 != VDEC_S_SUCCESS && p2 != VDEC_S_INPUT_BITSTREAM_ERR) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700956 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_EBD failure");
Arun Menon906de572013-06-18 17:01:40 -0700957 pThis->omx_report_error ();
958 } else {
959 if (p2 == VDEC_S_INPUT_BITSTREAM_ERR && p1) {
960 pThis->m_inp_err_count++;
961 pThis->time_stamp_dts.remove_time_stamp(
962 ((OMX_BUFFERHEADERTYPE *)p1)->nTimeStamp,
963 (pThis->drv_ctx.interlace != VDEC_InterlaceFrameProgressive)
964 ?true:false);
965 } else {
966 pThis->m_inp_err_count = 0;
967 }
968 if ( pThis->empty_buffer_done(&pThis->m_cmp,
969 (OMX_BUFFERHEADERTYPE *)p1) != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700970 DEBUG_PRINT_ERROR("empty_buffer_done failure");
Arun Menon906de572013-06-18 17:01:40 -0700971 pThis->omx_report_error ();
972 }
973 if (pThis->m_inp_err_count >= MAX_INPUT_ERROR) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700974 DEBUG_PRINT_ERROR("Input bitstream error for consecutive %d frames.", MAX_INPUT_ERROR);
Arun Menon906de572013-06-18 17:01:40 -0700975 pThis->omx_report_error ();
976 }
977 }
978 break;
979 case OMX_COMPONENT_GENERATE_INFO_FIELD_DROPPED: {
980 int64_t *timestamp = (int64_t *)p1;
981 if (p1) {
982 pThis->time_stamp_dts.remove_time_stamp(*timestamp,
983 (pThis->drv_ctx.interlace != VDEC_InterlaceFrameProgressive)
984 ?true:false);
985 free(timestamp);
986 }
987 }
988 break;
989 case OMX_COMPONENT_GENERATE_FBD:
990 if (p2 != VDEC_S_SUCCESS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700991 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_FBD failure");
Arun Menon906de572013-06-18 17:01:40 -0700992 pThis->omx_report_error ();
993 } else if ( pThis->fill_buffer_done(&pThis->m_cmp,
994 (OMX_BUFFERHEADERTYPE *)p1) != OMX_ErrorNone ) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -0700995 DEBUG_PRINT_ERROR("fill_buffer_done failure");
Arun Menon906de572013-06-18 17:01:40 -0700996 pThis->omx_report_error ();
997 }
998 break;
999
1000 case OMX_COMPONENT_GENERATE_EVENT_INPUT_FLUSH:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001001 DEBUG_PRINT_HIGH("Driver flush i/p Port complete");
Arun Menon906de572013-06-18 17:01:40 -07001002 if (!pThis->input_flush_progress) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001003 DEBUG_PRINT_HIGH("WARNING: Unexpected flush from driver");
Arun Menon906de572013-06-18 17:01:40 -07001004 } else {
1005 pThis->execute_input_flush();
1006 if (pThis->m_cb.EventHandler) {
1007 if (p2 != VDEC_S_SUCCESS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001008 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_EVENT_INPUT_FLUSH failure");
Arun Menon906de572013-06-18 17:01:40 -07001009 pThis->omx_report_error ();
1010 } else {
1011 /*Check if we need generate event for Flush done*/
1012 if (BITMASK_PRESENT(&pThis->m_flags,
1013 OMX_COMPONENT_INPUT_FLUSH_PENDING)) {
1014 BITMASK_CLEAR (&pThis->m_flags,OMX_COMPONENT_INPUT_FLUSH_PENDING);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001015 DEBUG_PRINT_LOW("Input Flush completed - Notify Client");
Arun Menon906de572013-06-18 17:01:40 -07001016 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
1017 OMX_EventCmdComplete,OMX_CommandFlush,
1018 OMX_CORE_INPUT_PORT_INDEX,NULL );
1019 }
1020 if (BITMASK_PRESENT(&pThis->m_flags,
1021 OMX_COMPONENT_IDLE_PENDING)) {
1022 if (pThis->stream_off(OMX_CORE_INPUT_PORT_INDEX)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001023 DEBUG_PRINT_ERROR("Failed to call streamoff on OUTPUT Port");
Arun Menon906de572013-06-18 17:01:40 -07001024 pThis->omx_report_error ();
1025 } else {
1026 pThis->streaming[OUTPUT_PORT] = false;
1027 }
1028 if (!pThis->output_flush_progress) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001029 DEBUG_PRINT_LOW("Input flush done hence issue stop");
Arun Menon906de572013-06-18 17:01:40 -07001030 pThis->post_event ((unsigned int)NULL, VDEC_S_SUCCESS,\
1031 OMX_COMPONENT_GENERATE_STOP_DONE);
1032 }
1033 }
1034 }
1035 } else {
1036 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1037 }
1038 }
1039 break;
1040
1041 case OMX_COMPONENT_GENERATE_EVENT_OUTPUT_FLUSH:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001042 DEBUG_PRINT_HIGH("Driver flush o/p Port complete");
Arun Menon906de572013-06-18 17:01:40 -07001043 if (!pThis->output_flush_progress) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001044 DEBUG_PRINT_HIGH("WARNING: Unexpected flush from driver");
Arun Menon906de572013-06-18 17:01:40 -07001045 } else {
1046 pThis->execute_output_flush();
1047 if (pThis->m_cb.EventHandler) {
1048 if (p2 != VDEC_S_SUCCESS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001049 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_EVENT_OUTPUT_FLUSH failed");
Arun Menon906de572013-06-18 17:01:40 -07001050 pThis->omx_report_error ();
1051 } else {
1052 /*Check if we need generate event for Flush done*/
1053 if (BITMASK_PRESENT(&pThis->m_flags,
1054 OMX_COMPONENT_OUTPUT_FLUSH_PENDING)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001055 DEBUG_PRINT_LOW("Notify Output Flush done");
Arun Menon906de572013-06-18 17:01:40 -07001056 BITMASK_CLEAR (&pThis->m_flags,OMX_COMPONENT_OUTPUT_FLUSH_PENDING);
1057 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
1058 OMX_EventCmdComplete,OMX_CommandFlush,
1059 OMX_CORE_OUTPUT_PORT_INDEX,NULL );
1060 }
1061 if (BITMASK_PRESENT(&pThis->m_flags,
1062 OMX_COMPONENT_OUTPUT_FLUSH_IN_DISABLE_PENDING)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001063 DEBUG_PRINT_LOW("Internal flush complete");
Arun Menon906de572013-06-18 17:01:40 -07001064 BITMASK_CLEAR (&pThis->m_flags,
1065 OMX_COMPONENT_OUTPUT_FLUSH_IN_DISABLE_PENDING);
1066 if (BITMASK_PRESENT(&pThis->m_flags,
1067 OMX_COMPONENT_DISABLE_OUTPUT_DEFERRED)) {
1068 pThis->post_event(OMX_CommandPortDisable,
1069 OMX_CORE_OUTPUT_PORT_INDEX,
1070 OMX_COMPONENT_GENERATE_EVENT);
1071 BITMASK_CLEAR (&pThis->m_flags,
1072 OMX_COMPONENT_DISABLE_OUTPUT_DEFERRED);
Praneeth Paladugub52072a2013-08-23 13:54:43 -07001073 BITMASK_CLEAR (&pThis->m_flags,
1074 OMX_COMPONENT_OUTPUT_DISABLE_PENDING);
Arun Menon906de572013-06-18 17:01:40 -07001075
1076 }
1077 }
1078
1079 if (BITMASK_PRESENT(&pThis->m_flags ,OMX_COMPONENT_IDLE_PENDING)) {
1080 if (pThis->stream_off(OMX_CORE_OUTPUT_PORT_INDEX)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001081 DEBUG_PRINT_ERROR("Failed to call streamoff on CAPTURE Port");
Arun Menon906de572013-06-18 17:01:40 -07001082 pThis->omx_report_error ();
1083 break;
1084 }
1085 pThis->streaming[CAPTURE_PORT] = false;
1086 if (!pThis->input_flush_progress) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001087 DEBUG_PRINT_LOW("Output flush done hence issue stop");
Arun Menon906de572013-06-18 17:01:40 -07001088 pThis->post_event ((unsigned int)NULL, VDEC_S_SUCCESS,\
1089 OMX_COMPONENT_GENERATE_STOP_DONE);
1090 }
1091 }
1092 }
1093 } else {
1094 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1095 }
1096 }
1097 break;
1098
1099 case OMX_COMPONENT_GENERATE_START_DONE:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001100 DEBUG_PRINT_HIGH("Rxd OMX_COMPONENT_GENERATE_START_DONE");
Arun Menon906de572013-06-18 17:01:40 -07001101
1102 if (pThis->m_cb.EventHandler) {
1103 if (p2 != VDEC_S_SUCCESS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001104 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_START_DONE Failure");
Arun Menon906de572013-06-18 17:01:40 -07001105 pThis->omx_report_error ();
1106 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001107 DEBUG_PRINT_LOW("OMX_COMPONENT_GENERATE_START_DONE Success");
Arun Menon906de572013-06-18 17:01:40 -07001108 if (BITMASK_PRESENT(&pThis->m_flags,OMX_COMPONENT_EXECUTE_PENDING)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001109 DEBUG_PRINT_LOW("Move to executing");
Arun Menon906de572013-06-18 17:01:40 -07001110 // Send the callback now
1111 BITMASK_CLEAR((&pThis->m_flags),OMX_COMPONENT_EXECUTE_PENDING);
1112 pThis->m_state = OMX_StateExecuting;
1113 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
1114 OMX_EventCmdComplete,OMX_CommandStateSet,
1115 OMX_StateExecuting, NULL);
1116 } else if (BITMASK_PRESENT(&pThis->m_flags,
1117 OMX_COMPONENT_PAUSE_PENDING)) {
1118 if (/*ioctl (pThis->drv_ctx.video_driver_fd,
1119 VDEC_IOCTL_CMD_PAUSE,NULL ) < */0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001120 DEBUG_PRINT_ERROR("VDEC_IOCTL_CMD_PAUSE failed");
Arun Menon906de572013-06-18 17:01:40 -07001121 pThis->omx_report_error ();
1122 }
1123 }
1124 }
1125 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001126 DEBUG_PRINT_LOW("Event Handler callback is NULL");
Arun Menon906de572013-06-18 17:01:40 -07001127 }
1128 break;
1129
1130 case OMX_COMPONENT_GENERATE_PAUSE_DONE:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001131 DEBUG_PRINT_HIGH("Rxd OMX_COMPONENT_GENERATE_PAUSE_DONE");
Arun Menon906de572013-06-18 17:01:40 -07001132 if (pThis->m_cb.EventHandler) {
1133 if (p2 != VDEC_S_SUCCESS) {
1134 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_PAUSE_DONE ret failed");
1135 pThis->omx_report_error ();
1136 } else {
1137 pThis->complete_pending_buffer_done_cbs();
1138 if (BITMASK_PRESENT(&pThis->m_flags,OMX_COMPONENT_PAUSE_PENDING)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001139 DEBUG_PRINT_LOW("OMX_COMPONENT_GENERATE_PAUSE_DONE nofity");
Arun Menon906de572013-06-18 17:01:40 -07001140 //Send the callback now
1141 BITMASK_CLEAR((&pThis->m_flags),OMX_COMPONENT_PAUSE_PENDING);
1142 pThis->m_state = OMX_StatePause;
1143 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
1144 OMX_EventCmdComplete,OMX_CommandStateSet,
1145 OMX_StatePause, NULL);
1146 }
1147 }
1148 } else {
1149 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1150 }
1151
1152 break;
1153
1154 case OMX_COMPONENT_GENERATE_RESUME_DONE:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001155 DEBUG_PRINT_HIGH("Rxd OMX_COMPONENT_GENERATE_RESUME_DONE");
Arun Menon906de572013-06-18 17:01:40 -07001156 if (pThis->m_cb.EventHandler) {
1157 if (p2 != VDEC_S_SUCCESS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001158 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_RESUME_DONE failed");
Arun Menon906de572013-06-18 17:01:40 -07001159 pThis->omx_report_error ();
1160 } else {
1161 if (BITMASK_PRESENT(&pThis->m_flags,OMX_COMPONENT_EXECUTE_PENDING)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001162 DEBUG_PRINT_LOW("Moving the decoder to execute state");
Arun Menon906de572013-06-18 17:01:40 -07001163 // Send the callback now
1164 BITMASK_CLEAR((&pThis->m_flags),OMX_COMPONENT_EXECUTE_PENDING);
1165 pThis->m_state = OMX_StateExecuting;
1166 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
1167 OMX_EventCmdComplete,OMX_CommandStateSet,
1168 OMX_StateExecuting,NULL);
1169 }
1170 }
1171 } else {
1172 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1173 }
1174
1175 break;
1176
1177 case OMX_COMPONENT_GENERATE_STOP_DONE:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001178 DEBUG_PRINT_HIGH("Rxd OMX_COMPONENT_GENERATE_STOP_DONE");
Arun Menon906de572013-06-18 17:01:40 -07001179 if (pThis->m_cb.EventHandler) {
1180 if (p2 != VDEC_S_SUCCESS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001181 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_STOP_DONE ret failed");
Arun Menon906de572013-06-18 17:01:40 -07001182 pThis->omx_report_error ();
1183 } else {
1184 pThis->complete_pending_buffer_done_cbs();
1185 if (BITMASK_PRESENT(&pThis->m_flags,OMX_COMPONENT_IDLE_PENDING)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001186 DEBUG_PRINT_LOW("OMX_COMPONENT_GENERATE_STOP_DONE Success");
Arun Menon906de572013-06-18 17:01:40 -07001187 // Send the callback now
1188 BITMASK_CLEAR((&pThis->m_flags),OMX_COMPONENT_IDLE_PENDING);
1189 pThis->m_state = OMX_StateIdle;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001190 DEBUG_PRINT_LOW("Move to Idle State");
Arun Menon906de572013-06-18 17:01:40 -07001191 pThis->m_cb.EventHandler(&pThis->m_cmp,pThis->m_app_data,
1192 OMX_EventCmdComplete,OMX_CommandStateSet,
1193 OMX_StateIdle,NULL);
1194 }
1195 }
1196 } else {
1197 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1198 }
1199
1200 break;
1201
1202 case OMX_COMPONENT_GENERATE_PORT_RECONFIG:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001203 DEBUG_PRINT_HIGH("Rxd OMX_COMPONENT_GENERATE_PORT_RECONFIG");
Arun Menon906de572013-06-18 17:01:40 -07001204
1205 if (p2 == OMX_IndexParamPortDefinition) {
1206 pThis->in_reconfig = true;
1207 }
1208 if (pThis->m_cb.EventHandler) {
1209 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data,
1210 OMX_EventPortSettingsChanged, p1, p2, NULL );
1211 } else {
1212 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1213 }
1214
Arun Menon906de572013-06-18 17:01:40 -07001215 break;
1216
1217 case OMX_COMPONENT_GENERATE_EOS_DONE:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001218 DEBUG_PRINT_HIGH("Rxd OMX_COMPONENT_GENERATE_EOS_DONE");
Arun Menon906de572013-06-18 17:01:40 -07001219 if (pThis->m_cb.EventHandler) {
1220 pThis->m_cb.EventHandler(&pThis->m_cmp, pThis->m_app_data, OMX_EventBufferFlag,
1221 OMX_CORE_OUTPUT_PORT_INDEX, OMX_BUFFERFLAG_EOS, NULL );
1222 } else {
1223 DEBUG_PRINT_ERROR("ERROR: %s()::EventHandler is NULL", __func__);
1224 }
1225 pThis->prev_ts = LLONG_MAX;
1226 pThis->rst_prev_ts = true;
1227 break;
1228
1229 case OMX_COMPONENT_GENERATE_HARDWARE_ERROR:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001230 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_HARDWARE_ERROR");
Arun Menon906de572013-06-18 17:01:40 -07001231 pThis->omx_report_error ();
1232 break;
1233
1234 case OMX_COMPONENT_GENERATE_UNSUPPORTED_SETTING:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001235 DEBUG_PRINT_ERROR("OMX_COMPONENT_GENERATE_UNSUPPORTED_SETTING");
Arun Menon906de572013-06-18 17:01:40 -07001236 pThis->omx_report_unsupported_setting();
1237 break;
1238
Arun Menon906de572013-06-18 17:01:40 -07001239 default:
1240 break;
1241 }
1242 }
1243 pthread_mutex_lock(&pThis->m_lock);
1244 qsize = pThis->m_cmd_q.m_size;
1245 if (pThis->m_state != OMX_StatePause)
1246 qsize += (pThis->m_ftb_q.m_size + pThis->m_etb_q.m_size);
1247 pthread_mutex_unlock(&pThis->m_lock);
1248 } while (qsize>0);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001249
1250}
1251
Vinay Kaliab9e98102013-04-02 19:31:43 -07001252int omx_vdec::update_resolution(int width, int height, int stride, int scan_lines)
Vinay Kalia592e4b42012-12-19 15:55:47 -08001253{
Arun Menon906de572013-06-18 17:01:40 -07001254 int format_changed = 0;
Surajit Podderd2644d52013-08-28 17:59:06 +05301255 if ((height != (int)drv_ctx.video_resolution.frame_height) ||
1256 (width != (int)drv_ctx.video_resolution.frame_width)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001257 DEBUG_PRINT_HIGH("NOTE_CIF: W/H %d (%d), %d (%d)",
Arun Menon906de572013-06-18 17:01:40 -07001258 width, drv_ctx.video_resolution.frame_width,
1259 height,drv_ctx.video_resolution.frame_height);
1260 format_changed = 1;
1261 }
Vinay Kalia592e4b42012-12-19 15:55:47 -08001262 drv_ctx.video_resolution.frame_height = height;
1263 drv_ctx.video_resolution.frame_width = width;
Vinay Kalia21649b32013-03-18 17:28:07 -07001264 drv_ctx.video_resolution.scan_lines = scan_lines;
1265 drv_ctx.video_resolution.stride = stride;
Vinay Kalia592e4b42012-12-19 15:55:47 -08001266 rectangle.nLeft = 0;
1267 rectangle.nTop = 0;
1268 rectangle.nWidth = drv_ctx.video_resolution.frame_width;
1269 rectangle.nHeight = drv_ctx.video_resolution.frame_height;
Arun Menon906de572013-06-18 17:01:40 -07001270 return format_changed;
Vinay Kalia592e4b42012-12-19 15:55:47 -08001271}
1272
Arun Menon6836ba02013-02-19 20:37:40 -08001273OMX_ERRORTYPE omx_vdec::is_video_session_supported()
1274{
Arun Menon906de572013-06-18 17:01:40 -07001275 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc",
1276 OMX_MAX_STRINGNAME_SIZE) &&
1277 (m_profile == HIGH_PROFILE || m_profile == MAIN_PROFILE)) {
1278 m_decoder_capability.max_width = 1280;
1279 m_decoder_capability.max_height = 720;
1280 DEBUG_PRINT_HIGH("Set max_width=1280 & max_height=720 for H264 HP/MP");
1281 }
Arun Menon888aa852013-05-30 11:24:42 -07001282
Arun Menon906de572013-06-18 17:01:40 -07001283 if ((drv_ctx.video_resolution.frame_width *
1284 drv_ctx.video_resolution.frame_height >
1285 m_decoder_capability.max_width *
1286 m_decoder_capability.max_height) ||
1287 (drv_ctx.video_resolution.frame_width*
1288 drv_ctx.video_resolution.frame_height <
1289 m_decoder_capability.min_width *
1290 m_decoder_capability.min_height)) {
1291 DEBUG_PRINT_ERROR(
1292 "Unsupported WxH = (%u)x(%u) supported range is min(%u)x(%u) - max(%u)x(%u)",
1293 drv_ctx.video_resolution.frame_width,
1294 drv_ctx.video_resolution.frame_height,
1295 m_decoder_capability.min_width,
1296 m_decoder_capability.min_height,
1297 m_decoder_capability.max_width,
1298 m_decoder_capability.max_height);
1299 return OMX_ErrorUnsupportedSetting;
1300 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001301 DEBUG_PRINT_HIGH("video session supported");
Arun Menon906de572013-06-18 17:01:40 -07001302 return OMX_ErrorNone;
Arun Menon6836ba02013-02-19 20:37:40 -08001303}
1304
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07001305int omx_vdec::log_input_buffers(const char *buffer_addr, int buffer_len)
1306{
1307 if (m_debug.in_buffer_log && !m_debug.infile) {
1308 if(!strncmp(drv_ctx.kind,"OMX.qcom.video.decoder.mpeg4", OMX_MAX_STRINGNAME_SIZE)) {
1309 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.m4v",
1310 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1311 }
1312 else if(!strncmp(drv_ctx.kind,"OMX.qcom.video.decoder.mpeg2", OMX_MAX_STRINGNAME_SIZE)) {
1313 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.mpg", m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this); }
1314 else if(!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.h263", OMX_MAX_STRINGNAME_SIZE)) {
1315 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.263",
1316 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1317 }
1318 else if(!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc", OMX_MAX_STRINGNAME_SIZE)) {
1319 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.264",
1320 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1321 }
1322 else if(!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vc1", OMX_MAX_STRINGNAME_SIZE)) {
1323 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.vc1",
1324 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1325 }
1326 else if(!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.wmv", OMX_MAX_STRINGNAME_SIZE)) {
1327 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.vc1",
1328 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1329 }
1330 else if(!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8", OMX_MAX_STRINGNAME_SIZE)) {
1331 sprintf(m_debug.infile_name, "%s/input_dec_%d_%d_%p.ivf",
1332 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1333 }
1334 m_debug.infile = fopen (m_debug.infile_name, "ab");
1335 if (!m_debug.infile) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001336 DEBUG_PRINT_HIGH("Failed to open input file: %s for logging", m_debug.infile_name);
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07001337 m_debug.infile_name[0] = '\0';
1338 return -1;
1339 }
1340 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8", OMX_MAX_STRINGNAME_SIZE)) {
1341 struct ivf_file_header {
1342 OMX_U8 signature[4]; //='DKIF';
1343 OMX_U8 version ; //= 0;
1344 OMX_U8 headersize ; //= 32;
1345 OMX_U32 FourCC;
1346 OMX_U8 width;
1347 OMX_U8 height;
1348 OMX_U32 rate;
1349 OMX_U32 scale;
1350 OMX_U32 length;
1351 OMX_U8 unused[4];
1352 } file_header;
1353
1354 memset((void *)&file_header,0,sizeof(file_header));
1355 file_header.signature[0] = 'D';
1356 file_header.signature[1] = 'K';
1357 file_header.signature[2] = 'I';
1358 file_header.signature[3] = 'F';
1359 file_header.version = 0;
1360 file_header.headersize = 32;
1361 file_header.FourCC = 0x30385056;
1362 fwrite((const char *)&file_header,
1363 sizeof(file_header),1,m_debug.infile);
1364 }
1365 }
1366 if (m_debug.infile && buffer_addr && buffer_len) {
1367 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8", OMX_MAX_STRINGNAME_SIZE)) {
1368 struct vp8_ivf_frame_header {
1369 OMX_U32 framesize;
1370 OMX_U32 timestamp_lo;
1371 OMX_U32 timestamp_hi;
1372 } vp8_frame_header;
1373 vp8_frame_header.framesize = buffer_len;
1374 /* Currently FW doesn't use timestamp values */
1375 vp8_frame_header.timestamp_lo = 0;
1376 vp8_frame_header.timestamp_hi = 0;
1377 fwrite((const char *)&vp8_frame_header,
1378 sizeof(vp8_frame_header),1,m_debug.infile);
1379 }
1380 fwrite(buffer_addr, buffer_len, 1, m_debug.infile);
1381 }
1382 return 0;
1383}
1384
1385int omx_vdec::log_output_buffers(OMX_BUFFERHEADERTYPE *buffer) {
1386 if (m_debug.out_buffer_log && !m_debug.outfile) {
1387 sprintf(m_debug.outfile_name, "%s/output_%d_%d_%p.yuv",
1388 m_debug.log_loc, drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height, this);
1389 m_debug.outfile = fopen (m_debug.outfile_name, "ab");
1390 if (!m_debug.outfile) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001391 DEBUG_PRINT_HIGH("Failed to open output file: %s for logging", m_debug.log_loc);
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07001392 m_debug.outfile_name[0] = '\0';
1393 return -1;
1394 }
1395 }
1396 if (m_debug.outfile && buffer && buffer->nFilledLen) {
1397 int buf_index = buffer - m_out_mem_ptr;
1398 int stride = drv_ctx.video_resolution.stride;
1399 int scanlines = drv_ctx.video_resolution.scan_lines;
Deepak Vermaa2efdb12013-12-26 12:30:05 +05301400 if (m_smoothstreaming_mode) {
1401 stride = drv_ctx.video_resolution.frame_width;
1402 scanlines = drv_ctx.video_resolution.frame_height;
1403 stride = (stride + DEFAULT_WIDTH_ALIGNMENT - 1) & (~(DEFAULT_WIDTH_ALIGNMENT - 1));
1404 scanlines = (scanlines + DEFAULT_HEIGHT_ALIGNMENT - 1) & (~(DEFAULT_HEIGHT_ALIGNMENT - 1));
1405 }
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07001406 char *temp = (char *)drv_ctx.ptr_outputbuffer[buf_index].bufferaddr;
1407 unsigned i;
Deepak Vermaa2efdb12013-12-26 12:30:05 +05301408 DEBUG_PRINT_HIGH("Logging width/height(%u/%u) stride/scanlines(%u/%u)",
1409 drv_ctx.video_resolution.frame_width,
1410 drv_ctx.video_resolution.frame_height, stride, scanlines);
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07001411 int bytes_written = 0;
1412 for (i = 0; i < drv_ctx.video_resolution.frame_height; i++) {
1413 bytes_written = fwrite(temp, drv_ctx.video_resolution.frame_width, 1, m_debug.outfile);
1414 temp += stride;
1415 }
1416 temp = (char *)drv_ctx.ptr_outputbuffer[buf_index].bufferaddr + stride * scanlines;
1417 int stride_c = stride;
1418 for(i = 0; i < drv_ctx.video_resolution.frame_height/2; i++) {
1419 bytes_written += fwrite(temp, drv_ctx.video_resolution.frame_width, 1, m_debug.outfile);
1420 temp += stride_c;
1421 }
1422 }
1423 return 0;
1424}
1425
Shalaj Jain273b3e02012-06-22 19:08:03 -07001426/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07001427 FUNCTION
1428 omx_vdec::ComponentInit
Shalaj Jain273b3e02012-06-22 19:08:03 -07001429
Arun Menon906de572013-06-18 17:01:40 -07001430 DESCRIPTION
1431 Initialize the component.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001432
Arun Menon906de572013-06-18 17:01:40 -07001433 PARAMETERS
1434 ctxt -- Context information related to the self.
1435 id -- Event identifier. This could be any of the following:
1436 1. Command completion event
1437 2. Buffer done callback event
1438 3. Frame done callback event
Shalaj Jain273b3e02012-06-22 19:08:03 -07001439
Arun Menon906de572013-06-18 17:01:40 -07001440 RETURN VALUE
1441 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001442
Arun Menon906de572013-06-18 17:01:40 -07001443 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07001444OMX_ERRORTYPE omx_vdec::component_init(OMX_STRING role)
1445{
1446
Arun Menon906de572013-06-18 17:01:40 -07001447 OMX_ERRORTYPE eRet = OMX_ErrorNone;
1448 struct v4l2_fmtdesc fdesc;
1449 struct v4l2_format fmt;
1450 struct v4l2_requestbuffers bufreq;
1451 struct v4l2_control control;
1452 struct v4l2_frmsizeenum frmsize;
1453 unsigned int alignment = 0,buffer_size = 0;
1454 int fds[2];
1455 int r,ret=0;
1456 bool codec_ambiguous = false;
1457 OMX_STRING device_name = (OMX_STRING)"/dev/video/venus_dec";
Jia Meng3a3c6492013-12-19 17:16:52 +08001458 char property_value[PROPERTY_VALUE_MAX] = {0};
Sachin Shahc82a18f2013-03-29 14:45:38 -07001459
1460#ifdef _ANDROID_
Praveen Chavane9e56202013-09-19 03:48:16 -07001461 char platform_name[PROPERTY_VALUE_MAX];
Arun Menon906de572013-06-18 17:01:40 -07001462 property_get("ro.board.platform", platform_name, "0");
1463 if (!strncmp(platform_name, "msm8610", 7)) {
1464 device_name = (OMX_STRING)"/dev/video/q6_dec";
Deepak Vermaa2efdb12013-12-26 12:30:05 +05301465 is_q6_platform = true;
1466 maxSmoothStreamingWidth = 1280;
1467 maxSmoothStreamingHeight = 720;
Arun Menon906de572013-06-18 17:01:40 -07001468 }
Sachin Shahc82a18f2013-03-29 14:45:38 -07001469#endif
1470
Arun Menon906de572013-06-18 17:01:40 -07001471 if (!strncmp(role, "OMX.qcom.video.decoder.avc.secure",OMX_MAX_STRINGNAME_SIZE)) {
1472 struct v4l2_control control;
1473 secure_mode = true;
1474 arbitrary_bytes = false;
1475 role = (OMX_STRING)"OMX.qcom.video.decoder.avc";
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05301476 } else if (!strncmp(role, "OMX.qcom.video.decoder.mpeg2.secure",
1477 OMX_MAX_STRINGNAME_SIZE)){
1478 secure_mode = true;
1479 arbitrary_bytes = false;
1480 role = (OMX_STRING)"OMX.qcom.video.decoder.mpeg2";
Arun Menon906de572013-06-18 17:01:40 -07001481 }
Vinay Kalia53fa6832012-10-11 17:55:30 -07001482
Arun Menon906de572013-06-18 17:01:40 -07001483 drv_ctx.video_driver_fd = open(device_name, O_RDWR);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001484
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001485 DEBUG_PRINT_HIGH("omx_vdec::component_init(): Open returned fd %d",
Jayasena Sangaraboinac453bd82013-08-01 14:02:52 -07001486 drv_ctx.video_driver_fd);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001487
Arun Menon906de572013-06-18 17:01:40 -07001488 if (drv_ctx.video_driver_fd == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001489 DEBUG_PRINT_ERROR("omx_vdec_msm8974 :: Got fd as 0 for msm_vidc_dec, Opening again");
Arun Menon906de572013-06-18 17:01:40 -07001490 drv_ctx.video_driver_fd = open(device_name, O_RDWR);
1491 close(0);
1492 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001493
Arun Menon906de572013-06-18 17:01:40 -07001494 if (drv_ctx.video_driver_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001495 DEBUG_PRINT_ERROR("Omx_vdec::Comp Init Returning failure, errno %d", errno);
Arun Menon906de572013-06-18 17:01:40 -07001496 return OMX_ErrorInsufficientResources;
1497 }
1498 drv_ctx.frame_rate.fps_numerator = DEFAULT_FPS;
1499 drv_ctx.frame_rate.fps_denominator = 1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001500
Vinay Kaliadae8ad62013-04-26 20:42:10 -07001501 ret = subscribe_to_events(drv_ctx.video_driver_fd);
Vinay Kalia184cd0f2013-04-29 18:26:42 -07001502 if (!ret) {
Arun Menon906de572013-06-18 17:01:40 -07001503 async_thread_created = true;
1504 ret = pthread_create(&async_thread_id,0,async_message_thread,this);
1505 }
1506 if (ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001507 DEBUG_PRINT_ERROR("Failed to create async_message_thread");
Arun Menon906de572013-06-18 17:01:40 -07001508 async_thread_created = false;
1509 return OMX_ErrorInsufficientResources;
Vinay Kaliadae8ad62013-04-26 20:42:10 -07001510 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001511
Shalaj Jain273b3e02012-06-22 19:08:03 -07001512#ifdef OUTPUT_EXTRADATA_LOG
Deva Ramasubramanianee6f1f42014-01-31 12:49:18 -08001513 outputExtradataFile = fopen (output_extradata_filename, "ab");
Shalaj Jain273b3e02012-06-22 19:08:03 -07001514#endif
1515
Arun Menon906de572013-06-18 17:01:40 -07001516 // Copy the role information which provides the decoder kind
1517 strlcpy(drv_ctx.kind,role,128);
Vinay Kalia53fa6832012-10-11 17:55:30 -07001518
Arun Menon906de572013-06-18 17:01:40 -07001519 if (!strncmp(drv_ctx.kind,"OMX.qcom.video.decoder.mpeg4",\
1520 OMX_MAX_STRINGNAME_SIZE)) {
1521 strlcpy((char *)m_cRole, "video_decoder.mpeg4",\
1522 OMX_MAX_STRINGNAME_SIZE);
1523 drv_ctx.timestamp_adjust = true;
1524 drv_ctx.decoder_format = VDEC_CODECTYPE_MPEG4;
1525 eCompressionFormat = OMX_VIDEO_CodingMPEG4;
1526 output_capability=V4L2_PIX_FMT_MPEG4;
1527 /*Initialize Start Code for MPEG4*/
1528 codec_type_parse = CODEC_TYPE_MPEG4;
1529 m_frame_parser.init_start_codes (codec_type_parse);
Arun Menon906de572013-06-18 17:01:40 -07001530 } else if (!strncmp(drv_ctx.kind,"OMX.qcom.video.decoder.mpeg2",\
1531 OMX_MAX_STRINGNAME_SIZE)) {
1532 strlcpy((char *)m_cRole, "video_decoder.mpeg2",\
1533 OMX_MAX_STRINGNAME_SIZE);
1534 drv_ctx.decoder_format = VDEC_CODECTYPE_MPEG2;
1535 output_capability = V4L2_PIX_FMT_MPEG2;
1536 eCompressionFormat = OMX_VIDEO_CodingMPEG2;
1537 /*Initialize Start Code for MPEG2*/
1538 codec_type_parse = CODEC_TYPE_MPEG2;
1539 m_frame_parser.init_start_codes (codec_type_parse);
Arun Menon906de572013-06-18 17:01:40 -07001540 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.h263",\
1541 OMX_MAX_STRINGNAME_SIZE)) {
1542 strlcpy((char *)m_cRole, "video_decoder.h263",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001543 DEBUG_PRINT_LOW("H263 Decoder selected");
Arun Menon906de572013-06-18 17:01:40 -07001544 drv_ctx.decoder_format = VDEC_CODECTYPE_H263;
1545 eCompressionFormat = OMX_VIDEO_CodingH263;
1546 output_capability = V4L2_PIX_FMT_H263;
1547 codec_type_parse = CODEC_TYPE_H263;
1548 m_frame_parser.init_start_codes (codec_type_parse);
Arun Menon906de572013-06-18 17:01:40 -07001549 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx311",\
1550 OMX_MAX_STRINGNAME_SIZE)) {
1551 strlcpy((char *)m_cRole, "video_decoder.divx",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001552 DEBUG_PRINT_LOW ("DIVX 311 Decoder selected");
Arun Menon906de572013-06-18 17:01:40 -07001553 drv_ctx.decoder_format = VDEC_CODECTYPE_DIVX_3;
1554 output_capability = V4L2_PIX_FMT_DIVX_311;
1555 eCompressionFormat = (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingDivx;
1556 codec_type_parse = CODEC_TYPE_DIVX;
1557 m_frame_parser.init_start_codes (codec_type_parse);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001558
Arun Menon906de572013-06-18 17:01:40 -07001559 eRet = createDivxDrmContext();
1560 if (eRet != OMX_ErrorNone) {
1561 DEBUG_PRINT_ERROR("createDivxDrmContext Failed");
1562 return eRet;
1563 }
1564 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx4",\
1565 OMX_MAX_STRINGNAME_SIZE)) {
1566 strlcpy((char *)m_cRole, "video_decoder.divx",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001567 DEBUG_PRINT_ERROR ("DIVX 4 Decoder selected");
Arun Menon906de572013-06-18 17:01:40 -07001568 drv_ctx.decoder_format = VDEC_CODECTYPE_DIVX_4;
1569 output_capability = V4L2_PIX_FMT_DIVX;
1570 eCompressionFormat = (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingDivx;
1571 codec_type_parse = CODEC_TYPE_DIVX;
1572 codec_ambiguous = true;
1573 m_frame_parser.init_start_codes (codec_type_parse);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001574
Arun Menon906de572013-06-18 17:01:40 -07001575 eRet = createDivxDrmContext();
1576 if (eRet != OMX_ErrorNone) {
1577 DEBUG_PRINT_ERROR("createDivxDrmContext Failed");
1578 return eRet;
1579 }
1580 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx",\
1581 OMX_MAX_STRINGNAME_SIZE)) {
1582 strlcpy((char *)m_cRole, "video_decoder.divx",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001583 DEBUG_PRINT_ERROR ("DIVX 5/6 Decoder selected");
Arun Menon906de572013-06-18 17:01:40 -07001584 drv_ctx.decoder_format = VDEC_CODECTYPE_DIVX_6;
1585 output_capability = V4L2_PIX_FMT_DIVX;
1586 eCompressionFormat = (OMX_VIDEO_CODINGTYPE)QOMX_VIDEO_CodingDivx;
1587 codec_type_parse = CODEC_TYPE_DIVX;
1588 codec_ambiguous = true;
1589 m_frame_parser.init_start_codes (codec_type_parse);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001590
Arun Menon906de572013-06-18 17:01:40 -07001591 eRet = createDivxDrmContext();
1592 if (eRet != OMX_ErrorNone) {
1593 DEBUG_PRINT_ERROR("createDivxDrmContext Failed");
1594 return eRet;
1595 }
Deva Ramasubramanian9403f022012-11-28 18:27:53 -08001596
Arun Menon906de572013-06-18 17:01:40 -07001597 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc",\
1598 OMX_MAX_STRINGNAME_SIZE)) {
1599 strlcpy((char *)m_cRole, "video_decoder.avc",OMX_MAX_STRINGNAME_SIZE);
1600 drv_ctx.decoder_format = VDEC_CODECTYPE_H264;
1601 output_capability=V4L2_PIX_FMT_H264;
1602 eCompressionFormat = OMX_VIDEO_CodingAVC;
1603 codec_type_parse = CODEC_TYPE_H264;
1604 m_frame_parser.init_start_codes (codec_type_parse);
1605 m_frame_parser.init_nal_length(nal_length);
Arun Menon906de572013-06-18 17:01:40 -07001606 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vc1",\
1607 OMX_MAX_STRINGNAME_SIZE)) {
1608 strlcpy((char *)m_cRole, "video_decoder.vc1",OMX_MAX_STRINGNAME_SIZE);
1609 drv_ctx.decoder_format = VDEC_CODECTYPE_VC1;
1610 eCompressionFormat = OMX_VIDEO_CodingWMV;
1611 codec_type_parse = CODEC_TYPE_VC1;
1612 output_capability = V4L2_PIX_FMT_VC1_ANNEX_G;
1613 m_frame_parser.init_start_codes (codec_type_parse);
Arun Menon906de572013-06-18 17:01:40 -07001614 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.wmv",\
1615 OMX_MAX_STRINGNAME_SIZE)) {
1616 strlcpy((char *)m_cRole, "video_decoder.vc1",OMX_MAX_STRINGNAME_SIZE);
1617 drv_ctx.decoder_format = VDEC_CODECTYPE_VC1_RCV;
1618 eCompressionFormat = OMX_VIDEO_CodingWMV;
1619 codec_type_parse = CODEC_TYPE_VC1;
1620 output_capability = V4L2_PIX_FMT_VC1_ANNEX_L;
1621 m_frame_parser.init_start_codes (codec_type_parse);
Arun Menon906de572013-06-18 17:01:40 -07001622 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8", \
1623 OMX_MAX_STRINGNAME_SIZE)) {
1624 strlcpy((char *)m_cRole, "video_decoder.vp8",OMX_MAX_STRINGNAME_SIZE);
1625 output_capability=V4L2_PIX_FMT_VP8;
1626 eCompressionFormat = OMX_VIDEO_CodingVPX;
1627 codec_type_parse = CODEC_TYPE_VP8;
1628 arbitrary_bytes = false;
Praneeth Paladugu2b2ef2d2013-04-10 22:04:51 -07001629
Arun Menon906de572013-06-18 17:01:40 -07001630 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001631 DEBUG_PRINT_ERROR("ERROR:Unknown Component");
Arun Menon906de572013-06-18 17:01:40 -07001632 eRet = OMX_ErrorInvalidComponentName;
1633 }
Arun Menon906de572013-06-18 17:01:40 -07001634 if (eRet == OMX_ErrorNone) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07001635
Arun Menon906de572013-06-18 17:01:40 -07001636 drv_ctx.output_format = VDEC_YUV_FORMAT_NV12;
Vinay Kaliada4f4422013-01-09 10:45:03 -08001637 OMX_COLOR_FORMATTYPE dest_color_format = (OMX_COLOR_FORMATTYPE)
1638 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
1639 if (!client_buffers.set_color_format(dest_color_format)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001640 DEBUG_PRINT_ERROR("Setting color format failed");
Vinay Kaliada4f4422013-01-09 10:45:03 -08001641 eRet = OMX_ErrorInsufficientResources;
1642 }
1643
Arun Menon906de572013-06-18 17:01:40 -07001644 capture_capability= V4L2_PIX_FMT_NV12;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001645
Arun Menon906de572013-06-18 17:01:40 -07001646 struct v4l2_capability cap;
1647 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_QUERYCAP, &cap);
1648 if (ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001649 DEBUG_PRINT_ERROR("Failed to query capabilities");
Arun Menon906de572013-06-18 17:01:40 -07001650 /*TODO: How to handle this case */
1651 } else {
1652 DEBUG_PRINT_HIGH("Capabilities: driver_name = %s, card = %s, bus_info = %s,"
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001653 " version = %d, capabilities = %x", cap.driver, cap.card,
Arun Menon906de572013-06-18 17:01:40 -07001654 cap.bus_info, cap.version, cap.capabilities);
1655 }
1656 ret=0;
1657 fdesc.type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
1658 fdesc.index=0;
1659 while (ioctl(drv_ctx.video_driver_fd, VIDIOC_ENUM_FMT, &fdesc) == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001660 DEBUG_PRINT_HIGH("fmt: description: %s, fmt: %x, flags = %x", fdesc.description,
Arun Menon906de572013-06-18 17:01:40 -07001661 fdesc.pixelformat, fdesc.flags);
1662 fdesc.index++;
1663 }
1664 fdesc.type=V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
1665 fdesc.index=0;
1666 while (ioctl(drv_ctx.video_driver_fd, VIDIOC_ENUM_FMT, &fdesc) == 0) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07001667
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001668 DEBUG_PRINT_HIGH("fmt: description: %s, fmt: %x, flags = %x", fdesc.description,
Arun Menon906de572013-06-18 17:01:40 -07001669 fdesc.pixelformat, fdesc.flags);
1670 fdesc.index++;
1671 }
Deva Ramasubramanian3c55b212013-06-18 15:03:49 -07001672 update_resolution(320, 240, 320, 240);
Arun Menon906de572013-06-18 17:01:40 -07001673 fmt.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
1674 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
1675 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
1676 fmt.fmt.pix_mp.pixelformat = output_capability;
1677 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
1678 if (ret) {
1679 /*TODO: How to handle this case */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001680 DEBUG_PRINT_ERROR("Failed to set format on output port");
Arun Menon906de572013-06-18 17:01:40 -07001681 return OMX_ErrorInsufficientResources;
1682 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001683 DEBUG_PRINT_HIGH("Set Format was successful");
Arun Menon906de572013-06-18 17:01:40 -07001684 if (codec_ambiguous) {
1685 if (output_capability == V4L2_PIX_FMT_DIVX) {
1686 struct v4l2_control divx_ctrl;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001687
Arun Menon906de572013-06-18 17:01:40 -07001688 if (drv_ctx.decoder_format == VDEC_CODECTYPE_DIVX_4) {
1689 divx_ctrl.value = V4L2_MPEG_VIDC_VIDEO_DIVX_FORMAT_4;
1690 } else if (drv_ctx.decoder_format == VDEC_CODECTYPE_DIVX_5) {
1691 divx_ctrl.value = V4L2_MPEG_VIDC_VIDEO_DIVX_FORMAT_5;
1692 } else {
1693 divx_ctrl.value = V4L2_MPEG_VIDC_VIDEO_DIVX_FORMAT_6;
1694 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001695
Arun Menon906de572013-06-18 17:01:40 -07001696 divx_ctrl.id = V4L2_CID_MPEG_VIDC_VIDEO_DIVX_FORMAT;
1697 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &divx_ctrl);
1698 if (ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001699 DEBUG_PRINT_ERROR("Failed to set divx version");
Arun Menon906de572013-06-18 17:01:40 -07001700 }
1701 } else {
1702 DEBUG_PRINT_ERROR("Codec should not be ambiguous");
1703 }
1704 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001705
Jia Meng3a3c6492013-12-19 17:16:52 +08001706 property_get("persist.vidc.dec.conceal_color", property_value, DEFAULT_CONCEAL_COLOR);
1707 m_conceal_color= atoi(property_value);
1708 DEBUG_PRINT_HIGH("trying to set 0x%x as conceal color\n",m_conceal_color);
1709 control.id = V4L2_CID_MPEG_VIDC_VIDEO_CONCEAL_COLOR;
1710 control.value = m_conceal_color;
1711 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control);
1712 if (ret) {
1713 DEBUG_PRINT_ERROR("Failed to set conceal color %d\n", ret);
1714 }
1715
Arun Menon906de572013-06-18 17:01:40 -07001716 //Get the hardware capabilities
1717 memset((void *)&frmsize,0,sizeof(frmsize));
1718 frmsize.index = 0;
1719 frmsize.pixel_format = output_capability;
1720 ret = ioctl(drv_ctx.video_driver_fd,
1721 VIDIOC_ENUM_FRAMESIZES, &frmsize);
1722 if (ret || frmsize.type != V4L2_FRMSIZE_TYPE_STEPWISE) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001723 DEBUG_PRINT_ERROR("Failed to get framesizes");
Arun Menon906de572013-06-18 17:01:40 -07001724 return OMX_ErrorHardware;
1725 }
Deva Ramasubramanian3c55b212013-06-18 15:03:49 -07001726
Arun Menon906de572013-06-18 17:01:40 -07001727 if (frmsize.type == V4L2_FRMSIZE_TYPE_STEPWISE) {
1728 m_decoder_capability.min_width = frmsize.stepwise.min_width;
1729 m_decoder_capability.max_width = frmsize.stepwise.max_width;
1730 m_decoder_capability.min_height = frmsize.stepwise.min_height;
1731 m_decoder_capability.max_height = frmsize.stepwise.max_height;
1732 }
Deva Ramasubramanian3c55b212013-06-18 15:03:49 -07001733
Arun Menon906de572013-06-18 17:01:40 -07001734 fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
1735 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
1736 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
1737 fmt.fmt.pix_mp.pixelformat = capture_capability;
1738 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
1739 if (ret) {
1740 /*TODO: How to handle this case */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001741 DEBUG_PRINT_ERROR("Failed to set format on capture port");
Arun Menon906de572013-06-18 17:01:40 -07001742 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001743 DEBUG_PRINT_HIGH("Set Format was successful");
Arun Menon906de572013-06-18 17:01:40 -07001744 if (secure_mode) {
1745 control.id = V4L2_CID_MPEG_VIDC_VIDEO_SECURE;
1746 control.value = 1;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001747 DEBUG_PRINT_LOW("Omx_vdec:: calling to open secure device %d", ret);
Arun Menon906de572013-06-18 17:01:40 -07001748 ret=ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL,&control);
1749 if (ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001750 DEBUG_PRINT_ERROR("Omx_vdec:: Unable to open secure device %d", ret);
Arun Menon906de572013-06-18 17:01:40 -07001751 return OMX_ErrorInsufficientResources;
1752 }
1753 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001754
Arun Menon906de572013-06-18 17:01:40 -07001755 /*Get the Buffer requirements for input and output ports*/
1756 drv_ctx.ip_buf.buffer_type = VDEC_BUFFER_TYPE_INPUT;
1757 drv_ctx.op_buf.buffer_type = VDEC_BUFFER_TYPE_OUTPUT;
1758 if (secure_mode) {
1759 drv_ctx.op_buf.alignment=SZ_1M;
1760 drv_ctx.ip_buf.alignment=SZ_1M;
1761 } else {
1762 drv_ctx.op_buf.alignment=SZ_4K;
1763 drv_ctx.ip_buf.alignment=SZ_4K;
1764 }
1765 drv_ctx.interlace = VDEC_InterlaceFrameProgressive;
1766 drv_ctx.extradata = 0;
1767 drv_ctx.picture_order = VDEC_ORDER_DISPLAY;
1768 control.id = V4L2_CID_MPEG_VIDC_VIDEO_OUTPUT_ORDER;
1769 control.value = V4L2_MPEG_VIDC_VIDEO_OUTPUT_ORDER_DISPLAY;
1770 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control);
1771 drv_ctx.idr_only_decoding = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001772
Vinay Kalia5713bb32013-01-16 18:39:59 -08001773 m_state = OMX_StateLoaded;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001774#ifdef DEFAULT_EXTRADATA
Arun Menonf8908a62013-12-20 17:36:21 -08001775 if (strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8",
1776 OMX_MAX_STRINGNAME_SIZE) && (eRet == OMX_ErrorNone))
1777 enable_extradata(DEFAULT_EXTRADATA, true, true);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001778#endif
Vinay Kalia5713bb32013-01-16 18:39:59 -08001779 eRet=get_buffer_req(&drv_ctx.ip_buf);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001780 DEBUG_PRINT_HIGH("Input Buffer Size =%d",drv_ctx.ip_buf.buffer_size);
Vinay Kalia5713bb32013-01-16 18:39:59 -08001781 get_buffer_req(&drv_ctx.op_buf);
Arun Menon906de572013-06-18 17:01:40 -07001782 if (drv_ctx.decoder_format == VDEC_CODECTYPE_H264) {
1783 if (m_frame_parser.mutils == NULL) {
1784 m_frame_parser.mutils = new H264_Utils();
Shalaj Jain273b3e02012-06-22 19:08:03 -07001785
Arun Menon906de572013-06-18 17:01:40 -07001786 if (m_frame_parser.mutils == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001787 DEBUG_PRINT_ERROR("parser utils Allocation failed ");
Arun Menon906de572013-06-18 17:01:40 -07001788 eRet = OMX_ErrorInsufficientResources;
1789 } else {
1790 h264_scratch.nAllocLen = drv_ctx.ip_buf.buffer_size;
1791 h264_scratch.pBuffer = (OMX_U8 *)malloc (drv_ctx.ip_buf.buffer_size);
1792 h264_scratch.nFilledLen = 0;
1793 h264_scratch.nOffset = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001794
Arun Menon906de572013-06-18 17:01:40 -07001795 if (h264_scratch.pBuffer == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001796 DEBUG_PRINT_ERROR("h264_scratch.pBuffer Allocation failed ");
Arun Menon906de572013-06-18 17:01:40 -07001797 return OMX_ErrorInsufficientResources;
1798 }
1799 m_frame_parser.mutils->initialize_frame_checking_environment();
1800 m_frame_parser.mutils->allocate_rbsp_buffer (drv_ctx.ip_buf.buffer_size);
1801 }
1802 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001803
Arun Menon906de572013-06-18 17:01:40 -07001804 h264_parser = new h264_stream_parser();
1805 if (!h264_parser) {
1806 DEBUG_PRINT_ERROR("ERROR: H264 parser allocation failed!");
1807 eRet = OMX_ErrorInsufficientResources;
1808 }
1809 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001810
Arun Menon906de572013-06-18 17:01:40 -07001811 if (pipe(fds)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001812 DEBUG_PRINT_ERROR("pipe creation failed");
Arun Menon906de572013-06-18 17:01:40 -07001813 eRet = OMX_ErrorInsufficientResources;
1814 } else {
1815 int temp1[2];
1816 if (fds[0] == 0 || fds[1] == 0) {
1817 if (pipe (temp1)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001818 DEBUG_PRINT_ERROR("pipe creation failed");
Arun Menon906de572013-06-18 17:01:40 -07001819 return OMX_ErrorInsufficientResources;
1820 }
1821 //close (fds[0]);
1822 //close (fds[1]);
1823 fds[0] = temp1 [0];
1824 fds[1] = temp1 [1];
1825 }
1826 m_pipe_in = fds[0];
1827 m_pipe_out = fds[1];
1828 msg_thread_created = true;
1829 r = pthread_create(&msg_thread_id,0,message_thread,this);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001830
Arun Menon906de572013-06-18 17:01:40 -07001831 if (r < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001832 DEBUG_PRINT_ERROR("component_init(): message_thread creation failed");
Arun Menon906de572013-06-18 17:01:40 -07001833 msg_thread_created = false;
1834 eRet = OMX_ErrorInsufficientResources;
1835 }
1836 }
1837 }
1838
1839 if (eRet != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001840 DEBUG_PRINT_ERROR("Component Init Failed");
Arun Menon906de572013-06-18 17:01:40 -07001841 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001842 DEBUG_PRINT_HIGH("omx_vdec::component_init() success");
Arun Menon906de572013-06-18 17:01:40 -07001843 }
1844 //memset(&h264_mv_buff,0,sizeof(struct h264_mv_buffer));
1845 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001846}
1847
1848/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07001849 FUNCTION
1850 omx_vdec::GetComponentVersion
Shalaj Jain273b3e02012-06-22 19:08:03 -07001851
Arun Menon906de572013-06-18 17:01:40 -07001852 DESCRIPTION
1853 Returns the component version.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001854
Arun Menon906de572013-06-18 17:01:40 -07001855 PARAMETERS
1856 TBD.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001857
Arun Menon906de572013-06-18 17:01:40 -07001858 RETURN VALUE
1859 OMX_ErrorNone.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001860
Arun Menon906de572013-06-18 17:01:40 -07001861 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07001862OMX_ERRORTYPE omx_vdec::get_component_version
Arun Menon906de572013-06-18 17:01:40 -07001863(
1864 OMX_IN OMX_HANDLETYPE hComp,
1865 OMX_OUT OMX_STRING componentName,
1866 OMX_OUT OMX_VERSIONTYPE* componentVersion,
1867 OMX_OUT OMX_VERSIONTYPE* specVersion,
1868 OMX_OUT OMX_UUIDTYPE* componentUUID
1869 )
Shalaj Jain273b3e02012-06-22 19:08:03 -07001870{
Arun Menon906de572013-06-18 17:01:40 -07001871 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001872 DEBUG_PRINT_ERROR("Get Comp Version in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07001873 return OMX_ErrorInvalidState;
1874 }
Arun Menon906de572013-06-18 17:01:40 -07001875 /* TBD -- Return the proper version */
1876 if (specVersion) {
1877 specVersion->nVersion = OMX_SPEC_VERSION;
1878 }
1879 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001880}
1881/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07001882 FUNCTION
1883 omx_vdec::SendCommand
Shalaj Jain273b3e02012-06-22 19:08:03 -07001884
Arun Menon906de572013-06-18 17:01:40 -07001885 DESCRIPTION
1886 Returns zero if all the buffers released..
Shalaj Jain273b3e02012-06-22 19:08:03 -07001887
Arun Menon906de572013-06-18 17:01:40 -07001888 PARAMETERS
1889 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001890
Arun Menon906de572013-06-18 17:01:40 -07001891 RETURN VALUE
1892 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07001893
Arun Menon906de572013-06-18 17:01:40 -07001894 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07001895OMX_ERRORTYPE omx_vdec::send_command(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07001896 OMX_IN OMX_COMMANDTYPE cmd,
1897 OMX_IN OMX_U32 param1,
1898 OMX_IN OMX_PTR cmdData
1899 )
Shalaj Jain273b3e02012-06-22 19:08:03 -07001900{
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001901 DEBUG_PRINT_LOW("send_command: Recieved a Command from Client");
Arun Menon906de572013-06-18 17:01:40 -07001902 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001903 DEBUG_PRINT_ERROR("ERROR: Send Command in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07001904 return OMX_ErrorInvalidState;
1905 }
1906 if (cmd == OMX_CommandFlush && param1 != OMX_CORE_INPUT_PORT_INDEX
Arun Menon906de572013-06-18 17:01:40 -07001907 && param1 != OMX_CORE_OUTPUT_PORT_INDEX && param1 != OMX_ALL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001908 DEBUG_PRINT_ERROR("send_command(): ERROR OMX_CommandFlush "
Arun Menon906de572013-06-18 17:01:40 -07001909 "to invalid port: %lu", param1);
1910 return OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001911 }
1912 post_event((unsigned)cmd,(unsigned)param1,OMX_COMPONENT_GENERATE_COMMAND);
1913 sem_wait(&m_cmd_lock);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001914 DEBUG_PRINT_LOW("send_command: Command Processed");
Shalaj Jain273b3e02012-06-22 19:08:03 -07001915 return OMX_ErrorNone;
1916}
1917
1918/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07001919 FUNCTION
1920 omx_vdec::SendCommand
Shalaj Jain273b3e02012-06-22 19:08:03 -07001921
Arun Menon906de572013-06-18 17:01:40 -07001922 DESCRIPTION
1923 Returns zero if all the buffers released..
Shalaj Jain273b3e02012-06-22 19:08:03 -07001924
Arun Menon906de572013-06-18 17:01:40 -07001925 PARAMETERS
1926 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07001927
Arun Menon906de572013-06-18 17:01:40 -07001928 RETURN VALUE
1929 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07001930
Arun Menon906de572013-06-18 17:01:40 -07001931 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07001932OMX_ERRORTYPE omx_vdec::send_command_proxy(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07001933 OMX_IN OMX_COMMANDTYPE cmd,
1934 OMX_IN OMX_U32 param1,
1935 OMX_IN OMX_PTR cmdData
1936 )
Shalaj Jain273b3e02012-06-22 19:08:03 -07001937{
Arun Menon906de572013-06-18 17:01:40 -07001938 OMX_ERRORTYPE eRet = OMX_ErrorNone;
1939 OMX_STATETYPE eState = (OMX_STATETYPE) param1;
1940 int bFlag = 1,sem_posted = 0,ret=0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07001941
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001942 DEBUG_PRINT_LOW("send_command_proxy(): cmd = %d", cmd);
1943 DEBUG_PRINT_HIGH("send_command_proxy(): Current State %d, Expected State %d",
Arun Menon906de572013-06-18 17:01:40 -07001944 m_state, eState);
Shalaj Jain273b3e02012-06-22 19:08:03 -07001945
Arun Menon906de572013-06-18 17:01:40 -07001946 if (cmd == OMX_CommandStateSet) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001947 DEBUG_PRINT_HIGH("send_command_proxy(): OMX_CommandStateSet issued");
1948 DEBUG_PRINT_HIGH("Current State %d, Expected State %d", m_state, eState);
Arun Menon906de572013-06-18 17:01:40 -07001949 /***************************/
1950 /* Current State is Loaded */
1951 /***************************/
1952 if (m_state == OMX_StateLoaded) {
1953 if (eState == OMX_StateIdle) {
1954 //if all buffers are allocated or all ports disabled
1955 if (allocate_done() ||
1956 (m_inp_bEnabled == OMX_FALSE && m_out_bEnabled == OMX_FALSE)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001957 DEBUG_PRINT_LOW("send_command_proxy(): Loaded-->Idle");
Arun Menon906de572013-06-18 17:01:40 -07001958 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001959 DEBUG_PRINT_LOW("send_command_proxy(): Loaded-->Idle-Pending");
Arun Menon906de572013-06-18 17:01:40 -07001960 BITMASK_SET(&m_flags, OMX_COMPONENT_IDLE_PENDING);
1961 // Skip the event notification
1962 bFlag = 0;
1963 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07001964 }
Arun Menon906de572013-06-18 17:01:40 -07001965 /* Requesting transition from Loaded to Loaded */
1966 else if (eState == OMX_StateLoaded) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001967 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Loaded-->Loaded");
Arun Menon906de572013-06-18 17:01:40 -07001968 post_event(OMX_EventError,OMX_ErrorSameState,\
1969 OMX_COMPONENT_GENERATE_EVENT);
1970 eRet = OMX_ErrorSameState;
1971 }
1972 /* Requesting transition from Loaded to WaitForResources */
1973 else if (eState == OMX_StateWaitForResources) {
1974 /* Since error is None , we will post an event
1975 at the end of this function definition */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001976 DEBUG_PRINT_LOW("send_command_proxy(): Loaded-->WaitForResources");
Arun Menon906de572013-06-18 17:01:40 -07001977 }
1978 /* Requesting transition from Loaded to Executing */
1979 else if (eState == OMX_StateExecuting) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001980 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Loaded-->Executing");
Arun Menon906de572013-06-18 17:01:40 -07001981 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
1982 OMX_COMPONENT_GENERATE_EVENT);
1983 eRet = OMX_ErrorIncorrectStateTransition;
1984 }
1985 /* Requesting transition from Loaded to Pause */
1986 else if (eState == OMX_StatePause) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001987 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Loaded-->Pause");
Arun Menon906de572013-06-18 17:01:40 -07001988 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
1989 OMX_COMPONENT_GENERATE_EVENT);
1990 eRet = OMX_ErrorIncorrectStateTransition;
1991 }
1992 /* Requesting transition from Loaded to Invalid */
1993 else if (eState == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001994 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Loaded-->Invalid");
Arun Menon906de572013-06-18 17:01:40 -07001995 post_event(OMX_EventError,eState,OMX_COMPONENT_GENERATE_EVENT);
1996 eRet = OMX_ErrorInvalidState;
1997 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07001998 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Loaded-->Invalid(%d Not Handled)",\
Arun Menon906de572013-06-18 17:01:40 -07001999 eState);
2000 eRet = OMX_ErrorBadParameter;
2001 }
2002 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002003
Arun Menon906de572013-06-18 17:01:40 -07002004 /***************************/
2005 /* Current State is IDLE */
2006 /***************************/
2007 else if (m_state == OMX_StateIdle) {
2008 if (eState == OMX_StateLoaded) {
2009 if (release_done()) {
2010 /*
2011 Since error is None , we will post an event at the end
2012 of this function definition
2013 */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002014 DEBUG_PRINT_LOW("send_command_proxy(): Idle-->Loaded");
Arun Menon906de572013-06-18 17:01:40 -07002015 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002016 DEBUG_PRINT_LOW("send_command_proxy(): Idle-->Loaded-Pending");
Arun Menon906de572013-06-18 17:01:40 -07002017 BITMASK_SET(&m_flags, OMX_COMPONENT_LOADING_PENDING);
2018 // Skip the event notification
2019 bFlag = 0;
2020 }
2021 }
2022 /* Requesting transition from Idle to Executing */
2023 else if (eState == OMX_StateExecuting) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002024 DEBUG_PRINT_LOW("send_command_proxy(): Idle-->Executing");
Arun Menon906de572013-06-18 17:01:40 -07002025 //BITMASK_SET(&m_flags, OMX_COMPONENT_EXECUTE_PENDING);
2026 bFlag = 1;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002027 DEBUG_PRINT_LOW("send_command_proxy(): Idle-->Executing");
Arun Menon906de572013-06-18 17:01:40 -07002028 m_state=OMX_StateExecuting;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002029 DEBUG_PRINT_HIGH("Stream On CAPTURE Was successful");
Arun Menon906de572013-06-18 17:01:40 -07002030 }
2031 /* Requesting transition from Idle to Idle */
2032 else if (eState == OMX_StateIdle) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002033 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Idle-->Idle");
Arun Menon906de572013-06-18 17:01:40 -07002034 post_event(OMX_EventError,OMX_ErrorSameState,\
2035 OMX_COMPONENT_GENERATE_EVENT);
2036 eRet = OMX_ErrorSameState;
2037 }
2038 /* Requesting transition from Idle to WaitForResources */
2039 else if (eState == OMX_StateWaitForResources) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002040 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Idle-->WaitForResources");
Arun Menon906de572013-06-18 17:01:40 -07002041 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2042 OMX_COMPONENT_GENERATE_EVENT);
2043 eRet = OMX_ErrorIncorrectStateTransition;
2044 }
2045 /* Requesting transition from Idle to Pause */
2046 else if (eState == OMX_StatePause) {
2047 /*To pause the Video core we need to start the driver*/
2048 if (/*ioctl (drv_ctx.video_driver_fd,VDEC_IOCTL_CMD_START,
2049 NULL) < */0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002050 DEBUG_PRINT_ERROR("VDEC_IOCTL_CMD_START FAILED");
Arun Menon906de572013-06-18 17:01:40 -07002051 omx_report_error ();
2052 eRet = OMX_ErrorHardware;
2053 } else {
2054 BITMASK_SET(&m_flags,OMX_COMPONENT_PAUSE_PENDING);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002055 DEBUG_PRINT_LOW("send_command_proxy(): Idle-->Pause");
Arun Menon906de572013-06-18 17:01:40 -07002056 bFlag = 0;
2057 }
2058 }
2059 /* Requesting transition from Idle to Invalid */
2060 else if (eState == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002061 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Idle-->Invalid");
Arun Menon906de572013-06-18 17:01:40 -07002062 post_event(OMX_EventError,eState,OMX_COMPONENT_GENERATE_EVENT);
2063 eRet = OMX_ErrorInvalidState;
2064 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002065 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Idle --> %d Not Handled",eState);
Arun Menon906de572013-06-18 17:01:40 -07002066 eRet = OMX_ErrorBadParameter;
2067 }
2068 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002069
Arun Menon906de572013-06-18 17:01:40 -07002070 /******************************/
2071 /* Current State is Executing */
2072 /******************************/
2073 else if (m_state == OMX_StateExecuting) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002074 DEBUG_PRINT_LOW("Command Recieved in OMX_StateExecuting");
Arun Menon906de572013-06-18 17:01:40 -07002075 /* Requesting transition from Executing to Idle */
2076 if (eState == OMX_StateIdle) {
2077 /* Since error is None , we will post an event
2078 at the end of this function definition
2079 */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002080 DEBUG_PRINT_LOW("send_command_proxy(): Executing --> Idle");
Arun Menon906de572013-06-18 17:01:40 -07002081 BITMASK_SET(&m_flags,OMX_COMPONENT_IDLE_PENDING);
2082 if (!sem_posted) {
2083 sem_posted = 1;
2084 sem_post (&m_cmd_lock);
2085 execute_omx_flush(OMX_ALL);
2086 }
2087 bFlag = 0;
2088 }
2089 /* Requesting transition from Executing to Paused */
2090 else if (eState == OMX_StatePause) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002091 DEBUG_PRINT_LOW("PAUSE Command Issued");
Arun Menon906de572013-06-18 17:01:40 -07002092 m_state = OMX_StatePause;
2093 bFlag = 1;
2094 }
2095 /* Requesting transition from Executing to Loaded */
2096 else if (eState == OMX_StateLoaded) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002097 DEBUG_PRINT_ERROR("send_command_proxy(): Executing --> Loaded");
Arun Menon906de572013-06-18 17:01:40 -07002098 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2099 OMX_COMPONENT_GENERATE_EVENT);
2100 eRet = OMX_ErrorIncorrectStateTransition;
2101 }
2102 /* Requesting transition from Executing to WaitForResources */
2103 else if (eState == OMX_StateWaitForResources) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002104 DEBUG_PRINT_ERROR("send_command_proxy(): Executing --> WaitForResources");
Arun Menon906de572013-06-18 17:01:40 -07002105 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2106 OMX_COMPONENT_GENERATE_EVENT);
2107 eRet = OMX_ErrorIncorrectStateTransition;
2108 }
2109 /* Requesting transition from Executing to Executing */
2110 else if (eState == OMX_StateExecuting) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002111 DEBUG_PRINT_ERROR("send_command_proxy(): Executing --> Executing");
Arun Menon906de572013-06-18 17:01:40 -07002112 post_event(OMX_EventError,OMX_ErrorSameState,\
2113 OMX_COMPONENT_GENERATE_EVENT);
2114 eRet = OMX_ErrorSameState;
2115 }
2116 /* Requesting transition from Executing to Invalid */
2117 else if (eState == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002118 DEBUG_PRINT_ERROR("send_command_proxy(): Executing --> Invalid");
Arun Menon906de572013-06-18 17:01:40 -07002119 post_event(OMX_EventError,eState,OMX_COMPONENT_GENERATE_EVENT);
2120 eRet = OMX_ErrorInvalidState;
2121 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002122 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Executing --> %d Not Handled",eState);
Arun Menon906de572013-06-18 17:01:40 -07002123 eRet = OMX_ErrorBadParameter;
2124 }
2125 }
2126 /***************************/
2127 /* Current State is Pause */
2128 /***************************/
2129 else if (m_state == OMX_StatePause) {
2130 /* Requesting transition from Pause to Executing */
2131 if (eState == OMX_StateExecuting) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002132 DEBUG_PRINT_LOW("Pause --> Executing");
Arun Menon906de572013-06-18 17:01:40 -07002133 m_state = OMX_StateExecuting;
2134 bFlag = 1;
2135 }
2136 /* Requesting transition from Pause to Idle */
2137 else if (eState == OMX_StateIdle) {
2138 /* Since error is None , we will post an event
2139 at the end of this function definition */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002140 DEBUG_PRINT_LOW("Pause --> Idle");
Arun Menon906de572013-06-18 17:01:40 -07002141 BITMASK_SET(&m_flags,OMX_COMPONENT_IDLE_PENDING);
2142 if (!sem_posted) {
2143 sem_posted = 1;
2144 sem_post (&m_cmd_lock);
2145 execute_omx_flush(OMX_ALL);
2146 }
2147 bFlag = 0;
2148 }
2149 /* Requesting transition from Pause to loaded */
2150 else if (eState == OMX_StateLoaded) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002151 DEBUG_PRINT_ERROR("Pause --> loaded");
Arun Menon906de572013-06-18 17:01:40 -07002152 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2153 OMX_COMPONENT_GENERATE_EVENT);
2154 eRet = OMX_ErrorIncorrectStateTransition;
2155 }
2156 /* Requesting transition from Pause to WaitForResources */
2157 else if (eState == OMX_StateWaitForResources) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002158 DEBUG_PRINT_ERROR("Pause --> WaitForResources");
Arun Menon906de572013-06-18 17:01:40 -07002159 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2160 OMX_COMPONENT_GENERATE_EVENT);
2161 eRet = OMX_ErrorIncorrectStateTransition;
2162 }
2163 /* Requesting transition from Pause to Pause */
2164 else if (eState == OMX_StatePause) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002165 DEBUG_PRINT_ERROR("Pause --> Pause");
Arun Menon906de572013-06-18 17:01:40 -07002166 post_event(OMX_EventError,OMX_ErrorSameState,\
2167 OMX_COMPONENT_GENERATE_EVENT);
2168 eRet = OMX_ErrorSameState;
2169 }
2170 /* Requesting transition from Pause to Invalid */
2171 else if (eState == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002172 DEBUG_PRINT_ERROR("Pause --> Invalid");
Arun Menon906de572013-06-18 17:01:40 -07002173 post_event(OMX_EventError,eState,OMX_COMPONENT_GENERATE_EVENT);
2174 eRet = OMX_ErrorInvalidState;
2175 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002176 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Paused --> %d Not Handled",eState);
Arun Menon906de572013-06-18 17:01:40 -07002177 eRet = OMX_ErrorBadParameter;
2178 }
2179 }
2180 /***************************/
2181 /* Current State is WaitForResources */
2182 /***************************/
2183 else if (m_state == OMX_StateWaitForResources) {
2184 /* Requesting transition from WaitForResources to Loaded */
2185 if (eState == OMX_StateLoaded) {
2186 /* Since error is None , we will post an event
2187 at the end of this function definition */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002188 DEBUG_PRINT_LOW("send_command_proxy(): WaitForResources-->Loaded");
Arun Menon906de572013-06-18 17:01:40 -07002189 }
2190 /* Requesting transition from WaitForResources to WaitForResources */
2191 else if (eState == OMX_StateWaitForResources) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002192 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): WaitForResources-->WaitForResources");
Arun Menon906de572013-06-18 17:01:40 -07002193 post_event(OMX_EventError,OMX_ErrorSameState,
2194 OMX_COMPONENT_GENERATE_EVENT);
2195 eRet = OMX_ErrorSameState;
2196 }
2197 /* Requesting transition from WaitForResources to Executing */
2198 else if (eState == OMX_StateExecuting) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002199 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): WaitForResources-->Executing");
Arun Menon906de572013-06-18 17:01:40 -07002200 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2201 OMX_COMPONENT_GENERATE_EVENT);
2202 eRet = OMX_ErrorIncorrectStateTransition;
2203 }
2204 /* Requesting transition from WaitForResources to Pause */
2205 else if (eState == OMX_StatePause) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002206 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): WaitForResources-->Pause");
Arun Menon906de572013-06-18 17:01:40 -07002207 post_event(OMX_EventError,OMX_ErrorIncorrectStateTransition,\
2208 OMX_COMPONENT_GENERATE_EVENT);
2209 eRet = OMX_ErrorIncorrectStateTransition;
2210 }
2211 /* Requesting transition from WaitForResources to Invalid */
2212 else if (eState == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002213 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): WaitForResources-->Invalid");
Arun Menon906de572013-06-18 17:01:40 -07002214 post_event(OMX_EventError,eState,OMX_COMPONENT_GENERATE_EVENT);
2215 eRet = OMX_ErrorInvalidState;
2216 }
2217 /* Requesting transition from WaitForResources to Loaded -
2218 is NOT tested by Khronos TS */
2219
2220 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002221 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): %d --> %d(Not Handled)",m_state,eState);
Arun Menon906de572013-06-18 17:01:40 -07002222 eRet = OMX_ErrorBadParameter;
2223 }
2224 }
2225 /********************************/
2226 /* Current State is Invalid */
2227 /*******************************/
2228 else if (m_state == OMX_StateInvalid) {
2229 /* State Transition from Inavlid to any state */
2230 if (eState == (OMX_StateLoaded || OMX_StateWaitForResources
2231 || OMX_StateIdle || OMX_StateExecuting
2232 || OMX_StatePause || OMX_StateInvalid)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002233 DEBUG_PRINT_ERROR("ERROR::send_command_proxy(): Invalid -->Loaded");
Arun Menon906de572013-06-18 17:01:40 -07002234 post_event(OMX_EventError,OMX_ErrorInvalidState,\
2235 OMX_COMPONENT_GENERATE_EVENT);
2236 eRet = OMX_ErrorInvalidState;
2237 }
2238 } else if (cmd == OMX_CommandFlush) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002239 DEBUG_PRINT_HIGH("send_command_proxy(): OMX_CommandFlush issued"
Arun Menon906de572013-06-18 17:01:40 -07002240 "with param1: %lu", param1);
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07002241#ifdef _MSM8974_
2242 send_codec_config();
2243#endif
Arun Menon906de572013-06-18 17:01:40 -07002244 if (OMX_CORE_INPUT_PORT_INDEX == param1 || OMX_ALL == param1) {
2245 BITMASK_SET(&m_flags, OMX_COMPONENT_INPUT_FLUSH_PENDING);
2246 }
2247 if (OMX_CORE_OUTPUT_PORT_INDEX == param1 || OMX_ALL == param1) {
2248 BITMASK_SET(&m_flags, OMX_COMPONENT_OUTPUT_FLUSH_PENDING);
2249 }
2250 if (!sem_posted) {
2251 sem_posted = 1;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002252 DEBUG_PRINT_LOW("Set the Semaphore");
Arun Menon906de572013-06-18 17:01:40 -07002253 sem_post (&m_cmd_lock);
2254 execute_omx_flush(param1);
2255 }
2256 bFlag = 0;
2257 } else if ( cmd == OMX_CommandPortEnable) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002258 DEBUG_PRINT_HIGH("send_command_proxy(): OMX_CommandPortEnable issued"
Arun Menon906de572013-06-18 17:01:40 -07002259 "with param1: %lu", param1);
2260 if (param1 == OMX_CORE_INPUT_PORT_INDEX || param1 == OMX_ALL) {
2261 m_inp_bEnabled = OMX_TRUE;
2262
2263 if ( (m_state == OMX_StateLoaded &&
2264 !BITMASK_PRESENT(&m_flags,OMX_COMPONENT_IDLE_PENDING))
2265 || allocate_input_done()) {
2266 post_event(OMX_CommandPortEnable,OMX_CORE_INPUT_PORT_INDEX,
2267 OMX_COMPONENT_GENERATE_EVENT);
2268 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002269 DEBUG_PRINT_LOW("send_command_proxy(): Disabled-->Enabled Pending");
Arun Menon906de572013-06-18 17:01:40 -07002270 BITMASK_SET(&m_flags, OMX_COMPONENT_INPUT_ENABLE_PENDING);
2271 // Skip the event notification
2272 bFlag = 0;
2273 }
2274 }
2275 if (param1 == OMX_CORE_OUTPUT_PORT_INDEX || param1 == OMX_ALL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002276 DEBUG_PRINT_LOW("Enable output Port command recieved");
Arun Menon906de572013-06-18 17:01:40 -07002277 m_out_bEnabled = OMX_TRUE;
2278
2279 if ( (m_state == OMX_StateLoaded &&
2280 !BITMASK_PRESENT(&m_flags,OMX_COMPONENT_IDLE_PENDING))
2281 || (allocate_output_done())) {
2282 post_event(OMX_CommandPortEnable,OMX_CORE_OUTPUT_PORT_INDEX,
2283 OMX_COMPONENT_GENERATE_EVENT);
2284
2285 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002286 DEBUG_PRINT_LOW("send_command_proxy(): Disabled-->Enabled Pending");
Arun Menon906de572013-06-18 17:01:40 -07002287 BITMASK_SET(&m_flags, OMX_COMPONENT_OUTPUT_ENABLE_PENDING);
2288 // Skip the event notification
2289 bFlag = 0;
2290 }
2291 }
2292 } else if (cmd == OMX_CommandPortDisable) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002293 DEBUG_PRINT_HIGH("send_command_proxy(): OMX_CommandPortDisable issued"
Arun Menon906de572013-06-18 17:01:40 -07002294 "with param1: %lu", param1);
2295 if (param1 == OMX_CORE_INPUT_PORT_INDEX || param1 == OMX_ALL) {
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07002296 codec_config_flag = false;
Arun Menon906de572013-06-18 17:01:40 -07002297 m_inp_bEnabled = OMX_FALSE;
2298 if ((m_state == OMX_StateLoaded || m_state == OMX_StateIdle)
2299 && release_input_done()) {
2300 post_event(OMX_CommandPortDisable,OMX_CORE_INPUT_PORT_INDEX,
2301 OMX_COMPONENT_GENERATE_EVENT);
2302 } else {
2303 BITMASK_SET(&m_flags, OMX_COMPONENT_INPUT_DISABLE_PENDING);
2304 if (m_state == OMX_StatePause ||m_state == OMX_StateExecuting) {
2305 if (!sem_posted) {
2306 sem_posted = 1;
2307 sem_post (&m_cmd_lock);
2308 }
2309 execute_omx_flush(OMX_CORE_INPUT_PORT_INDEX);
2310 }
2311
2312 // Skip the event notification
2313 bFlag = 0;
2314 }
2315 }
2316 if (param1 == OMX_CORE_OUTPUT_PORT_INDEX || param1 == OMX_ALL) {
2317 m_out_bEnabled = OMX_FALSE;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002318 DEBUG_PRINT_LOW("Disable output Port command recieved");
Arun Menon906de572013-06-18 17:01:40 -07002319 if ((m_state == OMX_StateLoaded || m_state == OMX_StateIdle)
2320 && release_output_done()) {
2321 post_event(OMX_CommandPortDisable,OMX_CORE_OUTPUT_PORT_INDEX,\
2322 OMX_COMPONENT_GENERATE_EVENT);
2323 } else {
2324 BITMASK_SET(&m_flags, OMX_COMPONENT_OUTPUT_DISABLE_PENDING);
2325 if (m_state == OMX_StatePause ||m_state == OMX_StateExecuting) {
2326 if (!sem_posted) {
2327 sem_posted = 1;
2328 sem_post (&m_cmd_lock);
2329 }
2330 BITMASK_SET(&m_flags, OMX_COMPONENT_OUTPUT_FLUSH_IN_DISABLE_PENDING);
2331 execute_omx_flush(OMX_CORE_OUTPUT_PORT_INDEX);
2332 }
2333 // Skip the event notification
2334 bFlag = 0;
2335
2336 }
2337 }
2338 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002339 DEBUG_PRINT_ERROR("Error: Invalid Command other than StateSet (%d)",cmd);
Arun Menon906de572013-06-18 17:01:40 -07002340 eRet = OMX_ErrorNotImplemented;
2341 }
2342 if (eRet == OMX_ErrorNone && bFlag) {
2343 post_event(cmd,eState,OMX_COMPONENT_GENERATE_EVENT);
2344 }
2345 if (!sem_posted) {
2346 sem_post(&m_cmd_lock);
2347 }
2348
2349 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002350}
2351
2352/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07002353 FUNCTION
2354 omx_vdec::ExecuteOmxFlush
Shalaj Jain273b3e02012-06-22 19:08:03 -07002355
Arun Menon906de572013-06-18 17:01:40 -07002356 DESCRIPTION
2357 Executes the OMX flush.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002358
Arun Menon906de572013-06-18 17:01:40 -07002359 PARAMETERS
2360 flushtype - input flush(1)/output flush(0)/ both.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002361
Arun Menon906de572013-06-18 17:01:40 -07002362 RETURN VALUE
2363 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07002364
Arun Menon906de572013-06-18 17:01:40 -07002365 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07002366bool omx_vdec::execute_omx_flush(OMX_U32 flushType)
2367{
Arun Menon906de572013-06-18 17:01:40 -07002368 bool bRet = false;
2369 struct v4l2_plane plane;
2370 struct v4l2_buffer v4l2_buf;
2371 struct v4l2_decoder_cmd dec;
Surajit Podderd2644d52013-08-28 17:59:06 +05302372 DEBUG_PRINT_LOW("in %s, flushing %lu", __func__, flushType);
Arun Menon906de572013-06-18 17:01:40 -07002373 memset((void *)&v4l2_buf,0,sizeof(v4l2_buf));
2374 dec.cmd = V4L2_DEC_QCOM_CMD_FLUSH;
Deva Ramasubramaniancc8fb902013-05-07 18:19:14 -07002375
Arun Menon906de572013-06-18 17:01:40 -07002376 DEBUG_PRINT_HIGH("in %s: reconfig? %d", __func__, in_reconfig);
Deva Ramasubramaniancc8fb902013-05-07 18:19:14 -07002377
Arun Menon906de572013-06-18 17:01:40 -07002378 if (in_reconfig && flushType == OMX_CORE_OUTPUT_PORT_INDEX) {
2379 output_flush_progress = true;
2380 dec.flags = V4L2_DEC_QCOM_CMD_FLUSH_CAPTURE;
2381 } else {
2382 /* XXX: The driver/hardware does not support flushing of individual ports
2383 * in all states. So we pretty much need to flush both ports internally,
2384 * but client should only get the FLUSH_(INPUT|OUTPUT)_DONE for the one it
2385 * requested. Since OMX_COMPONENT_(OUTPUT|INPUT)_FLUSH_PENDING isn't set,
2386 * we automatically omit sending the FLUSH done for the "opposite" port. */
2387 input_flush_progress = true;
2388 output_flush_progress = true;
2389 dec.flags = V4L2_DEC_QCOM_CMD_FLUSH_OUTPUT | V4L2_DEC_QCOM_CMD_FLUSH_CAPTURE;
2390 }
Deva Ramasubramanian03c9c742012-07-02 15:00:15 -07002391
Arun Menon906de572013-06-18 17:01:40 -07002392 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_DECODER_CMD, &dec)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002393 DEBUG_PRINT_ERROR("Flush Port (%lu) Failed ", flushType);
Arun Menon906de572013-06-18 17:01:40 -07002394 bRet = false;
2395 }
Deva Ramasubramanian03c9c742012-07-02 15:00:15 -07002396
Arun Menon906de572013-06-18 17:01:40 -07002397 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002398}
2399/*=========================================================================
2400FUNCTION : execute_output_flush
2401
2402DESCRIPTION
Arun Menon906de572013-06-18 17:01:40 -07002403Executes the OMX flush at OUTPUT PORT.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002404
2405PARAMETERS
Arun Menon906de572013-06-18 17:01:40 -07002406None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002407
2408RETURN VALUE
Arun Menon906de572013-06-18 17:01:40 -07002409true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07002410==========================================================================*/
2411bool omx_vdec::execute_output_flush()
2412{
Arun Menon906de572013-06-18 17:01:40 -07002413 unsigned p1 = 0; // Parameter - 1
2414 unsigned p2 = 0; // Parameter - 2
2415 unsigned ident = 0;
2416 bool bRet = true;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002417
Arun Menon906de572013-06-18 17:01:40 -07002418 /*Generate FBD for all Buffers in the FTBq*/
2419 pthread_mutex_lock(&m_lock);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002420 DEBUG_PRINT_LOW("Initiate Output Flush");
vivek mehta79cff222014-01-22 12:17:07 -08002421
2422 //reset last render TS
2423 if(m_last_rendered_TS > 0) {
2424 m_last_rendered_TS = 0;
2425 }
vivek mehtaa75c69f2014-01-10 21:50:37 -08002426
Arun Menon906de572013-06-18 17:01:40 -07002427 while (m_ftb_q.m_size) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002428 DEBUG_PRINT_LOW("Buffer queue size %d pending buf cnt %d",
Arun Menon906de572013-06-18 17:01:40 -07002429 m_ftb_q.m_size,pending_output_buffers);
2430 m_ftb_q.pop_entry(&p1,&p2,&ident);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002431 DEBUG_PRINT_LOW("ID(%x) P1(%x) P2(%x)", ident, p1, p2);
Arun Menon906de572013-06-18 17:01:40 -07002432 if (ident == m_fill_output_msg ) {
2433 m_cb.FillBufferDone(&m_cmp, m_app_data, (OMX_BUFFERHEADERTYPE *)p2);
2434 } else if (ident == OMX_COMPONENT_GENERATE_FBD) {
2435 fill_buffer_done(&m_cmp,(OMX_BUFFERHEADERTYPE *)p1);
2436 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002437 }
Arun Menon906de572013-06-18 17:01:40 -07002438 pthread_mutex_unlock(&m_lock);
2439 output_flush_progress = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002440
Arun Menon906de572013-06-18 17:01:40 -07002441 if (arbitrary_bytes) {
2442 prev_ts = LLONG_MAX;
2443 rst_prev_ts = true;
2444 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002445 DEBUG_PRINT_HIGH("OMX flush o/p Port complete PenBuf(%d)", pending_output_buffers);
Arun Menon906de572013-06-18 17:01:40 -07002446 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002447}
2448/*=========================================================================
2449FUNCTION : execute_input_flush
2450
2451DESCRIPTION
Arun Menon906de572013-06-18 17:01:40 -07002452Executes the OMX flush at INPUT PORT.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002453
2454PARAMETERS
Arun Menon906de572013-06-18 17:01:40 -07002455None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002456
2457RETURN VALUE
Arun Menon906de572013-06-18 17:01:40 -07002458true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07002459==========================================================================*/
2460bool omx_vdec::execute_input_flush()
2461{
Arun Menon906de572013-06-18 17:01:40 -07002462 unsigned i =0;
2463 unsigned p1 = 0; // Parameter - 1
2464 unsigned p2 = 0; // Parameter - 2
2465 unsigned ident = 0;
2466 bool bRet = true;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002467
Arun Menon906de572013-06-18 17:01:40 -07002468 /*Generate EBD for all Buffers in the ETBq*/
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002469 DEBUG_PRINT_LOW("Initiate Input Flush");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002470
Arun Menon906de572013-06-18 17:01:40 -07002471 pthread_mutex_lock(&m_lock);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002472 DEBUG_PRINT_LOW("Check if the Queue is empty");
Arun Menon906de572013-06-18 17:01:40 -07002473 while (m_etb_q.m_size) {
2474 m_etb_q.pop_entry(&p1,&p2,&ident);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002475
Arun Menon906de572013-06-18 17:01:40 -07002476 if (ident == OMX_COMPONENT_GENERATE_ETB_ARBITRARY) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002477 DEBUG_PRINT_LOW("Flush Input Heap Buffer %p",(OMX_BUFFERHEADERTYPE *)p2);
Arun Menon906de572013-06-18 17:01:40 -07002478 m_cb.EmptyBufferDone(&m_cmp ,m_app_data, (OMX_BUFFERHEADERTYPE *)p2);
2479 } else if (ident == OMX_COMPONENT_GENERATE_ETB) {
2480 pending_input_buffers++;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002481 DEBUG_PRINT_LOW("Flush Input OMX_COMPONENT_GENERATE_ETB %p, pending_input_buffers %d",
Arun Menon906de572013-06-18 17:01:40 -07002482 (OMX_BUFFERHEADERTYPE *)p2, pending_input_buffers);
2483 empty_buffer_done(&m_cmp,(OMX_BUFFERHEADERTYPE *)p2);
2484 } else if (ident == OMX_COMPONENT_GENERATE_EBD) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002485 DEBUG_PRINT_LOW("Flush Input OMX_COMPONENT_GENERATE_EBD %p",
Arun Menon906de572013-06-18 17:01:40 -07002486 (OMX_BUFFERHEADERTYPE *)p1);
2487 empty_buffer_done(&m_cmp,(OMX_BUFFERHEADERTYPE *)p1);
2488 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002489 }
Arun Menon906de572013-06-18 17:01:40 -07002490 time_stamp_dts.flush_timestamp();
2491 /*Check if Heap Buffers are to be flushed*/
2492 if (arbitrary_bytes && !(codec_config_flag)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002493 DEBUG_PRINT_LOW("Reset all the variables before flusing");
Arun Menon906de572013-06-18 17:01:40 -07002494 h264_scratch.nFilledLen = 0;
2495 nal_count = 0;
2496 look_ahead_nal = false;
2497 frame_count = 0;
2498 h264_last_au_ts = LLONG_MAX;
2499 h264_last_au_flags = 0;
2500 memset(m_demux_offsets, 0, ( sizeof(OMX_U32) * 8192) );
2501 m_demux_entries = 0;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002502 DEBUG_PRINT_LOW("Initialize parser");
Arun Menon906de572013-06-18 17:01:40 -07002503 if (m_frame_parser.mutils) {
2504 m_frame_parser.mutils->initialize_frame_checking_environment();
2505 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002506
Arun Menon906de572013-06-18 17:01:40 -07002507 while (m_input_pending_q.m_size) {
2508 m_input_pending_q.pop_entry(&p1,&p2,&ident);
2509 m_cb.EmptyBufferDone(&m_cmp ,m_app_data, (OMX_BUFFERHEADERTYPE *)p1);
2510 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002511
Arun Menon906de572013-06-18 17:01:40 -07002512 if (psource_frame) {
2513 m_cb.EmptyBufferDone(&m_cmp ,m_app_data,psource_frame);
2514 psource_frame = NULL;
2515 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002516
Arun Menon906de572013-06-18 17:01:40 -07002517 if (pdest_frame) {
2518 pdest_frame->nFilledLen = 0;
2519 m_input_free_q.insert_entry((unsigned) pdest_frame, (unsigned int)NULL,
2520 (unsigned int)NULL);
2521 pdest_frame = NULL;
2522 }
2523 m_frame_parser.flush();
2524 } else if (codec_config_flag) {
2525 DEBUG_PRINT_HIGH("frame_parser flushing skipped due to codec config buffer "
2526 "is not sent to the driver yet");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002527 }
Arun Menon906de572013-06-18 17:01:40 -07002528 pthread_mutex_unlock(&m_lock);
2529 input_flush_progress = false;
2530 if (!arbitrary_bytes) {
2531 prev_ts = LLONG_MAX;
2532 rst_prev_ts = true;
2533 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002534#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -07002535 if (m_debug_timestamp) {
2536 m_timestamp_list.reset_ts_list();
2537 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002538#endif
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002539 DEBUG_PRINT_HIGH("OMX flush i/p Port complete PenBuf(%d)", pending_input_buffers);
Arun Menon906de572013-06-18 17:01:40 -07002540 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002541}
2542
2543
2544/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07002545 FUNCTION
2546 omx_vdec::SendCommandEvent
Shalaj Jain273b3e02012-06-22 19:08:03 -07002547
Arun Menon906de572013-06-18 17:01:40 -07002548 DESCRIPTION
2549 Send the event to decoder pipe. This is needed to generate the callbacks
2550 in decoder thread context.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002551
Arun Menon906de572013-06-18 17:01:40 -07002552 PARAMETERS
2553 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002554
Arun Menon906de572013-06-18 17:01:40 -07002555 RETURN VALUE
2556 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07002557
Arun Menon906de572013-06-18 17:01:40 -07002558 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07002559bool omx_vdec::post_event(unsigned int p1,
Arun Menon906de572013-06-18 17:01:40 -07002560 unsigned int p2,
2561 unsigned int id)
Shalaj Jain273b3e02012-06-22 19:08:03 -07002562{
Arun Menon906de572013-06-18 17:01:40 -07002563 bool bRet = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002564
2565
Arun Menon906de572013-06-18 17:01:40 -07002566 pthread_mutex_lock(&m_lock);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002567
Arun Menon906de572013-06-18 17:01:40 -07002568 if (id == m_fill_output_msg ||
2569 id == OMX_COMPONENT_GENERATE_FBD) {
2570 m_ftb_q.insert_entry(p1,p2,id);
2571 } else if (id == OMX_COMPONENT_GENERATE_ETB ||
2572 id == OMX_COMPONENT_GENERATE_EBD ||
2573 id == OMX_COMPONENT_GENERATE_ETB_ARBITRARY) {
2574 m_etb_q.insert_entry(p1,p2,id);
2575 } else {
2576 m_cmd_q.insert_entry(p1,p2,id);
2577 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002578
Arun Menon906de572013-06-18 17:01:40 -07002579 bRet = true;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002580 DEBUG_PRINT_LOW("Value of this pointer in post_event %p",this);
Arun Menon906de572013-06-18 17:01:40 -07002581 post_message(this, id);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002582
Arun Menon906de572013-06-18 17:01:40 -07002583 pthread_mutex_unlock(&m_lock);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002584
Arun Menon906de572013-06-18 17:01:40 -07002585 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002586}
2587
2588OMX_ERRORTYPE omx_vdec::get_supported_profile_level_for_1080p(OMX_VIDEO_PARAM_PROFILELEVELTYPE *profileLevelType)
2589{
Arun Menon906de572013-06-18 17:01:40 -07002590 OMX_ERRORTYPE eRet = OMX_ErrorNone;
2591 if (!profileLevelType)
2592 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002593
Arun Menon906de572013-06-18 17:01:40 -07002594 if (profileLevelType->nPortIndex == 0) {
2595 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc",OMX_MAX_STRINGNAME_SIZE)) {
2596 if (profileLevelType->nProfileIndex == 0) {
2597 profileLevelType->eProfile = OMX_VIDEO_AVCProfileBaseline;
2598 profileLevelType->eLevel = OMX_VIDEO_AVCLevel4;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002599
Arun Menon906de572013-06-18 17:01:40 -07002600 } else if (profileLevelType->nProfileIndex == 1) {
2601 profileLevelType->eProfile = OMX_VIDEO_AVCProfileMain;
2602 profileLevelType->eLevel = OMX_VIDEO_AVCLevel4;
2603 } else if (profileLevelType->nProfileIndex == 2) {
2604 profileLevelType->eProfile = OMX_VIDEO_AVCProfileHigh;
2605 profileLevelType->eLevel = OMX_VIDEO_AVCLevel4;
2606 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002607 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported nProfileIndex ret NoMore %lu",
Arun Menon906de572013-06-18 17:01:40 -07002608 profileLevelType->nProfileIndex);
2609 eRet = OMX_ErrorNoMore;
2610 }
2611 } else if ((!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.h263",OMX_MAX_STRINGNAME_SIZE))) {
2612 if (profileLevelType->nProfileIndex == 0) {
2613 profileLevelType->eProfile = OMX_VIDEO_H263ProfileBaseline;
2614 profileLevelType->eLevel = OMX_VIDEO_H263Level70;
2615 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002616 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported nProfileIndex ret NoMore %lu", profileLevelType->nProfileIndex);
Arun Menon906de572013-06-18 17:01:40 -07002617 eRet = OMX_ErrorNoMore;
2618 }
2619 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg4",OMX_MAX_STRINGNAME_SIZE)) {
2620 if (profileLevelType->nProfileIndex == 0) {
2621 profileLevelType->eProfile = OMX_VIDEO_MPEG4ProfileSimple;
2622 profileLevelType->eLevel = OMX_VIDEO_MPEG4Level5;
2623 } else if (profileLevelType->nProfileIndex == 1) {
2624 profileLevelType->eProfile = OMX_VIDEO_MPEG4ProfileAdvancedSimple;
2625 profileLevelType->eLevel = OMX_VIDEO_MPEG4Level5;
2626 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002627 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported nProfileIndex ret NoMore %lu", profileLevelType->nProfileIndex);
Arun Menon906de572013-06-18 17:01:40 -07002628 eRet = OMX_ErrorNoMore;
2629 }
2630 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8",OMX_MAX_STRINGNAME_SIZE)) {
2631 eRet = OMX_ErrorNoMore;
2632 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg2",OMX_MAX_STRINGNAME_SIZE)) {
2633 if (profileLevelType->nProfileIndex == 0) {
2634 profileLevelType->eProfile = OMX_VIDEO_MPEG2ProfileSimple;
2635 profileLevelType->eLevel = OMX_VIDEO_MPEG2LevelHL;
2636 } else if (profileLevelType->nProfileIndex == 1) {
2637 profileLevelType->eProfile = OMX_VIDEO_MPEG2ProfileMain;
2638 profileLevelType->eLevel = OMX_VIDEO_MPEG2LevelHL;
2639 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002640 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported nProfileIndex ret NoMore %lu", profileLevelType->nProfileIndex);
Arun Menon906de572013-06-18 17:01:40 -07002641 eRet = OMX_ErrorNoMore;
2642 }
2643 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002644 DEBUG_PRINT_ERROR("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported ret NoMore for codec: %s", drv_ctx.kind);
Arun Menon906de572013-06-18 17:01:40 -07002645 eRet = OMX_ErrorNoMore;
2646 }
2647 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002648 DEBUG_PRINT_ERROR("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported should be queries on Input port only %lu", profileLevelType->nPortIndex);
Arun Menon906de572013-06-18 17:01:40 -07002649 eRet = OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002650 }
Arun Menon906de572013-06-18 17:01:40 -07002651 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002652}
2653
2654/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07002655 FUNCTION
2656 omx_vdec::GetParameter
Shalaj Jain273b3e02012-06-22 19:08:03 -07002657
Arun Menon906de572013-06-18 17:01:40 -07002658 DESCRIPTION
2659 OMX Get Parameter method implementation
Shalaj Jain273b3e02012-06-22 19:08:03 -07002660
Arun Menon906de572013-06-18 17:01:40 -07002661 PARAMETERS
2662 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002663
Arun Menon906de572013-06-18 17:01:40 -07002664 RETURN VALUE
2665 Error None if successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002666
Arun Menon906de572013-06-18 17:01:40 -07002667 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07002668OMX_ERRORTYPE omx_vdec::get_parameter(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07002669 OMX_IN OMX_INDEXTYPE paramIndex,
2670 OMX_INOUT OMX_PTR paramData)
Shalaj Jain273b3e02012-06-22 19:08:03 -07002671{
2672 OMX_ERRORTYPE eRet = OMX_ErrorNone;
2673
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002674 DEBUG_PRINT_LOW("get_parameter:");
Arun Menon906de572013-06-18 17:01:40 -07002675 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002676 DEBUG_PRINT_ERROR("Get Param in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002677 return OMX_ErrorInvalidState;
2678 }
Arun Menon906de572013-06-18 17:01:40 -07002679 if (paramData == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002680 DEBUG_PRINT_LOW("Get Param in Invalid paramData");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002681 return OMX_ErrorBadParameter;
2682 }
Arun Menon906de572013-06-18 17:01:40 -07002683 switch ((unsigned long)paramIndex) {
2684 case OMX_IndexParamPortDefinition: {
2685 OMX_PARAM_PORTDEFINITIONTYPE *portDefn =
2686 (OMX_PARAM_PORTDEFINITIONTYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002687 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamPortDefinition");
Arun Menon906de572013-06-18 17:01:40 -07002688 eRet = update_portdef(portDefn);
2689 if (eRet == OMX_ErrorNone)
2690 m_port_def = *portDefn;
2691 break;
2692 }
2693 case OMX_IndexParamVideoInit: {
2694 OMX_PORT_PARAM_TYPE *portParamType =
2695 (OMX_PORT_PARAM_TYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002696 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoInit");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002697
Arun Menon906de572013-06-18 17:01:40 -07002698 portParamType->nVersion.nVersion = OMX_SPEC_VERSION;
2699 portParamType->nSize = sizeof(portParamType);
2700 portParamType->nPorts = 2;
2701 portParamType->nStartPortNumber = 0;
2702 break;
2703 }
2704 case OMX_IndexParamVideoPortFormat: {
2705 OMX_VIDEO_PARAM_PORTFORMATTYPE *portFmt =
2706 (OMX_VIDEO_PARAM_PORTFORMATTYPE *)paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002707 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoPortFormat");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002708
Arun Menon906de572013-06-18 17:01:40 -07002709 portFmt->nVersion.nVersion = OMX_SPEC_VERSION;
2710 portFmt->nSize = sizeof(portFmt);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002711
Arun Menon906de572013-06-18 17:01:40 -07002712 if (0 == portFmt->nPortIndex) {
2713 if (0 == portFmt->nIndex) {
2714 portFmt->eColorFormat = OMX_COLOR_FormatUnused;
2715 portFmt->eCompressionFormat = eCompressionFormat;
2716 } else {
2717 DEBUG_PRINT_ERROR("get_parameter: OMX_IndexParamVideoPortFormat:"\
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002718 " NoMore compression formats");
Arun Menon906de572013-06-18 17:01:40 -07002719 eRet = OMX_ErrorNoMore;
2720 }
2721 } else if (1 == portFmt->nPortIndex) {
2722 portFmt->eCompressionFormat = OMX_VIDEO_CodingUnused;
Praveen Chavandb7776f2014-02-06 18:17:25 -08002723 //On Android, we default to standard YUV formats for non-surface use-cases
2724 //where apps prefer known color formats.
2725 OMX_COLOR_FORMATTYPE formatsNonSurfaceMode[] = {
2726 [0] = OMX_COLOR_FormatYUV420SemiPlanar,
2727 [1] = OMX_COLOR_FormatYUV420Planar,
2728 [2] = (OMX_COLOR_FORMATTYPE)QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m,
2729 };
2730 //for surface mode (normal playback), advertise native/accelerated formats first
2731 OMX_COLOR_FORMATTYPE formatsDefault[] = {
2732 [0] = (OMX_COLOR_FORMATTYPE)QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m,
2733 [1] = OMX_COLOR_FormatYUV420Planar,
2734 [2] = OMX_COLOR_FormatYUV420SemiPlanar,
2735 };
2736#if _ANDROID_
2737 //Distinguish non-surface mode from normal playback use-case based on
2738 //usage hinted via "OMX.google.android.index.useAndroidNativeBuffer2"
2739 OMX_COLOR_FORMATTYPE *colorFormats =
2740 m_enable_android_native_buffers ? formatsDefault : formatsNonSurfaceMode;
2741 OMX_U32 maxIndex =
2742 m_enable_android_native_buffers ? sizeof(formatsDefault) : sizeof(formatsNonSurfaceMode);
2743 maxIndex /= sizeof(OMX_COLOR_FORMATTYPE);
2744#else
2745 OMX_COLOR_FORMATTYPE *colorFormats = formatsDefault;
2746 OMX_U32 maxIndex = sizeof(formatsDefault) / sizeof(OMX_COLOR_FORMATTYPE);
2747#endif
Shalaj Jain273b3e02012-06-22 19:08:03 -07002748
Praveen Chavandb7776f2014-02-06 18:17:25 -08002749 if (portFmt->nIndex < maxIndex) {
2750 portFmt->eColorFormat = colorFormats[portFmt->nIndex];
2751 } else {
2752 eRet = OMX_ErrorNoMore;
Arun Menon906de572013-06-18 17:01:40 -07002753 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoPortFormat:"\
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002754 " NoMore Color formats");
Arun Menon906de572013-06-18 17:01:40 -07002755 }
Praveen Chavandb7776f2014-02-06 18:17:25 -08002756 DEBUG_PRINT_HIGH("returning color-format: 0x%x", portFmt->eColorFormat);
Arun Menon906de572013-06-18 17:01:40 -07002757 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002758 DEBUG_PRINT_ERROR("get_parameter: Bad port index %d",
Arun Menon906de572013-06-18 17:01:40 -07002759 (int)portFmt->nPortIndex);
2760 eRet = OMX_ErrorBadPortIndex;
2761 }
2762 break;
2763 }
2764 /*Component should support this port definition*/
2765 case OMX_IndexParamAudioInit: {
2766 OMX_PORT_PARAM_TYPE *audioPortParamType =
2767 (OMX_PORT_PARAM_TYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002768 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamAudioInit");
Arun Menon906de572013-06-18 17:01:40 -07002769 audioPortParamType->nVersion.nVersion = OMX_SPEC_VERSION;
2770 audioPortParamType->nSize = sizeof(audioPortParamType);
2771 audioPortParamType->nPorts = 0;
2772 audioPortParamType->nStartPortNumber = 0;
2773 break;
2774 }
2775 /*Component should support this port definition*/
2776 case OMX_IndexParamImageInit: {
2777 OMX_PORT_PARAM_TYPE *imagePortParamType =
2778 (OMX_PORT_PARAM_TYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002779 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamImageInit");
Arun Menon906de572013-06-18 17:01:40 -07002780 imagePortParamType->nVersion.nVersion = OMX_SPEC_VERSION;
2781 imagePortParamType->nSize = sizeof(imagePortParamType);
2782 imagePortParamType->nPorts = 0;
2783 imagePortParamType->nStartPortNumber = 0;
2784 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002785
Arun Menon906de572013-06-18 17:01:40 -07002786 }
2787 /*Component should support this port definition*/
2788 case OMX_IndexParamOtherInit: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002789 DEBUG_PRINT_ERROR("get_parameter: OMX_IndexParamOtherInit %08x",
Arun Menon906de572013-06-18 17:01:40 -07002790 paramIndex);
2791 eRet =OMX_ErrorUnsupportedIndex;
2792 break;
2793 }
2794 case OMX_IndexParamStandardComponentRole: {
2795 OMX_PARAM_COMPONENTROLETYPE *comp_role;
2796 comp_role = (OMX_PARAM_COMPONENTROLETYPE *) paramData;
2797 comp_role->nVersion.nVersion = OMX_SPEC_VERSION;
2798 comp_role->nSize = sizeof(*comp_role);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002799
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002800 DEBUG_PRINT_LOW("Getparameter: OMX_IndexParamStandardComponentRole %d",
Arun Menon906de572013-06-18 17:01:40 -07002801 paramIndex);
2802 strlcpy((char*)comp_role->cRole,(const char*)m_cRole,
2803 OMX_MAX_STRINGNAME_SIZE);
2804 break;
2805 }
2806 /* Added for parameter test */
2807 case OMX_IndexParamPriorityMgmt: {
Shalaj Jain273b3e02012-06-22 19:08:03 -07002808
Arun Menon906de572013-06-18 17:01:40 -07002809 OMX_PRIORITYMGMTTYPE *priorityMgmType =
2810 (OMX_PRIORITYMGMTTYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002811 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamPriorityMgmt");
Arun Menon906de572013-06-18 17:01:40 -07002812 priorityMgmType->nVersion.nVersion = OMX_SPEC_VERSION;
2813 priorityMgmType->nSize = sizeof(priorityMgmType);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002814
Arun Menon906de572013-06-18 17:01:40 -07002815 break;
2816 }
2817 /* Added for parameter test */
2818 case OMX_IndexParamCompBufferSupplier: {
2819 OMX_PARAM_BUFFERSUPPLIERTYPE *bufferSupplierType =
2820 (OMX_PARAM_BUFFERSUPPLIERTYPE*) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002821 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamCompBufferSupplier");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002822
Arun Menon906de572013-06-18 17:01:40 -07002823 bufferSupplierType->nSize = sizeof(bufferSupplierType);
2824 bufferSupplierType->nVersion.nVersion = OMX_SPEC_VERSION;
2825 if (0 == bufferSupplierType->nPortIndex)
2826 bufferSupplierType->nPortIndex = OMX_BufferSupplyUnspecified;
2827 else if (1 == bufferSupplierType->nPortIndex)
2828 bufferSupplierType->nPortIndex = OMX_BufferSupplyUnspecified;
2829 else
2830 eRet = OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002831
2832
Arun Menon906de572013-06-18 17:01:40 -07002833 break;
2834 }
2835 case OMX_IndexParamVideoAvc: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002836 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoAvc %08x",
Arun Menon906de572013-06-18 17:01:40 -07002837 paramIndex);
2838 break;
2839 }
2840 case OMX_IndexParamVideoH263: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002841 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoH263 %08x",
Arun Menon906de572013-06-18 17:01:40 -07002842 paramIndex);
2843 break;
2844 }
2845 case OMX_IndexParamVideoMpeg4: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002846 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoMpeg4 %08x",
Arun Menon906de572013-06-18 17:01:40 -07002847 paramIndex);
2848 break;
2849 }
2850 case OMX_IndexParamVideoMpeg2: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002851 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoMpeg2 %08x",
Arun Menon906de572013-06-18 17:01:40 -07002852 paramIndex);
2853 break;
2854 }
2855 case OMX_IndexParamVideoProfileLevelQuerySupported: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002856 DEBUG_PRINT_LOW("get_parameter: OMX_IndexParamVideoProfileLevelQuerySupported %08x", paramIndex);
Arun Menon906de572013-06-18 17:01:40 -07002857 OMX_VIDEO_PARAM_PROFILELEVELTYPE *profileLevelType =
2858 (OMX_VIDEO_PARAM_PROFILELEVELTYPE *)paramData;
2859 eRet = get_supported_profile_level_for_1080p(profileLevelType);
2860 break;
2861 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07002862#if defined (_ANDROID_HONEYCOMB_) || defined (_ANDROID_ICS_)
Arun Menon906de572013-06-18 17:01:40 -07002863 case OMX_GoogleAndroidIndexGetAndroidNativeBufferUsage: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002864 DEBUG_PRINT_LOW("get_parameter: OMX_GoogleAndroidIndexGetAndroidNativeBufferUsage");
Arun Menon906de572013-06-18 17:01:40 -07002865 GetAndroidNativeBufferUsageParams* nativeBuffersUsage = (GetAndroidNativeBufferUsageParams *) paramData;
2866 if (nativeBuffersUsage->nPortIndex == OMX_CORE_OUTPUT_PORT_INDEX) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07002867
Arun Menon906de572013-06-18 17:01:40 -07002868 if (secure_mode) {
2869 nativeBuffersUsage->nUsage = (GRALLOC_USAGE_PRIVATE_MM_HEAP | GRALLOC_USAGE_PROTECTED |
2870 GRALLOC_USAGE_PRIVATE_UNCACHED);
2871 } else {
2872 nativeBuffersUsage->nUsage =
2873 (GRALLOC_USAGE_PRIVATE_IOMMU_HEAP |
2874 GRALLOC_USAGE_PRIVATE_UNCACHED);
2875 }
2876 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002877 DEBUG_PRINT_HIGH("get_parameter: OMX_GoogleAndroidIndexGetAndroidNativeBufferUsage failed!");
Arun Menon906de572013-06-18 17:01:40 -07002878 eRet = OMX_ErrorBadParameter;
2879 }
2880 }
2881 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002882#endif
2883
Arun Menon906de572013-06-18 17:01:40 -07002884 default: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002885 DEBUG_PRINT_ERROR("get_parameter: unknown param %08x", paramIndex);
Arun Menon906de572013-06-18 17:01:40 -07002886 eRet =OMX_ErrorUnsupportedIndex;
2887 }
2888
Shalaj Jain273b3e02012-06-22 19:08:03 -07002889 }
2890
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002891 DEBUG_PRINT_LOW("get_parameter returning WxH(%d x %d) SxSH(%d x %d)",
Arun Menon906de572013-06-18 17:01:40 -07002892 drv_ctx.video_resolution.frame_width,
2893 drv_ctx.video_resolution.frame_height,
2894 drv_ctx.video_resolution.stride,
2895 drv_ctx.video_resolution.scan_lines);
Shalaj Jain273b3e02012-06-22 19:08:03 -07002896
Arun Menon906de572013-06-18 17:01:40 -07002897 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002898}
2899
2900#if defined (_ANDROID_HONEYCOMB_) || defined (_ANDROID_ICS_)
2901OMX_ERRORTYPE omx_vdec::use_android_native_buffer(OMX_IN OMX_HANDLETYPE hComp, OMX_PTR data)
2902{
2903 DEBUG_PRINT_LOW("Inside use_android_native_buffer");
2904 OMX_ERRORTYPE eRet = OMX_ErrorNone;
2905 UseAndroidNativeBufferParams *params = (UseAndroidNativeBufferParams *)data;
2906
Arun Menon906de572013-06-18 17:01:40 -07002907 if ((params == NULL) ||
2908 (params->nativeBuffer == NULL) ||
2909 (params->nativeBuffer->handle == NULL) ||
2910 !m_enable_android_native_buffers)
Shalaj Jain273b3e02012-06-22 19:08:03 -07002911 return OMX_ErrorBadParameter;
2912 m_use_android_native_buffers = OMX_TRUE;
2913 sp<android_native_buffer_t> nBuf = params->nativeBuffer;
2914 private_handle_t *handle = (private_handle_t *)nBuf->handle;
Arun Menon906de572013-06-18 17:01:40 -07002915 if (OMX_CORE_OUTPUT_PORT_INDEX == params->nPortIndex) { //android native buffers can be used only on Output port
Shalaj Jain273b3e02012-06-22 19:08:03 -07002916 OMX_U8 *buffer = NULL;
Arun Menon906de572013-06-18 17:01:40 -07002917 if (!secure_mode) {
2918 buffer = (OMX_U8*)mmap(0, handle->size,
Shalaj Jain273b3e02012-06-22 19:08:03 -07002919 PROT_READ|PROT_WRITE, MAP_SHARED, handle->fd, 0);
Arun Menon906de572013-06-18 17:01:40 -07002920 if (buffer == MAP_FAILED) {
2921 DEBUG_PRINT_ERROR("Failed to mmap pmem with fd = %d, size = %d", handle->fd, handle->size);
2922 return OMX_ErrorInsufficientResources;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002923 }
2924 }
2925 eRet = use_buffer(hComp,params->bufferHeader,params->nPortIndex,data,handle->size,buffer);
2926 } else {
2927 eRet = OMX_ErrorBadParameter;
2928 }
2929 return eRet;
2930}
2931#endif
Praveen Chavancf924182013-12-06 23:16:23 -08002932
2933OMX_ERRORTYPE omx_vdec::enable_smoothstreaming() {
2934 struct v4l2_control control;
2935 struct v4l2_format fmt;
2936 control.id = V4L2_CID_MPEG_VIDC_VIDEO_CONTINUE_DATA_TRANSFER;
2937 control.value = 1;
2938 int rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL,&control);
2939 if (rc < 0) {
2940 DEBUG_PRINT_ERROR("Failed to enable Smooth Streaming on driver.");
2941 return OMX_ErrorHardware;
2942 }
2943 m_smoothstreaming_mode = true;
2944 return OMX_ErrorNone;
2945}
2946
Shalaj Jain273b3e02012-06-22 19:08:03 -07002947/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07002948 FUNCTION
2949 omx_vdec::Setparameter
Shalaj Jain273b3e02012-06-22 19:08:03 -07002950
Arun Menon906de572013-06-18 17:01:40 -07002951 DESCRIPTION
2952 OMX Set Parameter method implementation.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002953
Arun Menon906de572013-06-18 17:01:40 -07002954 PARAMETERS
2955 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002956
Arun Menon906de572013-06-18 17:01:40 -07002957 RETURN VALUE
2958 OMX Error None if successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07002959
Arun Menon906de572013-06-18 17:01:40 -07002960 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07002961OMX_ERRORTYPE omx_vdec::set_parameter(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07002962 OMX_IN OMX_INDEXTYPE paramIndex,
2963 OMX_IN OMX_PTR paramData)
Shalaj Jain273b3e02012-06-22 19:08:03 -07002964{
2965 OMX_ERRORTYPE eRet = OMX_ErrorNone;
Praneeth Paladugu226667c2012-09-12 16:42:30 -07002966 int ret=0;
2967 struct v4l2_format fmt;
Arun Menon906de572013-06-18 17:01:40 -07002968 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002969 DEBUG_PRINT_ERROR("Set Param in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002970 return OMX_ErrorInvalidState;
2971 }
Arun Menon906de572013-06-18 17:01:40 -07002972 if (paramData == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002973 DEBUG_PRINT_ERROR("Get Param in Invalid paramData");
Arun Menon906de572013-06-18 17:01:40 -07002974 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07002975 }
Arun Menon906de572013-06-18 17:01:40 -07002976 if ((m_state != OMX_StateLoaded) &&
2977 BITMASK_ABSENT(&m_flags,OMX_COMPONENT_OUTPUT_ENABLE_PENDING) &&
2978 (m_out_bEnabled == OMX_TRUE) &&
2979 BITMASK_ABSENT(&m_flags, OMX_COMPONENT_INPUT_ENABLE_PENDING) &&
2980 (m_inp_bEnabled == OMX_TRUE)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002981 DEBUG_PRINT_ERROR("Set Param in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07002982 return OMX_ErrorIncorrectStateOperation;
2983 }
Arun Menon906de572013-06-18 17:01:40 -07002984 switch ((unsigned long)paramIndex) {
2985 case OMX_IndexParamPortDefinition: {
2986 OMX_PARAM_PORTDEFINITIONTYPE *portDefn;
2987 portDefn = (OMX_PARAM_PORTDEFINITIONTYPE *) paramData;
2988 //TODO: Check if any allocate buffer/use buffer/useNativeBuffer has
2989 //been called.
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002990 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPortDefinition H= %d, W = %d",
Arun Menon906de572013-06-18 17:01:40 -07002991 (int)portDefn->format.video.nFrameHeight,
2992 (int)portDefn->format.video.nFrameWidth);
2993 if (OMX_DirOutput == portDefn->eDir) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07002994 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPortDefinition OP port");
Arun Menon906de572013-06-18 17:01:40 -07002995 m_display_id = portDefn->format.video.pNativeWindow;
2996 unsigned int buffer_size;
Praveen Chavane78460c2013-12-06 23:16:04 -08002997 /* update output port resolution with client supplied dimensions
2998 in case scaling is enabled, else it follows input resolution set
2999 */
3000 if (is_down_scalar_enabled) {
3001 DEBUG_PRINT_LOW("\n SetParam OP: WxH(%lu x %lu)\n",
Praneeth Paladugu42306bb2013-08-27 22:01:28 -07003002 portDefn->format.video.nFrameWidth,
3003 portDefn->format.video.nFrameHeight);
3004 if (portDefn->format.video.nFrameHeight != 0x0 &&
3005 portDefn->format.video.nFrameWidth != 0x0) {
3006 update_resolution(portDefn->format.video.nFrameWidth,
3007 portDefn->format.video.nFrameHeight,
3008 portDefn->format.video.nFrameWidth,
3009 portDefn->format.video.nFrameHeight);
3010 eRet = is_video_session_supported();
3011 if (eRet)
3012 break;
3013 fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
3014 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
3015 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
3016 fmt.fmt.pix_mp.pixelformat = capture_capability;
3017 DEBUG_PRINT_LOW("\n fmt.fmt.pix_mp.height = %d , fmt.fmt.pix_mp.width = %d \n",fmt.fmt.pix_mp.height,fmt.fmt.pix_mp.width);
3018 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
3019 if (ret) {
3020 DEBUG_PRINT_ERROR("\n Set Resolution failed");
3021 eRet = OMX_ErrorUnsupportedSetting;
3022 } else
3023 eRet = get_buffer_req(&drv_ctx.op_buf);
3024 }
Praveen Chavane78460c2013-12-06 23:16:04 -08003025 }
Arun Menon906de572013-06-18 17:01:40 -07003026 if (!client_buffers.get_buffer_req(buffer_size)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003027 DEBUG_PRINT_ERROR("Error in getting buffer requirements");
Arun Menon906de572013-06-18 17:01:40 -07003028 eRet = OMX_ErrorBadParameter;
3029 } else {
3030 if ( portDefn->nBufferCountActual >= drv_ctx.op_buf.mincount &&
3031 portDefn->nBufferSize >= drv_ctx.op_buf.buffer_size ) {
3032 drv_ctx.op_buf.actualcount = portDefn->nBufferCountActual;
3033 drv_ctx.op_buf.buffer_size = portDefn->nBufferSize;
3034 drv_ctx.extradata_info.count = drv_ctx.op_buf.actualcount;
3035 drv_ctx.extradata_info.size = drv_ctx.extradata_info.count *
3036 drv_ctx.extradata_info.buffer_size;
3037 eRet = set_buffer_req(&drv_ctx.op_buf);
3038 if (eRet == OMX_ErrorNone)
3039 m_port_def = *portDefn;
3040 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003041 DEBUG_PRINT_ERROR("ERROR: OP Requirements(#%d: %u) Requested(#%lu: %lu)",
Arun Menon906de572013-06-18 17:01:40 -07003042 drv_ctx.op_buf.mincount, drv_ctx.op_buf.buffer_size,
3043 portDefn->nBufferCountActual, portDefn->nBufferSize);
3044 eRet = OMX_ErrorBadParameter;
3045 }
3046 }
3047 } else if (OMX_DirInput == portDefn->eDir) {
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08003048 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPortDefinition IP port");
Arun Menon906de572013-06-18 17:01:40 -07003049 bool port_format_changed = false;
3050 if ((portDefn->format.video.xFramerate >> 16) > 0 &&
3051 (portDefn->format.video.xFramerate >> 16) <= MAX_SUPPORTED_FPS) {
3052 // Frame rate only should be set if this is a "known value" or to
3053 // activate ts prediction logic (arbitrary mode only) sending input
3054 // timestamps with max value (LLONG_MAX).
3055 DEBUG_PRINT_HIGH("set_parameter: frame rate set by omx client : %lu",
3056 portDefn->format.video.xFramerate >> 16);
3057 Q16ToFraction(portDefn->format.video.xFramerate, drv_ctx.frame_rate.fps_numerator,
3058 drv_ctx.frame_rate.fps_denominator);
3059 if (!drv_ctx.frame_rate.fps_numerator) {
3060 DEBUG_PRINT_ERROR("Numerator is zero setting to 30");
3061 drv_ctx.frame_rate.fps_numerator = 30;
3062 }
3063 if (drv_ctx.frame_rate.fps_denominator)
3064 drv_ctx.frame_rate.fps_numerator = (int)
3065 drv_ctx.frame_rate.fps_numerator / drv_ctx.frame_rate.fps_denominator;
3066 drv_ctx.frame_rate.fps_denominator = 1;
3067 frm_int = drv_ctx.frame_rate.fps_denominator * 1e6 /
3068 drv_ctx.frame_rate.fps_numerator;
3069 DEBUG_PRINT_LOW("set_parameter: frm_int(%lu) fps(%.2f)",
3070 frm_int, drv_ctx.frame_rate.fps_numerator /
3071 (float)drv_ctx.frame_rate.fps_denominator);
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08003072
3073 struct v4l2_outputparm oparm;
3074 /*XXX: we're providing timing info as seconds per frame rather than frames
3075 * per second.*/
3076 oparm.timeperframe.numerator = drv_ctx.frame_rate.fps_denominator;
3077 oparm.timeperframe.denominator = drv_ctx.frame_rate.fps_numerator;
3078
3079 struct v4l2_streamparm sparm;
3080 sparm.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
3081 sparm.parm.output = oparm;
3082 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_PARM, &sparm)) {
3083 DEBUG_PRINT_ERROR("Unable to convey fps info to driver, performance might be affected");
3084 eRet = OMX_ErrorHardware;
3085 break;
3086 }
Arun Menon906de572013-06-18 17:01:40 -07003087 }
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08003088
Arun Menon906de572013-06-18 17:01:40 -07003089 if (drv_ctx.video_resolution.frame_height !=
3090 portDefn->format.video.nFrameHeight ||
3091 drv_ctx.video_resolution.frame_width !=
3092 portDefn->format.video.nFrameWidth) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003093 DEBUG_PRINT_LOW("SetParam IP: WxH(%lu x %lu)",
Arun Menon906de572013-06-18 17:01:40 -07003094 portDefn->format.video.nFrameWidth,
3095 portDefn->format.video.nFrameHeight);
3096 port_format_changed = true;
Praveen Chavancf924182013-12-06 23:16:23 -08003097 OMX_U32 frameWidth = portDefn->format.video.nFrameWidth;
3098 OMX_U32 frameHeight = portDefn->format.video.nFrameHeight;
3099 if (frameHeight != 0x0 && frameWidth != 0x0) {
3100 if (m_smoothstreaming_mode &&
3101 ((frameWidth * frameHeight) <
3102 (m_smoothstreaming_width * m_smoothstreaming_height))) {
3103 frameWidth = m_smoothstreaming_width;
3104 frameHeight = m_smoothstreaming_height;
3105 DEBUG_PRINT_LOW("NOTE: Setting resolution %lu x %lu for adaptive-playback/smooth-streaming",
3106 frameWidth, frameHeight);
3107 }
3108 update_resolution(frameWidth, frameHeight,
3109 frameWidth, frameHeight);
Arun Menon906de572013-06-18 17:01:40 -07003110 eRet = is_video_session_supported();
3111 if (eRet)
3112 break;
3113 fmt.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
3114 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
3115 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
3116 fmt.fmt.pix_mp.pixelformat = output_capability;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003117 DEBUG_PRINT_LOW("fmt.fmt.pix_mp.height = %d , fmt.fmt.pix_mp.width = %d",fmt.fmt.pix_mp.height,fmt.fmt.pix_mp.width);
Arun Menon906de572013-06-18 17:01:40 -07003118 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
3119 if (ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003120 DEBUG_PRINT_ERROR("Set Resolution failed");
Arun Menon906de572013-06-18 17:01:40 -07003121 eRet = OMX_ErrorUnsupportedSetting;
3122 } else
3123 eRet = get_buffer_req(&drv_ctx.op_buf);
3124 }
3125 }
3126 if (portDefn->nBufferCountActual >= drv_ctx.ip_buf.mincount
3127 || portDefn->nBufferSize != drv_ctx.ip_buf.buffer_size) {
3128 port_format_changed = true;
3129 vdec_allocatorproperty *buffer_prop = &drv_ctx.ip_buf;
3130 drv_ctx.ip_buf.actualcount = portDefn->nBufferCountActual;
3131 drv_ctx.ip_buf.buffer_size = (portDefn->nBufferSize + buffer_prop->alignment - 1) &
3132 (~(buffer_prop->alignment - 1));
3133 eRet = set_buffer_req(buffer_prop);
3134 }
3135 if (false == port_format_changed) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003136 DEBUG_PRINT_ERROR("ERROR: IP Requirements(#%d: %u) Requested(#%lu: %lu)",
Arun Menon906de572013-06-18 17:01:40 -07003137 drv_ctx.ip_buf.mincount, drv_ctx.ip_buf.buffer_size,
3138 portDefn->nBufferCountActual, portDefn->nBufferSize);
3139 eRet = OMX_ErrorBadParameter;
3140 }
3141 } else if (portDefn->eDir == OMX_DirMax) {
3142 DEBUG_PRINT_ERROR(" Set_parameter: Bad Port idx %d",
3143 (int)portDefn->nPortIndex);
3144 eRet = OMX_ErrorBadPortIndex;
3145 }
3146 }
3147 break;
3148 case OMX_IndexParamVideoPortFormat: {
3149 OMX_VIDEO_PARAM_PORTFORMATTYPE *portFmt =
3150 (OMX_VIDEO_PARAM_PORTFORMATTYPE *)paramData;
3151 int ret=0;
3152 struct v4l2_format fmt;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003153 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoPortFormat %d",
Arun Menon906de572013-06-18 17:01:40 -07003154 portFmt->eColorFormat);
Shalaj Jain273b3e02012-06-22 19:08:03 -07003155
Arun Menon906de572013-06-18 17:01:40 -07003156 if (1 == portFmt->nPortIndex) {
3157 fmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
3158 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
3159 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
3160 fmt.fmt.pix_mp.pixelformat = capture_capability;
3161 enum vdec_output_fromat op_format;
3162 if ((portFmt->eColorFormat == (OMX_COLOR_FORMATTYPE)
3163 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m) ||
Praveen Chavandb7776f2014-02-06 18:17:25 -08003164 (portFmt->eColorFormat == OMX_COLOR_FormatYUV420Planar) ||
3165 (portFmt->eColorFormat == OMX_COLOR_FormatYUV420SemiPlanar))
Arun Menon906de572013-06-18 17:01:40 -07003166 op_format = (enum vdec_output_fromat)VDEC_YUV_FORMAT_NV12;
Arun Menon906de572013-06-18 17:01:40 -07003167 else
3168 eRet = OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003169
Arun Menon906de572013-06-18 17:01:40 -07003170 if (eRet == OMX_ErrorNone) {
3171 drv_ctx.output_format = op_format;
3172 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
3173 if (ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003174 DEBUG_PRINT_ERROR("Set output format failed");
Arun Menon906de572013-06-18 17:01:40 -07003175 eRet = OMX_ErrorUnsupportedSetting;
3176 /*TODO: How to handle this case */
3177 } else {
3178 eRet = get_buffer_req(&drv_ctx.op_buf);
3179 }
3180 }
3181 if (eRet == OMX_ErrorNone) {
3182 if (!client_buffers.set_color_format(portFmt->eColorFormat)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003183 DEBUG_PRINT_ERROR("Set color format failed");
Arun Menon906de572013-06-18 17:01:40 -07003184 eRet = OMX_ErrorBadParameter;
3185 }
3186 }
3187 }
3188 }
3189 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003190
Arun Menon906de572013-06-18 17:01:40 -07003191 case OMX_QcomIndexPortDefn: {
3192 OMX_QCOM_PARAM_PORTDEFINITIONTYPE *portFmt =
3193 (OMX_QCOM_PARAM_PORTDEFINITIONTYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003194 DEBUG_PRINT_LOW("set_parameter: OMX_IndexQcomParamPortDefinitionType %lu",
Arun Menon906de572013-06-18 17:01:40 -07003195 portFmt->nFramePackingFormat);
Shalaj Jain273b3e02012-06-22 19:08:03 -07003196
Arun Menon906de572013-06-18 17:01:40 -07003197 /* Input port */
3198 if (portFmt->nPortIndex == 0) {
3199 if (portFmt->nFramePackingFormat == OMX_QCOM_FramePacking_Arbitrary) {
3200 if (secure_mode) {
3201 arbitrary_bytes = false;
3202 DEBUG_PRINT_ERROR("setparameter: cannot set to arbitary bytes mode in secure session");
3203 eRet = OMX_ErrorUnsupportedSetting;
3204 } else {
3205 arbitrary_bytes = true;
3206 }
3207 } else if (portFmt->nFramePackingFormat ==
3208 OMX_QCOM_FramePacking_OnlyOneCompleteFrame) {
3209 arbitrary_bytes = false;
3210 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003211 DEBUG_PRINT_ERROR("Setparameter: unknown FramePacking format %lu",
Arun Menon906de572013-06-18 17:01:40 -07003212 portFmt->nFramePackingFormat);
3213 eRet = OMX_ErrorUnsupportedSetting;
3214 }
3215 } else if (portFmt->nPortIndex == OMX_CORE_OUTPUT_PORT_INDEX) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003216 DEBUG_PRINT_HIGH("set_parameter: OMX_IndexQcomParamPortDefinitionType OP Port");
Arun Menon906de572013-06-18 17:01:40 -07003217 if ( (portFmt->nMemRegion > OMX_QCOM_MemRegionInvalid &&
3218 portFmt->nMemRegion < OMX_QCOM_MemRegionMax) &&
3219 portFmt->nCacheAttr == OMX_QCOM_CacheAttrNone) {
3220 m_out_mem_region_smi = OMX_TRUE;
3221 if ((m_out_mem_region_smi && m_out_pvt_entry_pmem)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003222 DEBUG_PRINT_HIGH("set_parameter: OMX_IndexQcomParamPortDefinitionType OP Port: out pmem set");
Arun Menon906de572013-06-18 17:01:40 -07003223 m_use_output_pmem = OMX_TRUE;
3224 }
3225 }
3226 }
3227 }
3228 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003229
Arun Menon906de572013-06-18 17:01:40 -07003230 case OMX_IndexParamStandardComponentRole: {
3231 OMX_PARAM_COMPONENTROLETYPE *comp_role;
3232 comp_role = (OMX_PARAM_COMPONENTROLETYPE *) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003233 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamStandardComponentRole %s",
Arun Menon906de572013-06-18 17:01:40 -07003234 comp_role->cRole);
Shalaj Jain273b3e02012-06-22 19:08:03 -07003235
Arun Menon906de572013-06-18 17:01:40 -07003236 if ((m_state == OMX_StateLoaded)&&
3237 !BITMASK_PRESENT(&m_flags,OMX_COMPONENT_IDLE_PENDING)) {
3238 DEBUG_PRINT_LOW("Set Parameter called in valid state");
3239 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003240 DEBUG_PRINT_ERROR("Set Parameter called in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07003241 return OMX_ErrorIncorrectStateOperation;
3242 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07003243
Arun Menon906de572013-06-18 17:01:40 -07003244 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc",OMX_MAX_STRINGNAME_SIZE)) {
3245 if (!strncmp((char*)comp_role->cRole,"video_decoder.avc",OMX_MAX_STRINGNAME_SIZE)) {
3246 strlcpy((char*)m_cRole,"video_decoder.avc",OMX_MAX_STRINGNAME_SIZE);
3247 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003248 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003249 eRet =OMX_ErrorUnsupportedSetting;
3250 }
3251 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg4",OMX_MAX_STRINGNAME_SIZE)) {
3252 if (!strncmp((const char*)comp_role->cRole,"video_decoder.mpeg4",OMX_MAX_STRINGNAME_SIZE)) {
3253 strlcpy((char*)m_cRole,"video_decoder.mpeg4",OMX_MAX_STRINGNAME_SIZE);
3254 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003255 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003256 eRet = OMX_ErrorUnsupportedSetting;
3257 }
3258 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.h263",OMX_MAX_STRINGNAME_SIZE)) {
3259 if (!strncmp((const char*)comp_role->cRole,"video_decoder.h263",OMX_MAX_STRINGNAME_SIZE)) {
3260 strlcpy((char*)m_cRole,"video_decoder.h263",OMX_MAX_STRINGNAME_SIZE);
3261 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003262 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003263 eRet =OMX_ErrorUnsupportedSetting;
3264 }
3265 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg2",OMX_MAX_STRINGNAME_SIZE)) {
3266 if (!strncmp((const char*)comp_role->cRole,"video_decoder.mpeg2",OMX_MAX_STRINGNAME_SIZE)) {
3267 strlcpy((char*)m_cRole,"video_decoder.mpeg2",OMX_MAX_STRINGNAME_SIZE);
3268 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003269 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003270 eRet = OMX_ErrorUnsupportedSetting;
3271 }
3272 } else if ((!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx",OMX_MAX_STRINGNAME_SIZE)) ||
3273 (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx311",OMX_MAX_STRINGNAME_SIZE))
3274 ) {
3275 if (!strncmp((const char*)comp_role->cRole,"video_decoder.divx",OMX_MAX_STRINGNAME_SIZE)) {
3276 strlcpy((char*)m_cRole,"video_decoder.divx",OMX_MAX_STRINGNAME_SIZE);
3277 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003278 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003279 eRet =OMX_ErrorUnsupportedSetting;
3280 }
3281 } else if ( (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vc1",OMX_MAX_STRINGNAME_SIZE)) ||
3282 (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.wmv",OMX_MAX_STRINGNAME_SIZE))
3283 ) {
3284 if (!strncmp((const char*)comp_role->cRole,"video_decoder.vc1",OMX_MAX_STRINGNAME_SIZE)) {
3285 strlcpy((char*)m_cRole,"video_decoder.vc1",OMX_MAX_STRINGNAME_SIZE);
3286 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003287 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003288 eRet =OMX_ErrorUnsupportedSetting;
3289 }
3290 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8",OMX_MAX_STRINGNAME_SIZE)) {
3291 if (!strncmp((const char*)comp_role->cRole,"video_decoder.vp8",OMX_MAX_STRINGNAME_SIZE) ||
3292 (!strncmp((const char*)comp_role->cRole,"video_decoder.vpx",OMX_MAX_STRINGNAME_SIZE))) {
3293 strlcpy((char*)m_cRole,"video_decoder.vp8",OMX_MAX_STRINGNAME_SIZE);
3294 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003295 DEBUG_PRINT_ERROR("Setparameter: unknown Index %s", comp_role->cRole);
Arun Menon906de572013-06-18 17:01:40 -07003296 eRet = OMX_ErrorUnsupportedSetting;
3297 }
3298 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003299 DEBUG_PRINT_ERROR("Setparameter: unknown param %s", drv_ctx.kind);
Arun Menon906de572013-06-18 17:01:40 -07003300 eRet = OMX_ErrorInvalidComponentName;
3301 }
3302 break;
3303 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07003304
Arun Menon906de572013-06-18 17:01:40 -07003305 case OMX_IndexParamPriorityMgmt: {
3306 if (m_state != OMX_StateLoaded) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003307 DEBUG_PRINT_ERROR("Set Parameter called in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07003308 return OMX_ErrorIncorrectStateOperation;
3309 }
3310 OMX_PRIORITYMGMTTYPE *priorityMgmtype = (OMX_PRIORITYMGMTTYPE*) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003311 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamPriorityMgmt %lu",
Arun Menon906de572013-06-18 17:01:40 -07003312 priorityMgmtype->nGroupID);
Shalaj Jain273b3e02012-06-22 19:08:03 -07003313
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003314 DEBUG_PRINT_LOW("set_parameter: priorityMgmtype %lu",
Arun Menon906de572013-06-18 17:01:40 -07003315 priorityMgmtype->nGroupPriority);
Shalaj Jain273b3e02012-06-22 19:08:03 -07003316
Arun Menon906de572013-06-18 17:01:40 -07003317 m_priority_mgm.nGroupID = priorityMgmtype->nGroupID;
3318 m_priority_mgm.nGroupPriority = priorityMgmtype->nGroupPriority;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003319
Arun Menon906de572013-06-18 17:01:40 -07003320 break;
3321 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07003322
Arun Menon906de572013-06-18 17:01:40 -07003323 case OMX_IndexParamCompBufferSupplier: {
3324 OMX_PARAM_BUFFERSUPPLIERTYPE *bufferSupplierType = (OMX_PARAM_BUFFERSUPPLIERTYPE*) paramData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003325 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamCompBufferSupplier %d",
Arun Menon906de572013-06-18 17:01:40 -07003326 bufferSupplierType->eBufferSupplier);
3327 if (bufferSupplierType->nPortIndex == 0 || bufferSupplierType->nPortIndex ==1)
3328 m_buffer_supplier.eBufferSupplier = bufferSupplierType->eBufferSupplier;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003329
Arun Menon906de572013-06-18 17:01:40 -07003330 else
Shalaj Jain273b3e02012-06-22 19:08:03 -07003331
Arun Menon906de572013-06-18 17:01:40 -07003332 eRet = OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003333
Arun Menon906de572013-06-18 17:01:40 -07003334 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003335
Arun Menon906de572013-06-18 17:01:40 -07003336 }
3337 case OMX_IndexParamVideoAvc: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003338 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoAvc %d",
Arun Menon906de572013-06-18 17:01:40 -07003339 paramIndex);
3340 break;
3341 }
3342 case OMX_IndexParamVideoH263: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003343 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoH263 %d",
Arun Menon906de572013-06-18 17:01:40 -07003344 paramIndex);
3345 break;
3346 }
3347 case OMX_IndexParamVideoMpeg4: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003348 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoMpeg4 %d",
Arun Menon906de572013-06-18 17:01:40 -07003349 paramIndex);
3350 break;
3351 }
3352 case OMX_IndexParamVideoMpeg2: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003353 DEBUG_PRINT_LOW("set_parameter: OMX_IndexParamVideoMpeg2 %d",
Arun Menon906de572013-06-18 17:01:40 -07003354 paramIndex);
3355 break;
3356 }
3357 case OMX_QcomIndexParamVideoDecoderPictureOrder: {
3358 QOMX_VIDEO_DECODER_PICTURE_ORDER *pictureOrder =
3359 (QOMX_VIDEO_DECODER_PICTURE_ORDER *)paramData;
3360 struct v4l2_control control;
3361 int pic_order,rc=0;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003362 DEBUG_PRINT_HIGH("set_parameter: OMX_QcomIndexParamVideoDecoderPictureOrder %d",
Arun Menon906de572013-06-18 17:01:40 -07003363 pictureOrder->eOutputPictureOrder);
3364 if (pictureOrder->eOutputPictureOrder == QOMX_VIDEO_DISPLAY_ORDER) {
3365 pic_order = V4L2_MPEG_VIDC_VIDEO_OUTPUT_ORDER_DISPLAY;
3366 } else if (pictureOrder->eOutputPictureOrder == QOMX_VIDEO_DECODE_ORDER) {
3367 pic_order = V4L2_MPEG_VIDC_VIDEO_OUTPUT_ORDER_DECODE;
3368 time_stamp_dts.set_timestamp_reorder_mode(false);
3369 } else
3370 eRet = OMX_ErrorBadParameter;
3371 if (eRet == OMX_ErrorNone) {
3372 control.id = V4L2_CID_MPEG_VIDC_VIDEO_OUTPUT_ORDER;
3373 control.value = pic_order;
3374 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control);
3375 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003376 DEBUG_PRINT_ERROR("Set picture order failed");
Arun Menon906de572013-06-18 17:01:40 -07003377 eRet = OMX_ErrorUnsupportedSetting;
3378 }
3379 }
3380 break;
3381 }
3382 case OMX_QcomIndexParamConcealMBMapExtraData:
Srinu Gorle2eb94e42014-02-14 13:37:40 +05303383 eRet = enable_extradata(VDEC_EXTRADATA_MB_ERROR_MAP, false,
3384 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3385 break;
3386 case OMX_QcomIndexParamFrameInfoExtraData:
3387 eRet = enable_extradata(OMX_FRAMEINFO_EXTRADATA, false,
3388 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3389 break;
Arun Menon906de572013-06-18 17:01:40 -07003390 case OMX_QcomIndexParamInterlaceExtraData:
Srinu Gorle2eb94e42014-02-14 13:37:40 +05303391 eRet = enable_extradata(OMX_INTERLACE_EXTRADATA, false,
3392 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3393 break;
Arun Menon906de572013-06-18 17:01:40 -07003394 case OMX_QcomIndexParamH264TimeInfo:
Srinu Gorle2eb94e42014-02-14 13:37:40 +05303395 eRet = enable_extradata(OMX_TIMEINFO_EXTRADATA, false,
3396 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3397 break;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303398 case OMX_QcomIndexParamVideoFramePackingExtradata:
Srinu Gorle2eb94e42014-02-14 13:37:40 +05303399 eRet = enable_extradata(OMX_FRAMEPACK_EXTRADATA, false,
3400 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3401 break;
3402 case OMX_QcomIndexParamVideoQPExtraData:
3403 eRet = enable_extradata(OMX_QP_EXTRADATA, false,
3404 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3405 break;
3406 case OMX_QcomIndexParamVideoInputBitsInfoExtraData:
3407 eRet = enable_extradata(OMX_BITSINFO_EXTRADATA, false,
3408 ((QOMX_ENABLETYPE *)paramData)->bEnable);
3409 break;
Arun Menon906de572013-06-18 17:01:40 -07003410 case OMX_QcomIndexParamVideoDivx: {
3411 QOMX_VIDEO_PARAM_DIVXTYPE* divXType = (QOMX_VIDEO_PARAM_DIVXTYPE *) paramData;
3412 }
3413 break;
3414 case OMX_QcomIndexPlatformPvt: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003415 DEBUG_PRINT_HIGH("set_parameter: OMX_QcomIndexPlatformPvt OP Port");
Arun Menon906de572013-06-18 17:01:40 -07003416 OMX_QCOM_PLATFORMPRIVATE_EXTN* entryType = (OMX_QCOM_PLATFORMPRIVATE_EXTN *) paramData;
3417 if (entryType->type != OMX_QCOM_PLATFORM_PRIVATE_PMEM) {
3418 DEBUG_PRINT_HIGH("set_parameter: Platform Private entry type (%d) not supported.", entryType->type);
3419 eRet = OMX_ErrorUnsupportedSetting;
3420 } else {
3421 m_out_pvt_entry_pmem = OMX_TRUE;
3422 if ((m_out_mem_region_smi && m_out_pvt_entry_pmem)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003423 DEBUG_PRINT_HIGH("set_parameter: OMX_QcomIndexPlatformPvt OP Port: out pmem set");
Arun Menon906de572013-06-18 17:01:40 -07003424 m_use_output_pmem = OMX_TRUE;
3425 }
3426 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07003427
Arun Menon906de572013-06-18 17:01:40 -07003428 }
3429 break;
3430 case OMX_QcomIndexParamVideoSyncFrameDecodingMode: {
3431 DEBUG_PRINT_HIGH("set_parameter: OMX_QcomIndexParamVideoSyncFrameDecodingMode");
3432 DEBUG_PRINT_HIGH("set idr only decoding for thumbnail mode");
3433 struct v4l2_control control;
3434 int rc;
3435 drv_ctx.idr_only_decoding = 1;
3436 control.id = V4L2_CID_MPEG_VIDC_VIDEO_OUTPUT_ORDER;
3437 control.value = V4L2_MPEG_VIDC_VIDEO_OUTPUT_ORDER_DECODE;
3438 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control);
3439 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003440 DEBUG_PRINT_ERROR("Set picture order failed");
Arun Menon906de572013-06-18 17:01:40 -07003441 eRet = OMX_ErrorUnsupportedSetting;
3442 } else {
3443 control.id = V4L2_CID_MPEG_VIDC_VIDEO_SYNC_FRAME_DECODE;
3444 control.value = V4L2_MPEG_VIDC_VIDEO_SYNC_FRAME_DECODE_ENABLE;
3445 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control);
3446 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003447 DEBUG_PRINT_ERROR("Sync frame setting failed");
Arun Menon906de572013-06-18 17:01:40 -07003448 eRet = OMX_ErrorUnsupportedSetting;
3449 }
3450 /*Setting sync frame decoding on driver might change buffer
3451 * requirements so update them here*/
3452 if (get_buffer_req(&drv_ctx.ip_buf)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003453 DEBUG_PRINT_ERROR("Sync frame setting failed: falied to get buffer i/p requirements");
Arun Menon906de572013-06-18 17:01:40 -07003454 eRet = OMX_ErrorUnsupportedSetting;
3455 }
3456 if (get_buffer_req(&drv_ctx.op_buf)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003457 DEBUG_PRINT_ERROR("Sync frame setting failed: falied to get buffer o/p requirements");
Arun Menon906de572013-06-18 17:01:40 -07003458 eRet = OMX_ErrorUnsupportedSetting;
3459 }
3460 }
3461 }
3462 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003463
Arun Menon906de572013-06-18 17:01:40 -07003464 case OMX_QcomIndexParamIndexExtraDataType: {
Srinu Gorle2eb94e42014-02-14 13:37:40 +05303465 QOMX_INDEXEXTRADATATYPE *extradataIndexType = (QOMX_INDEXEXTRADATATYPE *) paramData;
3466 if ((extradataIndexType->nIndex == OMX_IndexParamPortDefinition) &&
3467 (extradataIndexType->bEnabled == OMX_TRUE) &&
3468 (extradataIndexType->nPortIndex == 1)) {
3469 DEBUG_PRINT_HIGH("set_parameter: OMX_QcomIndexParamIndexExtraDataType SmoothStreaming");
3470 eRet = enable_extradata(OMX_PORTDEF_EXTRADATA, false, extradataIndexType->bEnabled);
3471 }
3472 }
Arun Menon906de572013-06-18 17:01:40 -07003473 break;
3474 case OMX_QcomIndexParamEnableSmoothStreaming: {
Arun Menonc821d8a2013-06-15 10:03:29 -07003475#ifndef SMOOTH_STREAMING_DISABLED
Praveen Chavancf924182013-12-06 23:16:23 -08003476 eRet = enable_smoothstreaming();
Arun Menonbc0922f2013-06-24 13:02:15 -07003477#else
Arun Menon906de572013-06-18 17:01:40 -07003478 eRet = OMX_ErrorUnsupportedSetting;
Arun Menonc821d8a2013-06-15 10:03:29 -07003479#endif
Arun Menon906de572013-06-18 17:01:40 -07003480 }
3481 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003482#if defined (_ANDROID_HONEYCOMB_) || defined (_ANDROID_ICS_)
Arun Menon906de572013-06-18 17:01:40 -07003483 /* Need to allow following two set_parameters even in Idle
3484 * state. This is ANDROID architecture which is not in sync
3485 * with openmax standard. */
3486 case OMX_GoogleAndroidIndexEnableAndroidNativeBuffers: {
3487 EnableAndroidNativeBuffersParams* enableNativeBuffers = (EnableAndroidNativeBuffersParams *) paramData;
3488 if (enableNativeBuffers) {
3489 m_enable_android_native_buffers = enableNativeBuffers->enable;
3490 }
3491 }
3492 break;
3493 case OMX_GoogleAndroidIndexUseAndroidNativeBuffer: {
3494 eRet = use_android_native_buffer(hComp, paramData);
3495 }
3496 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003497#endif
Arun Menon906de572013-06-18 17:01:40 -07003498 case OMX_QcomIndexParamEnableTimeStampReorder: {
3499 QOMX_INDEXTIMESTAMPREORDER *reorder = (QOMX_INDEXTIMESTAMPREORDER *)paramData;
3500 if (drv_ctx.picture_order == (vdec_output_order)QOMX_VIDEO_DISPLAY_ORDER) {
3501 if (reorder->bEnable == OMX_TRUE) {
3502 frm_int =0;
3503 time_stamp_dts.set_timestamp_reorder_mode(true);
3504 } else
3505 time_stamp_dts.set_timestamp_reorder_mode(false);
3506 } else {
3507 time_stamp_dts.set_timestamp_reorder_mode(false);
3508 if (reorder->bEnable == OMX_TRUE) {
3509 eRet = OMX_ErrorUnsupportedSetting;
3510 }
3511 }
3512 }
3513 break;
3514 case OMX_IndexParamVideoProfileLevelCurrent: {
3515 OMX_VIDEO_PARAM_PROFILELEVELTYPE* pParam =
3516 (OMX_VIDEO_PARAM_PROFILELEVELTYPE*)paramData;
3517 if (pParam) {
3518 m_profile_lvl.eProfile = pParam->eProfile;
3519 m_profile_lvl.eLevel = pParam->eLevel;
3520 }
3521 break;
Arun Menon888aa852013-05-30 11:24:42 -07003522
Arun Menon906de572013-06-18 17:01:40 -07003523 }
Arun Menone5652482013-08-04 13:33:05 -07003524 case OMX_QcomIndexParamVideoMetaBufferMode:
3525 {
3526 StoreMetaDataInBuffersParams *metabuffer =
3527 (StoreMetaDataInBuffersParams *)paramData;
3528 if (!metabuffer) {
3529 DEBUG_PRINT_ERROR("Invalid param: %p", metabuffer);
3530 eRet = OMX_ErrorBadParameter;
3531 break;
3532 }
3533 if (metabuffer->nPortIndex == OMX_CORE_OUTPUT_PORT_INDEX) {
3534 //set property dynamic buffer mode to driver.
3535 struct v4l2_control control;
3536 struct v4l2_format fmt;
3537 control.id = V4L2_CID_MPEG_VIDC_VIDEO_ALLOC_MODE_OUTPUT;
3538 if (metabuffer->bStoreMetaData == true) {
3539 control.value = V4L2_MPEG_VIDC_VIDEO_DYNAMIC;
3540 } else {
3541 control.value = V4L2_MPEG_VIDC_VIDEO_STATIC;
3542 }
3543 int rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL,&control);
3544 if (!rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003545 DEBUG_PRINT_HIGH("%s buffer mode",
Arun Menone5652482013-08-04 13:33:05 -07003546 (metabuffer->bStoreMetaData == true)? "Enabled dynamic" : "Disabled dynamic");
Arun Menonbdb80b02013-08-12 17:45:54 -07003547 dynamic_buf_mode = metabuffer->bStoreMetaData;
Arun Menone5652482013-08-04 13:33:05 -07003548 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003549 DEBUG_PRINT_ERROR("Failed to %s buffer mode",
Arun Menone5652482013-08-04 13:33:05 -07003550 (metabuffer->bStoreMetaData == true)? "enable dynamic" : "disable dynamic");
3551 eRet = OMX_ErrorUnsupportedSetting;
3552 }
3553 } else {
3554 DEBUG_PRINT_ERROR(
Praveen Chavancf924182013-12-06 23:16:23 -08003555 "OMX_QcomIndexParamVideoMetaBufferMode not supported for port: %lu",
Arun Menone5652482013-08-04 13:33:05 -07003556 metabuffer->nPortIndex);
3557 eRet = OMX_ErrorUnsupportedSetting;
3558 }
3559 break;
3560 }
Praneeth Paladugu42306bb2013-08-27 22:01:28 -07003561 case OMX_QcomIndexParamVideoDownScalar: {
3562 QOMX_INDEXDOWNSCALAR* pParam = (QOMX_INDEXDOWNSCALAR*)paramData;
3563 struct v4l2_control control;
3564 int rc;
3565 if (pParam) {
3566 is_down_scalar_enabled = pParam->bEnable;
3567 if (is_down_scalar_enabled) {
3568 control.id = V4L2_CID_MPEG_VIDC_VIDEO_STREAM_OUTPUT_MODE;
3569 control.value = V4L2_CID_MPEG_VIDC_VIDEO_STREAM_OUTPUT_SECONDARY;
3570 DEBUG_PRINT_LOW("set_parameter: OMX_QcomIndexParamVideoDownScalar value = %d\n",
3571 pParam->bEnable);
3572 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL,&control);
3573 if (rc < 0) {
3574 DEBUG_PRINT_ERROR("Failed to set down scalar on driver.");
3575 eRet = OMX_ErrorUnsupportedSetting;
3576 }
3577 control.id = V4L2_CID_MPEG_VIDC_VIDEO_KEEP_ASPECT_RATIO;
3578 control.value = 1;
3579 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL,&control);
3580 if (rc < 0) {
3581 DEBUG_PRINT_ERROR("Failed to set keep aspect ratio on driver.");
3582 eRet = OMX_ErrorUnsupportedSetting;
3583 }
3584 }
3585 }
3586 break;
3587 }
Praveen Chavancf924182013-12-06 23:16:23 -08003588#ifdef ADAPTIVE_PLAYBACK_SUPPORTED
3589 case OMX_QcomIndexParamVideoAdaptivePlaybackMode:
3590 {
3591 DEBUG_PRINT_LOW("set_parameter: OMX_GoogleAndroidIndexPrepareForAdaptivePlayback");
3592 PrepareForAdaptivePlaybackParams* pParams =
3593 (PrepareForAdaptivePlaybackParams *) paramData;
3594 if (pParams->nPortIndex == OMX_CORE_OUTPUT_PORT_INDEX) {
3595 if (!pParams->bEnable) {
3596 return OMX_ErrorNone;
3597 }
Deepak Vermaa2efdb12013-12-26 12:30:05 +05303598 if (pParams->nMaxFrameWidth > maxSmoothStreamingWidth
3599 || pParams->nMaxFrameHeight > maxSmoothStreamingHeight) {
Praveen Chavancf924182013-12-06 23:16:23 -08003600 DEBUG_PRINT_ERROR(
3601 "Adaptive playback request exceeds max supported resolution : [%lu x %lu] vs [%lu x %lu]",
3602 pParams->nMaxFrameWidth, pParams->nMaxFrameHeight,
Deepak Vermaa2efdb12013-12-26 12:30:05 +05303603 maxSmoothStreamingWidth, maxSmoothStreamingHeight);
Praveen Chavancf924182013-12-06 23:16:23 -08003604 eRet = OMX_ErrorBadParameter;
3605 } else {
3606 eRet = enable_smoothstreaming();
3607 if (eRet != OMX_ErrorNone) {
3608 DEBUG_PRINT_ERROR("Failed to enable Adaptive Playback on driver.");
3609 eRet = OMX_ErrorHardware;
3610 } else {
3611 DEBUG_PRINT_HIGH("Enabling Adaptive playback for %lu x %lu",
3612 pParams->nMaxFrameWidth, pParams->nMaxFrameHeight);
3613 m_smoothstreaming_mode = true;
3614 m_smoothstreaming_width = pParams->nMaxFrameWidth;
3615 m_smoothstreaming_height = pParams->nMaxFrameHeight;
3616 }
Deepak Vermaf8771292014-02-03 12:22:50 +05303617 struct v4l2_format fmt;
3618 update_resolution(m_smoothstreaming_width, m_smoothstreaming_height,
3619 m_smoothstreaming_width, m_smoothstreaming_height);
3620 eRet = is_video_session_supported();
3621 if (eRet)
3622 break;
3623 fmt.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
3624 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
3625 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
3626 fmt.fmt.pix_mp.pixelformat = output_capability;
3627 DEBUG_PRINT_LOW("fmt.fmt.pix_mp.height = %d , fmt.fmt.pix_mp.width = %d",
3628 fmt.fmt.pix_mp.height,fmt.fmt.pix_mp.width);
3629 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
3630 if (ret) {
3631 DEBUG_PRINT_ERROR("Set Resolution failed");
3632 eRet = OMX_ErrorUnsupportedSetting;
3633 } else
3634 eRet = get_buffer_req(&drv_ctx.op_buf);
Deepak Vermaa2efdb12013-12-26 12:30:05 +05303635 }
Praveen Chavancf924182013-12-06 23:16:23 -08003636 } else {
3637 DEBUG_PRINT_ERROR(
3638 "Prepare for adaptive playback supported only on output port");
3639 eRet = OMX_ErrorBadParameter;
3640 }
3641 break;
3642 }
3643
3644#endif
Arun Menon906de572013-06-18 17:01:40 -07003645 default: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003646 DEBUG_PRINT_ERROR("Setparameter: unknown param %d", paramIndex);
Arun Menon906de572013-06-18 17:01:40 -07003647 eRet = OMX_ErrorUnsupportedIndex;
3648 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07003649 }
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08003650 if (eRet != OMX_ErrorNone)
3651 DEBUG_PRINT_ERROR("set_parameter: Error: 0x%x, setting param 0x%x", eRet, paramIndex);
Arun Menon906de572013-06-18 17:01:40 -07003652 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003653}
3654
3655/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07003656 FUNCTION
3657 omx_vdec::GetConfig
Shalaj Jain273b3e02012-06-22 19:08:03 -07003658
Arun Menon906de572013-06-18 17:01:40 -07003659 DESCRIPTION
3660 OMX Get Config Method implementation.
Shalaj Jain273b3e02012-06-22 19:08:03 -07003661
Arun Menon906de572013-06-18 17:01:40 -07003662 PARAMETERS
3663 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07003664
Arun Menon906de572013-06-18 17:01:40 -07003665 RETURN VALUE
3666 OMX Error None if successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07003667
Arun Menon906de572013-06-18 17:01:40 -07003668 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07003669OMX_ERRORTYPE omx_vdec::get_config(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07003670 OMX_IN OMX_INDEXTYPE configIndex,
3671 OMX_INOUT OMX_PTR configData)
Shalaj Jain273b3e02012-06-22 19:08:03 -07003672{
Arun Menon906de572013-06-18 17:01:40 -07003673 OMX_ERRORTYPE eRet = OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003674
Arun Menon906de572013-06-18 17:01:40 -07003675 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003676 DEBUG_PRINT_ERROR("Get Config in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07003677 return OMX_ErrorInvalidState;
3678 }
Arun Menon906de572013-06-18 17:01:40 -07003679
3680 switch ((unsigned long)configIndex) {
3681 case OMX_QcomIndexConfigInterlaced: {
3682 OMX_QCOM_CONFIG_INTERLACETYPE *configFmt =
3683 (OMX_QCOM_CONFIG_INTERLACETYPE *) configData;
3684 if (configFmt->nPortIndex == 1) {
3685 if (configFmt->nIndex == 0) {
3686 configFmt->eInterlaceType = OMX_QCOM_InterlaceFrameProgressive;
3687 } else if (configFmt->nIndex == 1) {
3688 configFmt->eInterlaceType =
3689 OMX_QCOM_InterlaceInterleaveFrameTopFieldFirst;
3690 } else if (configFmt->nIndex == 2) {
3691 configFmt->eInterlaceType =
3692 OMX_QCOM_InterlaceInterleaveFrameBottomFieldFirst;
3693 } else {
3694 DEBUG_PRINT_ERROR("get_config: OMX_QcomIndexConfigInterlaced:"
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003695 " NoMore Interlaced formats");
Arun Menon906de572013-06-18 17:01:40 -07003696 eRet = OMX_ErrorNoMore;
3697 }
3698
3699 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003700 DEBUG_PRINT_ERROR("get_config: Bad port index %d queried on only o/p port",
Arun Menon906de572013-06-18 17:01:40 -07003701 (int)configFmt->nPortIndex);
3702 eRet = OMX_ErrorBadPortIndex;
3703 }
3704 break;
3705 }
3706 case OMX_QcomIndexQueryNumberOfVideoDecInstance: {
3707 QOMX_VIDEO_QUERY_DECODER_INSTANCES *decoderinstances =
3708 (QOMX_VIDEO_QUERY_DECODER_INSTANCES*)configData;
3709 decoderinstances->nNumOfInstances = 16;
3710 /*TODO: How to handle this case */
3711 break;
3712 }
3713 case OMX_QcomIndexConfigVideoFramePackingArrangement: {
3714 if (drv_ctx.decoder_format == VDEC_CODECTYPE_H264) {
3715 OMX_QCOM_FRAME_PACK_ARRANGEMENT *configFmt =
3716 (OMX_QCOM_FRAME_PACK_ARRANGEMENT *) configData;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303717 memcpy(configFmt, &m_frame_pack_arrangement,
3718 sizeof(OMX_QCOM_FRAME_PACK_ARRANGEMENT));
Arun Menon906de572013-06-18 17:01:40 -07003719 } else {
3720 DEBUG_PRINT_ERROR("get_config: Framepack data not supported for non H264 codecs");
3721 }
3722 break;
3723 }
3724 case OMX_IndexConfigCommonOutputCrop: {
3725 OMX_CONFIG_RECTTYPE *rect = (OMX_CONFIG_RECTTYPE *) configData;
3726 memcpy(rect, &rectangle, sizeof(OMX_CONFIG_RECTTYPE));
3727 break;
3728 }
3729 default: {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003730 DEBUG_PRINT_ERROR("get_config: unknown param %d",configIndex);
Arun Menon906de572013-06-18 17:01:40 -07003731 eRet = OMX_ErrorBadParameter;
3732 }
3733
Shalaj Jain273b3e02012-06-22 19:08:03 -07003734 }
Arun Menon906de572013-06-18 17:01:40 -07003735
3736 return eRet;
3737}
3738
3739/* ======================================================================
3740 FUNCTION
3741 omx_vdec::SetConfig
3742
3743 DESCRIPTION
3744 OMX Set Config method implementation
3745
3746 PARAMETERS
3747 <TBD>.
3748
3749 RETURN VALUE
3750 OMX Error None if successful.
3751 ========================================================================== */
3752OMX_ERRORTYPE omx_vdec::set_config(OMX_IN OMX_HANDLETYPE hComp,
3753 OMX_IN OMX_INDEXTYPE configIndex,
3754 OMX_IN OMX_PTR configData)
3755{
3756 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003757 DEBUG_PRINT_ERROR("Get Config in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07003758 return OMX_ErrorInvalidState;
3759 }
3760
3761 OMX_ERRORTYPE ret = OMX_ErrorNone;
3762 OMX_VIDEO_CONFIG_NALSIZE *pNal;
3763
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003764 DEBUG_PRINT_LOW("Set Config Called");
Arun Menon906de572013-06-18 17:01:40 -07003765
3766 if (configIndex == (OMX_INDEXTYPE)OMX_IndexVendorVideoExtraData) {
3767 OMX_VENDOR_EXTRADATATYPE *config = (OMX_VENDOR_EXTRADATATYPE *) configData;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003768 DEBUG_PRINT_LOW("Index OMX_IndexVendorVideoExtraData called");
Arun Menon906de572013-06-18 17:01:40 -07003769 if (!strcmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc")) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003770 DEBUG_PRINT_LOW("Index OMX_IndexVendorVideoExtraData AVC");
Arun Menon906de572013-06-18 17:01:40 -07003771 OMX_U32 extra_size;
3772 // Parsing done here for the AVC atom is definitely not generic
3773 // Currently this piece of code is working, but certainly
3774 // not tested with all .mp4 files.
3775 // Incase of failure, we might need to revisit this
3776 // for a generic piece of code.
3777
3778 // Retrieve size of NAL length field
3779 // byte #4 contains the size of NAL lenght field
3780 nal_length = (config->pData[4] & 0x03) + 1;
3781
3782 extra_size = 0;
3783 if (nal_length > 2) {
3784 /* Presently we assume that only one SPS and one PPS in AvC1 Atom */
3785 extra_size = (nal_length - 2) * 2;
3786 }
3787
3788 // SPS starts from byte #6
3789 OMX_U8 *pSrcBuf = (OMX_U8 *) (&config->pData[6]);
3790 OMX_U8 *pDestBuf;
3791 m_vendor_config.nPortIndex = config->nPortIndex;
3792
3793 // minus 6 --> SPS starts from byte #6
3794 // minus 1 --> picture param set byte to be ignored from avcatom
3795 m_vendor_config.nDataSize = config->nDataSize - 6 - 1 + extra_size;
3796 m_vendor_config.pData = (OMX_U8 *) malloc(m_vendor_config.nDataSize);
3797 OMX_U32 len;
3798 OMX_U8 index = 0;
3799 // case where SPS+PPS is sent as part of set_config
3800 pDestBuf = m_vendor_config.pData;
3801
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003802 DEBUG_PRINT_LOW("Rxd SPS+PPS nPortIndex[%lu] len[%lu] data[%p]",
Arun Menon906de572013-06-18 17:01:40 -07003803 m_vendor_config.nPortIndex,
3804 m_vendor_config.nDataSize,
3805 m_vendor_config.pData);
3806 while (index < 2) {
3807 uint8 *psize;
3808 len = *pSrcBuf;
3809 len = len << 8;
3810 len |= *(pSrcBuf + 1);
3811 psize = (uint8 *) & len;
3812 memcpy(pDestBuf + nal_length, pSrcBuf + 2,len);
3813 for (unsigned int i = 0; i < nal_length; i++) {
3814 pDestBuf[i] = psize[nal_length - 1 - i];
3815 }
3816 //memcpy(pDestBuf,pSrcBuf,(len+2));
3817 pDestBuf += len + nal_length;
3818 pSrcBuf += len + 2;
3819 index++;
3820 pSrcBuf++; // skip picture param set
3821 len = 0;
3822 }
3823 } else if (!strcmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg4") ||
3824 !strcmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg2")) {
3825 m_vendor_config.nPortIndex = config->nPortIndex;
3826 m_vendor_config.nDataSize = config->nDataSize;
3827 m_vendor_config.pData = (OMX_U8 *) malloc((config->nDataSize));
3828 memcpy(m_vendor_config.pData, config->pData,config->nDataSize);
3829 } else if (!strcmp(drv_ctx.kind, "OMX.qcom.video.decoder.vc1")) {
3830 if (m_vendor_config.pData) {
3831 free(m_vendor_config.pData);
3832 m_vendor_config.pData = NULL;
3833 m_vendor_config.nDataSize = 0;
3834 }
3835
3836 if (((*((OMX_U32 *) config->pData)) &
3837 VC1_SP_MP_START_CODE_MASK) ==
3838 VC1_SP_MP_START_CODE) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003839 DEBUG_PRINT_LOW("set_config - VC1 simple/main profile");
Arun Menon906de572013-06-18 17:01:40 -07003840 m_vendor_config.nPortIndex = config->nPortIndex;
3841 m_vendor_config.nDataSize = config->nDataSize;
3842 m_vendor_config.pData =
3843 (OMX_U8 *) malloc(config->nDataSize);
3844 memcpy(m_vendor_config.pData, config->pData,
3845 config->nDataSize);
3846 m_vc1_profile = VC1_SP_MP_RCV;
3847 } else if (*((OMX_U32 *) config->pData) == VC1_AP_SEQ_START_CODE) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003848 DEBUG_PRINT_LOW("set_config - VC1 Advance profile");
Arun Menon906de572013-06-18 17:01:40 -07003849 m_vendor_config.nPortIndex = config->nPortIndex;
3850 m_vendor_config.nDataSize = config->nDataSize;
3851 m_vendor_config.pData =
3852 (OMX_U8 *) malloc((config->nDataSize));
3853 memcpy(m_vendor_config.pData, config->pData,
3854 config->nDataSize);
3855 m_vc1_profile = VC1_AP;
3856 } else if ((config->nDataSize == VC1_STRUCT_C_LEN)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003857 DEBUG_PRINT_LOW("set_config - VC1 Simple/Main profile struct C only");
Arun Menon906de572013-06-18 17:01:40 -07003858 m_vendor_config.nPortIndex = config->nPortIndex;
3859 m_vendor_config.nDataSize = config->nDataSize;
3860 m_vendor_config.pData = (OMX_U8*)malloc(config->nDataSize);
3861 memcpy(m_vendor_config.pData,config->pData,config->nDataSize);
3862 m_vc1_profile = VC1_SP_MP_RCV;
3863 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003864 DEBUG_PRINT_LOW("set_config - Error: Unknown VC1 profile");
Arun Menon906de572013-06-18 17:01:40 -07003865 }
3866 }
3867 return ret;
3868 } else if (configIndex == OMX_IndexConfigVideoNalSize) {
3869 struct v4l2_control temp;
3870 temp.id = V4L2_CID_MPEG_VIDC_VIDEO_STREAM_FORMAT;
3871
3872 pNal = reinterpret_cast < OMX_VIDEO_CONFIG_NALSIZE * >(configData);
3873 switch (pNal->nNaluBytes) {
3874 case 0:
3875 temp.value = V4L2_MPEG_VIDC_VIDEO_NAL_FORMAT_STARTCODES;
3876 break;
3877 case 2:
3878 temp.value = V4L2_MPEG_VIDC_VIDEO_NAL_FORMAT_TWO_BYTE_LENGTH;
3879 break;
3880 case 4:
3881 temp.value = V4L2_MPEG_VIDC_VIDEO_NAL_FORMAT_FOUR_BYTE_LENGTH;
3882 break;
3883 default:
3884 return OMX_ErrorUnsupportedSetting;
3885 }
3886
3887 if (!arbitrary_bytes) {
3888 /* In arbitrary bytes mode, the assembler strips out nal size and replaces
3889 * with start code, so only need to notify driver in frame by frame mode */
3890 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &temp)) {
3891 DEBUG_PRINT_ERROR("Failed to set V4L2_CID_MPEG_VIDC_VIDEO_STREAM_FORMAT");
3892 return OMX_ErrorHardware;
3893 }
3894 }
3895
3896 nal_length = pNal->nNaluBytes;
3897 m_frame_parser.init_nal_length(nal_length);
3898
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003899 DEBUG_PRINT_LOW("OMX_IndexConfigVideoNalSize called with Size %d", nal_length);
Arun Menon906de572013-06-18 17:01:40 -07003900 return ret;
Surajit Podderd2644d52013-08-28 17:59:06 +05303901 } else if ((int)configIndex == (int)OMX_IndexVendorVideoFrameRate) {
Arun Menon906de572013-06-18 17:01:40 -07003902 OMX_VENDOR_VIDEOFRAMERATE *config = (OMX_VENDOR_VIDEOFRAMERATE *) configData;
Surajit Podderd2644d52013-08-28 17:59:06 +05303903 DEBUG_PRINT_HIGH("Index OMX_IndexVendorVideoFrameRate %lu", config->nFps);
Arun Menon906de572013-06-18 17:01:40 -07003904
3905 if (config->nPortIndex == OMX_CORE_INPUT_PORT_INDEX) {
3906 if (config->bEnabled) {
3907 if ((config->nFps >> 16) > 0) {
Surajit Podderd2644d52013-08-28 17:59:06 +05303908 DEBUG_PRINT_HIGH("set_config: frame rate set by omx client : %lu",
Arun Menon906de572013-06-18 17:01:40 -07003909 config->nFps >> 16);
3910 Q16ToFraction(config->nFps, drv_ctx.frame_rate.fps_numerator,
3911 drv_ctx.frame_rate.fps_denominator);
3912
3913 if (!drv_ctx.frame_rate.fps_numerator) {
3914 DEBUG_PRINT_ERROR("Numerator is zero setting to 30");
3915 drv_ctx.frame_rate.fps_numerator = 30;
3916 }
3917
3918 if (drv_ctx.frame_rate.fps_denominator) {
3919 drv_ctx.frame_rate.fps_numerator = (int)
3920 drv_ctx.frame_rate.fps_numerator / drv_ctx.frame_rate.fps_denominator;
3921 }
3922
3923 drv_ctx.frame_rate.fps_denominator = 1;
3924 frm_int = drv_ctx.frame_rate.fps_denominator * 1e6 /
3925 drv_ctx.frame_rate.fps_numerator;
3926
3927 struct v4l2_outputparm oparm;
3928 /*XXX: we're providing timing info as seconds per frame rather than frames
3929 * per second.*/
3930 oparm.timeperframe.numerator = drv_ctx.frame_rate.fps_denominator;
3931 oparm.timeperframe.denominator = drv_ctx.frame_rate.fps_numerator;
3932
3933 struct v4l2_streamparm sparm;
3934 sparm.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
3935 sparm.parm.output = oparm;
3936 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_PARM, &sparm)) {
3937 DEBUG_PRINT_ERROR("Unable to convey fps info to driver, \
3938 performance might be affected");
3939 ret = OMX_ErrorHardware;
3940 }
3941 client_set_fps = true;
3942 } else {
3943 DEBUG_PRINT_ERROR("Frame rate not supported.");
3944 ret = OMX_ErrorUnsupportedSetting;
3945 }
3946 } else {
3947 DEBUG_PRINT_HIGH("set_config: Disabled client's frame rate");
3948 client_set_fps = false;
3949 }
3950 } else {
3951 DEBUG_PRINT_ERROR(" Set_config: Bad Port idx %d",
3952 (int)config->nPortIndex);
3953 ret = OMX_ErrorBadPortIndex;
3954 }
3955
3956 return ret;
3957 }
3958
3959 return OMX_ErrorNotImplemented;
3960}
3961
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303962#define extn_equals(param, extn) (!strncmp(param, extn, strlen(extn)))
3963
Arun Menon906de572013-06-18 17:01:40 -07003964/* ======================================================================
3965 FUNCTION
3966 omx_vdec::GetExtensionIndex
3967
3968 DESCRIPTION
3969 OMX GetExtensionIndex method implementaion. <TBD>
3970
3971 PARAMETERS
3972 <TBD>.
3973
3974 RETURN VALUE
3975 OMX Error None if everything successful.
3976
3977 ========================================================================== */
3978OMX_ERRORTYPE omx_vdec::get_extension_index(OMX_IN OMX_HANDLETYPE hComp,
3979 OMX_IN OMX_STRING paramName,
3980 OMX_OUT OMX_INDEXTYPE* indexType)
3981{
3982 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07003983 DEBUG_PRINT_ERROR("Get Extension Index in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07003984 return OMX_ErrorInvalidState;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303985 } else if (extn_equals(paramName, "OMX.QCOM.index.param.video.SyncFrameDecodingMode")) {
Arun Menon906de572013-06-18 17:01:40 -07003986 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamVideoSyncFrameDecodingMode;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303987 } else if (extn_equals(paramName, "OMX.QCOM.index.param.IndexExtraData")) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07003988 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamIndexExtraDataType;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303989 } else if (extn_equals(paramName, OMX_QCOM_INDEX_PARAM_VIDEO_FRAMEPACKING_EXTRADATA)) {
3990 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamVideoFramePackingExtradata;
3991 } else if (extn_equals(paramName, OMX_QCOM_INDEX_CONFIG_VIDEO_FRAMEPACKING_INFO)) {
3992 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexConfigVideoFramePackingArrangement;
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08003993 } else if (extn_equals(paramName, OMX_QCOM_INDEX_PARAM_VIDEO_QP_EXTRADATA)) {
3994 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamVideoQPExtraData;
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08003995 } else if (extn_equals(paramName, OMX_QCOM_INDEX_PARAM_VIDEO_INPUTBITSINFO_EXTRADATA)) {
3996 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamVideoInputBitsInfoExtraData;
Shalaj Jain273b3e02012-06-22 19:08:03 -07003997 }
3998#if defined (_ANDROID_HONEYCOMB_) || defined (_ANDROID_ICS_)
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05303999 else if (extn_equals(paramName, "OMX.google.android.index.enableAndroidNativeBuffers")) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07004000 *indexType = (OMX_INDEXTYPE)OMX_GoogleAndroidIndexEnableAndroidNativeBuffers;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05304001 } else if (extn_equals(paramName, "OMX.google.android.index.useAndroidNativeBuffer2")) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07004002 *indexType = (OMX_INDEXTYPE)OMX_GoogleAndroidIndexUseAndroidNativeBuffer2;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05304003 } else if (extn_equals(paramName, "OMX.google.android.index.useAndroidNativeBuffer")) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004004 DEBUG_PRINT_ERROR("Extension: %s is supported", paramName);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004005 *indexType = (OMX_INDEXTYPE)OMX_GoogleAndroidIndexUseAndroidNativeBuffer;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05304006 } else if (extn_equals(paramName, "OMX.google.android.index.getAndroidNativeBufferUsage")) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07004007 *indexType = (OMX_INDEXTYPE)OMX_GoogleAndroidIndexGetAndroidNativeBufferUsage;
4008 }
4009#endif
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05304010 else if (extn_equals(paramName, "OMX.google.android.index.storeMetaDataInBuffers")) {
Arun Menone5652482013-08-04 13:33:05 -07004011 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamVideoMetaBufferMode;
4012 }
Pushkaraj Patil8f98adf2014-02-12 13:32:00 +05304013#ifdef ADAPTIVE_PLAYBACK_SUPPORTED
Praveen Chavancf924182013-12-06 23:16:23 -08004014 else if (extn_equals(paramName, "OMX.google.android.index.prepareForAdaptivePlayback")) {
4015 *indexType = (OMX_INDEXTYPE)OMX_QcomIndexParamVideoAdaptivePlaybackMode;
4016 }
4017#endif
Arun Menon906de572013-06-18 17:01:40 -07004018 else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004019 DEBUG_PRINT_ERROR("Extension: %s not implemented", paramName);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004020 return OMX_ErrorNotImplemented;
4021 }
4022 return OMX_ErrorNone;
4023}
4024
4025/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004026 FUNCTION
4027 omx_vdec::GetState
Shalaj Jain273b3e02012-06-22 19:08:03 -07004028
Arun Menon906de572013-06-18 17:01:40 -07004029 DESCRIPTION
4030 Returns the state information back to the caller.<TBD>
Shalaj Jain273b3e02012-06-22 19:08:03 -07004031
Arun Menon906de572013-06-18 17:01:40 -07004032 PARAMETERS
4033 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004034
Arun Menon906de572013-06-18 17:01:40 -07004035 RETURN VALUE
4036 Error None if everything is successful.
4037 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004038OMX_ERRORTYPE omx_vdec::get_state(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07004039 OMX_OUT OMX_STATETYPE* state)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004040{
Arun Menon906de572013-06-18 17:01:40 -07004041 *state = m_state;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004042 DEBUG_PRINT_LOW("get_state: Returning the state %d",*state);
Arun Menon906de572013-06-18 17:01:40 -07004043 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004044}
4045
4046/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004047 FUNCTION
4048 omx_vdec::ComponentTunnelRequest
Shalaj Jain273b3e02012-06-22 19:08:03 -07004049
Arun Menon906de572013-06-18 17:01:40 -07004050 DESCRIPTION
4051 OMX Component Tunnel Request method implementation. <TBD>
Shalaj Jain273b3e02012-06-22 19:08:03 -07004052
Arun Menon906de572013-06-18 17:01:40 -07004053 PARAMETERS
4054 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004055
Arun Menon906de572013-06-18 17:01:40 -07004056 RETURN VALUE
4057 OMX Error None if everything successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004058
Arun Menon906de572013-06-18 17:01:40 -07004059 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004060OMX_ERRORTYPE omx_vdec::component_tunnel_request(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07004061 OMX_IN OMX_U32 port,
4062 OMX_IN OMX_HANDLETYPE peerComponent,
4063 OMX_IN OMX_U32 peerPort,
4064 OMX_INOUT OMX_TUNNELSETUPTYPE* tunnelSetup)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004065{
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004066 DEBUG_PRINT_ERROR("Error: component_tunnel_request Not Implemented");
Arun Menon906de572013-06-18 17:01:40 -07004067 return OMX_ErrorNotImplemented;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004068}
4069
4070/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004071 FUNCTION
4072 omx_vdec::UseOutputBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07004073
Arun Menon906de572013-06-18 17:01:40 -07004074 DESCRIPTION
4075 Helper function for Use buffer in the input pin
Shalaj Jain273b3e02012-06-22 19:08:03 -07004076
Arun Menon906de572013-06-18 17:01:40 -07004077 PARAMETERS
4078 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004079
Arun Menon906de572013-06-18 17:01:40 -07004080 RETURN VALUE
4081 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07004082
Arun Menon906de572013-06-18 17:01:40 -07004083 ========================================================================== */
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004084OMX_ERRORTYPE omx_vdec::allocate_extradata()
4085{
4086#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07004087 if (drv_ctx.extradata_info.buffer_size) {
4088 if (drv_ctx.extradata_info.ion.ion_alloc_data.handle) {
4089 munmap((void *)drv_ctx.extradata_info.uaddr, drv_ctx.extradata_info.size);
4090 close(drv_ctx.extradata_info.ion.fd_ion_data.fd);
4091 free_ion_memory(&drv_ctx.extradata_info.ion);
Praveen Chavan61e5d162013-11-01 02:49:19 -07004092 memset(&drv_ctx.extradata_info, 0, sizeof(drv_ctx.extradata_info));
Arun Menon906de572013-06-18 17:01:40 -07004093 }
4094 drv_ctx.extradata_info.size = (drv_ctx.extradata_info.size + 4095) & (~4095);
4095 drv_ctx.extradata_info.ion.ion_device_fd = alloc_map_ion_memory(
4096 drv_ctx.extradata_info.size, 4096,
4097 &drv_ctx.extradata_info.ion.ion_alloc_data,
4098 &drv_ctx.extradata_info.ion.fd_ion_data, 0);
4099 if (drv_ctx.extradata_info.ion.ion_device_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004100 DEBUG_PRINT_ERROR("Failed to alloc extradata memory");
Arun Menon906de572013-06-18 17:01:40 -07004101 return OMX_ErrorInsufficientResources;
4102 }
4103 drv_ctx.extradata_info.uaddr = (char *)mmap(NULL,
4104 drv_ctx.extradata_info.size,
4105 PROT_READ|PROT_WRITE, MAP_SHARED,
4106 drv_ctx.extradata_info.ion.fd_ion_data.fd , 0);
4107 if (drv_ctx.extradata_info.uaddr == MAP_FAILED) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004108 DEBUG_PRINT_ERROR("Failed to map extradata memory");
Arun Menon906de572013-06-18 17:01:40 -07004109 close(drv_ctx.extradata_info.ion.fd_ion_data.fd);
4110 free_ion_memory(&drv_ctx.extradata_info.ion);
4111 return OMX_ErrorInsufficientResources;
4112 }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004113 }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004114#endif
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05304115 if (!m_other_extradata) {
4116 m_other_extradata = (OMX_OTHER_EXTRADATATYPE *)malloc(drv_ctx.extradata_info.buffer_size);
4117 if (!m_other_extradata) {
4118 DEBUG_PRINT_ERROR("Failed to alloc memory\n");
4119 return OMX_ErrorInsufficientResources;
4120 }
4121 }
Arun Menon906de572013-06-18 17:01:40 -07004122 return OMX_ErrorNone;
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004123}
4124
Arun Menon906de572013-06-18 17:01:40 -07004125void omx_vdec::free_extradata()
4126{
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004127#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07004128 if (drv_ctx.extradata_info.uaddr) {
4129 munmap((void *)drv_ctx.extradata_info.uaddr, drv_ctx.extradata_info.size);
4130 close(drv_ctx.extradata_info.ion.fd_ion_data.fd);
4131 free_ion_memory(&drv_ctx.extradata_info.ion);
4132 }
4133 memset(&drv_ctx.extradata_info, 0, sizeof(drv_ctx.extradata_info));
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004134#endif
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05304135 if (m_other_extradata) {
4136 free(m_other_extradata);
4137 m_other_extradata = NULL;
4138 }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004139}
4140
Shalaj Jain273b3e02012-06-22 19:08:03 -07004141OMX_ERRORTYPE omx_vdec::use_output_buffer(
Arun Menon906de572013-06-18 17:01:40 -07004142 OMX_IN OMX_HANDLETYPE hComp,
4143 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
4144 OMX_IN OMX_U32 port,
4145 OMX_IN OMX_PTR appData,
4146 OMX_IN OMX_U32 bytes,
4147 OMX_IN OMX_U8* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004148{
Arun Menon906de572013-06-18 17:01:40 -07004149 OMX_ERRORTYPE eRet = OMX_ErrorNone;
4150 OMX_BUFFERHEADERTYPE *bufHdr= NULL; // buffer header
4151 unsigned i= 0; // Temporary counter
4152 struct vdec_setbuffer_cmd setbuffers;
4153 OMX_PTR privateAppData = NULL;
4154 private_handle_t *handle = NULL;
4155 OMX_U8 *buff = buffer;
4156 struct v4l2_buffer buf;
4157 struct v4l2_plane plane[VIDEO_MAX_PLANES];
4158 int extra_idx = 0;
Deva Ramasubramanian614f79e2012-08-10 21:42:10 -07004159
Arun Menon906de572013-06-18 17:01:40 -07004160 if (!m_out_mem_ptr) {
4161 DEBUG_PRINT_HIGH("Use_op_buf:Allocating output headers");
4162 eRet = allocate_output_headers();
4163 if (eRet == OMX_ErrorNone)
4164 eRet = allocate_extradata();
Shalaj Jain273b3e02012-06-22 19:08:03 -07004165 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004166
Arun Menon906de572013-06-18 17:01:40 -07004167 if (eRet == OMX_ErrorNone) {
4168 for (i=0; i< drv_ctx.op_buf.actualcount; i++) {
4169 if (BITMASK_ABSENT(&m_out_bm_count,i)) {
4170 break;
4171 }
4172 }
4173 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004174
Arun Menon906de572013-06-18 17:01:40 -07004175 if (i >= drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004176 DEBUG_PRINT_ERROR("Already using %d o/p buffers", drv_ctx.op_buf.actualcount);
Arun Menon906de572013-06-18 17:01:40 -07004177 eRet = OMX_ErrorInsufficientResources;
4178 }
4179
Arun Menonbdb80b02013-08-12 17:45:54 -07004180 if (dynamic_buf_mode) {
4181 *bufferHdr = (m_out_mem_ptr + i );
4182 (*bufferHdr)->pBuffer = NULL;
4183 if (i == (drv_ctx.op_buf.actualcount -1) && !streaming[CAPTURE_PORT]) {
4184 enum v4l2_buf_type buf_type;
4185 int rr = 0;
4186 buf_type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
4187 if (rr = ioctl(drv_ctx.video_driver_fd, VIDIOC_STREAMON,&buf_type)) {
4188 DEBUG_PRINT_ERROR("STREAMON FAILED : %d", rr);
4189 return OMX_ErrorInsufficientResources;
4190 } else {
4191 streaming[CAPTURE_PORT] = true;
4192 DEBUG_PRINT_LOW("STREAMON Successful");
4193 }
4194 }
4195 BITMASK_SET(&m_out_bm_count,i);
4196 (*bufferHdr)->pAppPrivate = appData;
4197 (*bufferHdr)->pBuffer = buffer;
4198 (*bufferHdr)->nAllocLen = sizeof(struct VideoDecoderOutputMetaData);
4199 return eRet;
4200 }
Arun Menon906de572013-06-18 17:01:40 -07004201 if (eRet == OMX_ErrorNone) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07004202#if defined(_ANDROID_HONEYCOMB_) || defined(_ANDROID_ICS_)
Arun Menon906de572013-06-18 17:01:40 -07004203 if (m_enable_android_native_buffers) {
4204 if (m_use_android_native_buffers) {
4205 UseAndroidNativeBufferParams *params = (UseAndroidNativeBufferParams *)appData;
4206 sp<android_native_buffer_t> nBuf = params->nativeBuffer;
4207 handle = (private_handle_t *)nBuf->handle;
4208 privateAppData = params->pAppPrivate;
4209 } else {
4210 handle = (private_handle_t *)buff;
4211 privateAppData = appData;
4212 }
Deva Ramasubramanian614f79e2012-08-10 21:42:10 -07004213
Arun Menon906de572013-06-18 17:01:40 -07004214 if ((OMX_U32)handle->size < drv_ctx.op_buf.buffer_size) {
4215 DEBUG_PRINT_ERROR("Insufficient sized buffer given for playback,"
4216 " expected %u, got %lu",
4217 drv_ctx.op_buf.buffer_size, (OMX_U32)handle->size);
4218 return OMX_ErrorBadParameter;
4219 }
Deva Ramasubramanian614f79e2012-08-10 21:42:10 -07004220
Arun Menon906de572013-06-18 17:01:40 -07004221 if (!m_use_android_native_buffers) {
4222 if (!secure_mode) {
4223 buff = (OMX_U8*)mmap(0, handle->size,
4224 PROT_READ|PROT_WRITE, MAP_SHARED, handle->fd, 0);
4225 if (buff == MAP_FAILED) {
4226 DEBUG_PRINT_ERROR("Failed to mmap pmem with fd = %d, size = %d", handle->fd, handle->size);
4227 return OMX_ErrorInsufficientResources;
4228 }
Deva Ramasubramanian614f79e2012-08-10 21:42:10 -07004229 }
4230 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004231#if defined(_ANDROID_ICS_)
Arun Menon906de572013-06-18 17:01:40 -07004232 native_buffer[i].nativehandle = handle;
4233 native_buffer[i].privatehandle = handle;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004234#endif
Arun Menon906de572013-06-18 17:01:40 -07004235 if (!handle) {
4236 DEBUG_PRINT_ERROR("Native Buffer handle is NULL");
4237 return OMX_ErrorBadParameter;
4238 }
4239 drv_ctx.ptr_outputbuffer[i].pmem_fd = handle->fd;
4240 drv_ctx.ptr_outputbuffer[i].offset = 0;
4241 drv_ctx.ptr_outputbuffer[i].bufferaddr = buff;
4242 drv_ctx.ptr_outputbuffer[i].buffer_len = drv_ctx.op_buf.buffer_size;
4243 drv_ctx.ptr_outputbuffer[i].mmaped_size = handle->size;
4244 } else
4245#endif
4246
4247 if (!ouput_egl_buffers && !m_use_output_pmem) {
4248#ifdef USE_ION
4249 drv_ctx.op_buf_ion_info[i].ion_device_fd = alloc_map_ion_memory(
4250 drv_ctx.op_buf.buffer_size,drv_ctx.op_buf.alignment,
4251 &drv_ctx.op_buf_ion_info[i].ion_alloc_data,
4252 &drv_ctx.op_buf_ion_info[i].fd_ion_data, secure_mode ? ION_SECURE : 0);
4253 if (drv_ctx.op_buf_ion_info[i].ion_device_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004254 DEBUG_PRINT_ERROR("ION device fd is bad %d", drv_ctx.op_buf_ion_info[i].ion_device_fd);
Arun Menon906de572013-06-18 17:01:40 -07004255 return OMX_ErrorInsufficientResources;
4256 }
4257 drv_ctx.ptr_outputbuffer[i].pmem_fd = \
4258 drv_ctx.op_buf_ion_info[i].fd_ion_data.fd;
4259#else
4260 drv_ctx.ptr_outputbuffer[i].pmem_fd = \
4261 open (MEM_DEVICE,O_RDWR);
4262
4263 if (drv_ctx.ptr_outputbuffer[i].pmem_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004264 DEBUG_PRINT_ERROR("ION/pmem buffer fd is bad %d", drv_ctx.ptr_outputbuffer[i].pmem_fd);
Arun Menon906de572013-06-18 17:01:40 -07004265 return OMX_ErrorInsufficientResources;
4266 }
4267
4268 /* FIXME: why is this code even here? We already open MEM_DEVICE a few lines above */
4269 if (drv_ctx.ptr_outputbuffer[i].pmem_fd == 0) {
4270 drv_ctx.ptr_outputbuffer[i].pmem_fd = \
4271 open (MEM_DEVICE,O_RDWR);
4272 if (drv_ctx.ptr_outputbuffer[i].pmem_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004273 DEBUG_PRINT_ERROR("ION/pmem buffer fd is bad %d", drv_ctx.ptr_outputbuffer[i].pmem_fd);
Arun Menon906de572013-06-18 17:01:40 -07004274 return OMX_ErrorInsufficientResources;
4275 }
4276 }
4277
4278 if (!align_pmem_buffers(drv_ctx.ptr_outputbuffer[i].pmem_fd,
4279 drv_ctx.op_buf.buffer_size,
4280 drv_ctx.op_buf.alignment)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004281 DEBUG_PRINT_ERROR("align_pmem_buffers() failed");
Arun Menon906de572013-06-18 17:01:40 -07004282 close(drv_ctx.ptr_outputbuffer[i].pmem_fd);
4283 return OMX_ErrorInsufficientResources;
4284 }
4285#endif
4286 if (!secure_mode) {
4287 drv_ctx.ptr_outputbuffer[i].bufferaddr =
4288 (unsigned char *)mmap(NULL, drv_ctx.op_buf.buffer_size,
4289 PROT_READ|PROT_WRITE, MAP_SHARED,
4290 drv_ctx.ptr_outputbuffer[i].pmem_fd,0);
4291 if (drv_ctx.ptr_outputbuffer[i].bufferaddr == MAP_FAILED) {
4292 close(drv_ctx.ptr_outputbuffer[i].pmem_fd);
4293#ifdef USE_ION
4294 free_ion_memory(&drv_ctx.op_buf_ion_info[i]);
4295#endif
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004296 DEBUG_PRINT_ERROR("Unable to mmap output buffer");
Arun Menon906de572013-06-18 17:01:40 -07004297 return OMX_ErrorInsufficientResources;
4298 }
4299 }
4300 drv_ctx.ptr_outputbuffer[i].offset = 0;
4301 privateAppData = appData;
4302 } else {
4303
4304 DEBUG_PRINT_LOW("Use_op_buf: out_pmem=%d",m_use_output_pmem);
4305 if (!appData || !bytes ) {
4306 if (!secure_mode && !buffer) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004307 DEBUG_PRINT_ERROR("Bad parameters for use buffer in EGL image case");
Arun Menon906de572013-06-18 17:01:40 -07004308 return OMX_ErrorBadParameter;
4309 }
4310 }
4311
4312 OMX_QCOM_PLATFORM_PRIVATE_LIST *pmem_list;
4313 OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *pmem_info;
4314 pmem_list = (OMX_QCOM_PLATFORM_PRIVATE_LIST*) appData;
4315 if (!pmem_list->entryList || !pmem_list->entryList->entry ||
4316 !pmem_list->nEntries ||
4317 pmem_list->entryList->type != OMX_QCOM_PLATFORM_PRIVATE_PMEM) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004318 DEBUG_PRINT_ERROR("Pmem info not valid in use buffer");
Arun Menon906de572013-06-18 17:01:40 -07004319 return OMX_ErrorBadParameter;
4320 }
4321 pmem_info = (OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *)
4322 pmem_list->entryList->entry;
4323 DEBUG_PRINT_LOW("vdec: use buf: pmem_fd=0x%lx",
4324 pmem_info->pmem_fd);
4325 drv_ctx.ptr_outputbuffer[i].pmem_fd = pmem_info->pmem_fd;
4326 drv_ctx.ptr_outputbuffer[i].offset = pmem_info->offset;
4327 drv_ctx.ptr_outputbuffer[i].bufferaddr = buff;
4328 drv_ctx.ptr_outputbuffer[i].mmaped_size =
4329 drv_ctx.ptr_outputbuffer[i].buffer_len = drv_ctx.op_buf.buffer_size;
4330 privateAppData = appData;
4331 }
4332 m_pmem_info[i].offset = drv_ctx.ptr_outputbuffer[i].offset;
4333 m_pmem_info[i].pmem_fd = drv_ctx.ptr_outputbuffer[i].pmem_fd;
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05304334 m_pmem_info[i].size = drv_ctx.ptr_outputbuffer[i].buffer_len;
4335 m_pmem_info[i].mapped_size = drv_ctx.ptr_outputbuffer[i].mmaped_size;
4336 m_pmem_info[i].buffer = drv_ctx.ptr_outputbuffer[i].bufferaddr;
Arun Menon906de572013-06-18 17:01:40 -07004337
4338 *bufferHdr = (m_out_mem_ptr + i );
4339 if (secure_mode)
4340 drv_ctx.ptr_outputbuffer[i].bufferaddr = *bufferHdr;
4341 //setbuffers.buffer_type = VDEC_BUFFER_TYPE_OUTPUT;
4342 memcpy (&setbuffers.buffer,&drv_ctx.ptr_outputbuffer[i],
4343 sizeof (vdec_bufferpayload));
4344
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004345 DEBUG_PRINT_HIGH("Set the Output Buffer Idx: %d Addr: %p, pmem_fd=0x%x", i,
Arun Menon906de572013-06-18 17:01:40 -07004346 drv_ctx.ptr_outputbuffer[i].bufferaddr,
4347 drv_ctx.ptr_outputbuffer[i].pmem_fd );
4348
4349 buf.index = i;
4350 buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
4351 buf.memory = V4L2_MEMORY_USERPTR;
4352 plane[0].length = drv_ctx.op_buf.buffer_size;
4353 plane[0].m.userptr = (unsigned long)drv_ctx.ptr_outputbuffer[i].bufferaddr -
4354 (unsigned long)drv_ctx.ptr_outputbuffer[i].offset;
4355 plane[0].reserved[0] = drv_ctx.ptr_outputbuffer[i].pmem_fd;
4356 plane[0].reserved[1] = drv_ctx.ptr_outputbuffer[i].offset;
4357 plane[0].data_offset = 0;
4358 extra_idx = EXTRADATA_IDX(drv_ctx.num_planes);
4359 if (extra_idx && (extra_idx < VIDEO_MAX_PLANES)) {
4360 plane[extra_idx].length = drv_ctx.extradata_info.buffer_size;
4361 plane[extra_idx].m.userptr = (long unsigned int) (drv_ctx.extradata_info.uaddr + i * drv_ctx.extradata_info.buffer_size);
4362#ifdef USE_ION
4363 plane[extra_idx].reserved[0] = drv_ctx.extradata_info.ion.fd_ion_data.fd;
4364#endif
4365 plane[extra_idx].reserved[1] = i * drv_ctx.extradata_info.buffer_size;
4366 plane[extra_idx].data_offset = 0;
4367 } else if (extra_idx >= VIDEO_MAX_PLANES) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004368 DEBUG_PRINT_ERROR("Extradata index is more than allowed: %d", extra_idx);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004369 return OMX_ErrorBadParameter;
4370 }
Arun Menon906de572013-06-18 17:01:40 -07004371 buf.m.planes = plane;
4372 buf.length = drv_ctx.num_planes;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004373
Arun Menon906de572013-06-18 17:01:40 -07004374 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_PREPARE_BUF, &buf)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004375 DEBUG_PRINT_ERROR("Failed to prepare bufs");
Arun Menon906de572013-06-18 17:01:40 -07004376 /*TODO: How to handle this case */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004377 return OMX_ErrorInsufficientResources;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004378 }
4379
Arun Menon906de572013-06-18 17:01:40 -07004380 if (i == (drv_ctx.op_buf.actualcount -1) && !streaming[CAPTURE_PORT]) {
4381 enum v4l2_buf_type buf_type;
4382 buf_type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
4383 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_STREAMON,&buf_type)) {
4384 return OMX_ErrorInsufficientResources;
4385 } else {
4386 streaming[CAPTURE_PORT] = true;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004387 DEBUG_PRINT_LOW("STREAMON Successful");
Shalaj Jain273b3e02012-06-22 19:08:03 -07004388 }
4389 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004390
Arun Menon906de572013-06-18 17:01:40 -07004391 (*bufferHdr)->nAllocLen = drv_ctx.op_buf.buffer_size;
4392 if (m_enable_android_native_buffers) {
4393 DEBUG_PRINT_LOW("setting pBuffer to private_handle_t %p", handle);
4394 (*bufferHdr)->pBuffer = (OMX_U8 *)handle;
4395 } else {
4396 (*bufferHdr)->pBuffer = buff;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004397 }
Arun Menon906de572013-06-18 17:01:40 -07004398 (*bufferHdr)->pAppPrivate = privateAppData;
4399 BITMASK_SET(&m_out_bm_count,i);
4400 }
4401 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004402}
4403
4404/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004405 FUNCTION
4406 omx_vdec::use_input_heap_buffers
Shalaj Jain273b3e02012-06-22 19:08:03 -07004407
Arun Menon906de572013-06-18 17:01:40 -07004408 DESCRIPTION
4409 OMX Use Buffer Heap allocation method implementation.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004410
Arun Menon906de572013-06-18 17:01:40 -07004411 PARAMETERS
4412 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004413
Arun Menon906de572013-06-18 17:01:40 -07004414 RETURN VALUE
4415 OMX Error None , if everything successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004416
Arun Menon906de572013-06-18 17:01:40 -07004417 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004418OMX_ERRORTYPE omx_vdec::use_input_heap_buffers(
Arun Menon906de572013-06-18 17:01:40 -07004419 OMX_IN OMX_HANDLETYPE hComp,
4420 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
4421 OMX_IN OMX_U32 port,
4422 OMX_IN OMX_PTR appData,
4423 OMX_IN OMX_U32 bytes,
4424 OMX_IN OMX_U8* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004425{
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004426 DEBUG_PRINT_LOW("Inside %s, %p", __FUNCTION__, buffer);
Arun Menon906de572013-06-18 17:01:40 -07004427 OMX_ERRORTYPE eRet = OMX_ErrorNone;
4428 if (!m_inp_heap_ptr)
4429 m_inp_heap_ptr = (OMX_BUFFERHEADERTYPE*)
4430 calloc( (sizeof(OMX_BUFFERHEADERTYPE)),
4431 drv_ctx.ip_buf.actualcount);
4432 if (!m_phdr_pmem_ptr)
4433 m_phdr_pmem_ptr = (OMX_BUFFERHEADERTYPE**)
4434 calloc( (sizeof(OMX_BUFFERHEADERTYPE*)),
4435 drv_ctx.ip_buf.actualcount);
4436 if (!m_inp_heap_ptr || !m_phdr_pmem_ptr) {
4437 DEBUG_PRINT_ERROR("Insufficent memory");
4438 eRet = OMX_ErrorInsufficientResources;
4439 } else if (m_in_alloc_cnt < drv_ctx.ip_buf.actualcount) {
4440 input_use_buffer = true;
4441 memset(&m_inp_heap_ptr[m_in_alloc_cnt], 0, sizeof(OMX_BUFFERHEADERTYPE));
4442 m_inp_heap_ptr[m_in_alloc_cnt].pBuffer = buffer;
4443 m_inp_heap_ptr[m_in_alloc_cnt].nAllocLen = bytes;
4444 m_inp_heap_ptr[m_in_alloc_cnt].pAppPrivate = appData;
4445 m_inp_heap_ptr[m_in_alloc_cnt].nInputPortIndex = (OMX_U32) OMX_DirInput;
4446 m_inp_heap_ptr[m_in_alloc_cnt].nOutputPortIndex = (OMX_U32) OMX_DirMax;
4447 *bufferHdr = &m_inp_heap_ptr[m_in_alloc_cnt];
4448 eRet = allocate_input_buffer(hComp, &m_phdr_pmem_ptr[m_in_alloc_cnt], port, appData, bytes);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004449 DEBUG_PRINT_HIGH("Heap buffer(%p) Pmem buffer(%p)", *bufferHdr, m_phdr_pmem_ptr[m_in_alloc_cnt]);
Arun Menon906de572013-06-18 17:01:40 -07004450 if (!m_input_free_q.insert_entry((unsigned)m_phdr_pmem_ptr[m_in_alloc_cnt],
4451 (unsigned)NULL, (unsigned)NULL)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004452 DEBUG_PRINT_ERROR("ERROR:Free_q is full");
Arun Menon906de572013-06-18 17:01:40 -07004453 return OMX_ErrorInsufficientResources;
4454 }
4455 m_in_alloc_cnt++;
4456 } else {
4457 DEBUG_PRINT_ERROR("All i/p buffers have been set!");
4458 eRet = OMX_ErrorInsufficientResources;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004459 }
Arun Menon906de572013-06-18 17:01:40 -07004460 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004461}
4462
4463/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004464 FUNCTION
4465 omx_vdec::UseBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07004466
Arun Menon906de572013-06-18 17:01:40 -07004467 DESCRIPTION
4468 OMX Use Buffer method implementation.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004469
Arun Menon906de572013-06-18 17:01:40 -07004470 PARAMETERS
4471 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004472
Arun Menon906de572013-06-18 17:01:40 -07004473 RETURN VALUE
4474 OMX Error None , if everything successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004475
Arun Menon906de572013-06-18 17:01:40 -07004476 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004477OMX_ERRORTYPE omx_vdec::use_buffer(
Arun Menon906de572013-06-18 17:01:40 -07004478 OMX_IN OMX_HANDLETYPE hComp,
4479 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
4480 OMX_IN OMX_U32 port,
4481 OMX_IN OMX_PTR appData,
4482 OMX_IN OMX_U32 bytes,
4483 OMX_IN OMX_U8* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004484{
Arun Menon906de572013-06-18 17:01:40 -07004485 OMX_ERRORTYPE error = OMX_ErrorNone;
4486 struct vdec_setbuffer_cmd setbuffers;
4487
4488 if (bufferHdr == NULL || bytes == 0) {
4489 if (!secure_mode && buffer == NULL) {
4490 DEBUG_PRINT_ERROR("bad param 0x%p %ld 0x%p",bufferHdr, bytes, buffer);
4491 return OMX_ErrorBadParameter;
4492 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004493 }
Arun Menon906de572013-06-18 17:01:40 -07004494 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004495 DEBUG_PRINT_ERROR("Use Buffer in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07004496 return OMX_ErrorInvalidState;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004497 }
Arun Menon906de572013-06-18 17:01:40 -07004498 if (port == OMX_CORE_INPUT_PORT_INDEX)
4499 error = use_input_heap_buffers(hComp, bufferHdr, port, appData, bytes, buffer);
4500 else if (port == OMX_CORE_OUTPUT_PORT_INDEX)
4501 error = use_output_buffer(hComp,bufferHdr,port,appData,bytes,buffer); //not tested
4502 else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004503 DEBUG_PRINT_ERROR("Error: Invalid Port Index received %d",(int)port);
Arun Menon906de572013-06-18 17:01:40 -07004504 error = OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004505 }
Arun Menon906de572013-06-18 17:01:40 -07004506 DEBUG_PRINT_LOW("Use Buffer: port %lu, buffer %p, eRet %d", port, *bufferHdr, error);
4507 if (error == OMX_ErrorNone) {
4508 if (allocate_done() && BITMASK_PRESENT(&m_flags,OMX_COMPONENT_IDLE_PENDING)) {
4509 // Send the callback now
4510 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_IDLE_PENDING);
4511 post_event(OMX_CommandStateSet,OMX_StateIdle,
4512 OMX_COMPONENT_GENERATE_EVENT);
4513 }
4514 if (port == OMX_CORE_INPUT_PORT_INDEX && m_inp_bPopulated &&
4515 BITMASK_PRESENT(&m_flags,OMX_COMPONENT_INPUT_ENABLE_PENDING)) {
4516 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_INPUT_ENABLE_PENDING);
4517 post_event(OMX_CommandPortEnable,
4518 OMX_CORE_INPUT_PORT_INDEX,
4519 OMX_COMPONENT_GENERATE_EVENT);
4520 } else if (port == OMX_CORE_OUTPUT_PORT_INDEX && m_out_bPopulated &&
4521 BITMASK_PRESENT(&m_flags,OMX_COMPONENT_OUTPUT_ENABLE_PENDING)) {
4522 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_OUTPUT_ENABLE_PENDING);
4523 post_event(OMX_CommandPortEnable,
4524 OMX_CORE_OUTPUT_PORT_INDEX,
4525 OMX_COMPONENT_GENERATE_EVENT);
4526 }
4527 }
4528 return error;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004529}
4530
4531OMX_ERRORTYPE omx_vdec::free_input_buffer(unsigned int bufferindex,
Arun Menon906de572013-06-18 17:01:40 -07004532 OMX_BUFFERHEADERTYPE *pmem_bufferHdr)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004533{
Arun Menon906de572013-06-18 17:01:40 -07004534 if (m_inp_heap_ptr && !input_use_buffer && arbitrary_bytes) {
4535 if (m_inp_heap_ptr[bufferindex].pBuffer)
4536 free(m_inp_heap_ptr[bufferindex].pBuffer);
4537 m_inp_heap_ptr[bufferindex].pBuffer = NULL;
4538 }
4539 if (pmem_bufferHdr)
4540 free_input_buffer(pmem_bufferHdr);
4541 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004542}
4543
4544OMX_ERRORTYPE omx_vdec::free_input_buffer(OMX_BUFFERHEADERTYPE *bufferHdr)
4545{
Arun Menon906de572013-06-18 17:01:40 -07004546 unsigned int index = 0;
4547 if (bufferHdr == NULL || m_inp_mem_ptr == NULL) {
4548 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004549 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004550
Arun Menon906de572013-06-18 17:01:40 -07004551 index = bufferHdr - m_inp_mem_ptr;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004552 DEBUG_PRINT_LOW("Free Input Buffer index = %d",index);
Arun Menon906de572013-06-18 17:01:40 -07004553
4554 if (index < drv_ctx.ip_buf.actualcount && drv_ctx.ptr_inputbuffer) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004555 DEBUG_PRINT_LOW("Free Input Buffer index = %d",index);
Arun Menon906de572013-06-18 17:01:40 -07004556 if (drv_ctx.ptr_inputbuffer[index].pmem_fd > 0) {
4557 struct vdec_setbuffer_cmd setbuffers;
4558 setbuffers.buffer_type = VDEC_BUFFER_TYPE_INPUT;
4559 memcpy (&setbuffers.buffer,&drv_ctx.ptr_inputbuffer[index],
4560 sizeof (vdec_bufferpayload));
4561 if (!secure_mode) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004562 DEBUG_PRINT_LOW("unmap the input buffer fd=%d",
Arun Menon906de572013-06-18 17:01:40 -07004563 drv_ctx.ptr_inputbuffer[index].pmem_fd);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004564 DEBUG_PRINT_LOW("unmap the input buffer size=%d address = %p",
Arun Menon906de572013-06-18 17:01:40 -07004565 drv_ctx.ptr_inputbuffer[index].mmaped_size,
4566 drv_ctx.ptr_inputbuffer[index].bufferaddr);
4567 munmap (drv_ctx.ptr_inputbuffer[index].bufferaddr,
4568 drv_ctx.ptr_inputbuffer[index].mmaped_size);
4569 }
4570 close (drv_ctx.ptr_inputbuffer[index].pmem_fd);
4571 drv_ctx.ptr_inputbuffer[index].pmem_fd = -1;
4572 if (m_desc_buffer_ptr && m_desc_buffer_ptr[index].buf_addr) {
4573 free(m_desc_buffer_ptr[index].buf_addr);
4574 m_desc_buffer_ptr[index].buf_addr = NULL;
4575 m_desc_buffer_ptr[index].desc_data_size = 0;
4576 }
4577#ifdef USE_ION
4578 free_ion_memory(&drv_ctx.ip_buf_ion_info[index]);
4579#endif
4580 }
4581 }
4582
4583 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004584}
4585
4586OMX_ERRORTYPE omx_vdec::free_output_buffer(OMX_BUFFERHEADERTYPE *bufferHdr)
4587{
Arun Menon906de572013-06-18 17:01:40 -07004588 unsigned int index = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004589
Arun Menon906de572013-06-18 17:01:40 -07004590 if (bufferHdr == NULL || m_out_mem_ptr == NULL) {
4591 return OMX_ErrorBadParameter;
4592 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004593
Arun Menon906de572013-06-18 17:01:40 -07004594 index = bufferHdr - m_out_mem_ptr;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004595 DEBUG_PRINT_LOW("Free ouput Buffer index = %d",index);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004596
Arun Menon906de572013-06-18 17:01:40 -07004597 if (index < drv_ctx.op_buf.actualcount
4598 && drv_ctx.ptr_outputbuffer) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004599 DEBUG_PRINT_LOW("Free ouput Buffer index = %d addr = %p", index,
Arun Menon906de572013-06-18 17:01:40 -07004600 drv_ctx.ptr_outputbuffer[index].bufferaddr);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004601
Arun Menon906de572013-06-18 17:01:40 -07004602 struct vdec_setbuffer_cmd setbuffers;
4603 setbuffers.buffer_type = VDEC_BUFFER_TYPE_OUTPUT;
4604 memcpy (&setbuffers.buffer,&drv_ctx.ptr_outputbuffer[index],
4605 sizeof (vdec_bufferpayload));
Praveen Chavan61e5d162013-11-01 02:49:19 -07004606
4607 if (!dynamic_buf_mode) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07004608#ifdef _ANDROID_
Praveen Chavan61e5d162013-11-01 02:49:19 -07004609 if (m_enable_android_native_buffers) {
Arun Menon906de572013-06-18 17:01:40 -07004610 if (!secure_mode) {
Praveen Chavan61e5d162013-11-01 02:49:19 -07004611 if (drv_ctx.ptr_outputbuffer[index].pmem_fd > 0) {
4612 munmap(drv_ctx.ptr_outputbuffer[index].bufferaddr,
4613 drv_ctx.ptr_outputbuffer[index].mmaped_size);
4614 }
Arun Menon906de572013-06-18 17:01:40 -07004615 }
Praveen Chavan61e5d162013-11-01 02:49:19 -07004616 drv_ctx.ptr_outputbuffer[index].pmem_fd = -1;
4617 } else {
4618#endif
4619 if (drv_ctx.ptr_outputbuffer[0].pmem_fd > 0 && !ouput_egl_buffers && !m_use_output_pmem) {
4620 if (!secure_mode) {
4621 DEBUG_PRINT_LOW("\n unmap the output buffer fd = %d",
4622 drv_ctx.ptr_outputbuffer[0].pmem_fd);
4623 DEBUG_PRINT_LOW("\n unmap the ouput buffer size=%d address = %p",
4624 drv_ctx.ptr_outputbuffer[0].mmaped_size * drv_ctx.op_buf.actualcount,
4625 drv_ctx.ptr_outputbuffer[0].bufferaddr);
4626 munmap (drv_ctx.ptr_outputbuffer[0].bufferaddr,
4627 drv_ctx.ptr_outputbuffer[0].mmaped_size * drv_ctx.op_buf.actualcount);
4628 }
4629 close (drv_ctx.ptr_outputbuffer[0].pmem_fd);
4630 drv_ctx.ptr_outputbuffer[0].pmem_fd = -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004631#ifdef USE_ION
Praveen Chavan61e5d162013-11-01 02:49:19 -07004632 free_ion_memory(&drv_ctx.op_buf_ion_info[0]);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004633#endif
Praveen Chavan61e5d162013-11-01 02:49:19 -07004634 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004635#ifdef _ANDROID_
Praveen Chavan61e5d162013-11-01 02:49:19 -07004636 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004637#endif
Praveen Chavan61e5d162013-11-01 02:49:19 -07004638 } //!dynamic_buf_mode
Arun Menon906de572013-06-18 17:01:40 -07004639 if (release_output_done()) {
4640 free_extradata();
4641 }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07004642 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004643
Arun Menon906de572013-06-18 17:01:40 -07004644 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004645
4646}
4647
4648OMX_ERRORTYPE omx_vdec::allocate_input_heap_buffer(OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07004649 OMX_BUFFERHEADERTYPE **bufferHdr,
4650 OMX_U32 port,
4651 OMX_PTR appData,
4652 OMX_U32 bytes)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004653{
Arun Menon906de572013-06-18 17:01:40 -07004654 OMX_BUFFERHEADERTYPE *input = NULL;
4655 unsigned char *buf_addr = NULL;
4656 OMX_ERRORTYPE eRet = OMX_ErrorNone;
4657 unsigned i = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004658
Arun Menon906de572013-06-18 17:01:40 -07004659 /* Sanity Check*/
4660 if (bufferHdr == NULL) {
4661 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004662 }
4663
Arun Menon906de572013-06-18 17:01:40 -07004664 if (m_inp_heap_ptr == NULL) {
4665 m_inp_heap_ptr = (OMX_BUFFERHEADERTYPE*) \
4666 calloc( (sizeof(OMX_BUFFERHEADERTYPE)),
4667 drv_ctx.ip_buf.actualcount);
4668 m_phdr_pmem_ptr = (OMX_BUFFERHEADERTYPE**) \
4669 calloc( (sizeof(OMX_BUFFERHEADERTYPE*)),
4670 drv_ctx.ip_buf.actualcount);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004671
Arun Menon906de572013-06-18 17:01:40 -07004672 if (m_inp_heap_ptr == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004673 DEBUG_PRINT_ERROR("m_inp_heap_ptr Allocation failed ");
Arun Menon906de572013-06-18 17:01:40 -07004674 return OMX_ErrorInsufficientResources;
4675 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004676 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004677
Arun Menon906de572013-06-18 17:01:40 -07004678 /*Find a Free index*/
4679 for (i=0; i< drv_ctx.ip_buf.actualcount; i++) {
4680 if (BITMASK_ABSENT(&m_heap_inp_bm_count,i)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004681 DEBUG_PRINT_LOW("Free Input Buffer Index %d",i);
Arun Menon906de572013-06-18 17:01:40 -07004682 break;
4683 }
4684 }
4685
4686 if (i < drv_ctx.ip_buf.actualcount) {
4687 buf_addr = (unsigned char *)malloc (drv_ctx.ip_buf.buffer_size);
4688
4689 if (buf_addr == NULL) {
4690 return OMX_ErrorInsufficientResources;
4691 }
4692
4693 *bufferHdr = (m_inp_heap_ptr + i);
4694 input = *bufferHdr;
4695 BITMASK_SET(&m_heap_inp_bm_count,i);
4696
4697 input->pBuffer = (OMX_U8 *)buf_addr;
4698 input->nSize = sizeof(OMX_BUFFERHEADERTYPE);
4699 input->nVersion.nVersion = OMX_SPEC_VERSION;
4700 input->nAllocLen = drv_ctx.ip_buf.buffer_size;
4701 input->pAppPrivate = appData;
4702 input->nInputPortIndex = OMX_CORE_INPUT_PORT_INDEX;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004703 DEBUG_PRINT_LOW("Address of Heap Buffer %p",*bufferHdr );
Arun Menon906de572013-06-18 17:01:40 -07004704 eRet = allocate_input_buffer(hComp,&m_phdr_pmem_ptr [i],port,appData,bytes);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004705 DEBUG_PRINT_LOW("Address of Pmem Buffer %p",m_phdr_pmem_ptr[i]);
Arun Menon906de572013-06-18 17:01:40 -07004706 /*Add the Buffers to freeq*/
4707 if (!m_input_free_q.insert_entry((unsigned)m_phdr_pmem_ptr[i],
4708 (unsigned)NULL, (unsigned)NULL)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004709 DEBUG_PRINT_ERROR("ERROR:Free_q is full");
Arun Menon906de572013-06-18 17:01:40 -07004710 return OMX_ErrorInsufficientResources;
4711 }
4712 } else {
4713 return OMX_ErrorBadParameter;
4714 }
4715
4716 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004717
4718}
4719
4720
4721/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004722 FUNCTION
4723 omx_vdec::AllocateInputBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07004724
Arun Menon906de572013-06-18 17:01:40 -07004725 DESCRIPTION
4726 Helper function for allocate buffer in the input pin
Shalaj Jain273b3e02012-06-22 19:08:03 -07004727
Arun Menon906de572013-06-18 17:01:40 -07004728 PARAMETERS
4729 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004730
Arun Menon906de572013-06-18 17:01:40 -07004731 RETURN VALUE
4732 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07004733
Arun Menon906de572013-06-18 17:01:40 -07004734 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004735OMX_ERRORTYPE omx_vdec::allocate_input_buffer(
Arun Menon906de572013-06-18 17:01:40 -07004736 OMX_IN OMX_HANDLETYPE hComp,
4737 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
4738 OMX_IN OMX_U32 port,
4739 OMX_IN OMX_PTR appData,
4740 OMX_IN OMX_U32 bytes)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004741{
4742
Arun Menon906de572013-06-18 17:01:40 -07004743 OMX_ERRORTYPE eRet = OMX_ErrorNone;
4744 struct vdec_setbuffer_cmd setbuffers;
4745 OMX_BUFFERHEADERTYPE *input = NULL;
4746 unsigned i = 0;
4747 unsigned char *buf_addr = NULL;
4748 int pmem_fd = -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004749
Arun Menon906de572013-06-18 17:01:40 -07004750 if (bytes != drv_ctx.ip_buf.buffer_size) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004751 DEBUG_PRINT_LOW("Requested Size is wrong %lu epected is %d",
Arun Menon906de572013-06-18 17:01:40 -07004752 bytes, drv_ctx.ip_buf.buffer_size);
4753 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004754 }
4755
Arun Menon906de572013-06-18 17:01:40 -07004756 if (!m_inp_mem_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004757 DEBUG_PRINT_HIGH("Allocate i/p buffer Header: Cnt(%d) Sz(%d)",
Arun Menon906de572013-06-18 17:01:40 -07004758 drv_ctx.ip_buf.actualcount,
4759 drv_ctx.ip_buf.buffer_size);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004760
Arun Menon906de572013-06-18 17:01:40 -07004761 m_inp_mem_ptr = (OMX_BUFFERHEADERTYPE*) \
4762 calloc( (sizeof(OMX_BUFFERHEADERTYPE)), drv_ctx.ip_buf.actualcount);
4763
4764 if (m_inp_mem_ptr == NULL) {
4765 return OMX_ErrorInsufficientResources;
4766 }
4767
4768 drv_ctx.ptr_inputbuffer = (struct vdec_bufferpayload *) \
4769 calloc ((sizeof (struct vdec_bufferpayload)),drv_ctx.ip_buf.actualcount);
4770
4771 if (drv_ctx.ptr_inputbuffer == NULL) {
4772 return OMX_ErrorInsufficientResources;
4773 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004774#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07004775 drv_ctx.ip_buf_ion_info = (struct vdec_ion *) \
4776 calloc ((sizeof (struct vdec_ion)),drv_ctx.ip_buf.actualcount);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004777
Arun Menon906de572013-06-18 17:01:40 -07004778 if (drv_ctx.ip_buf_ion_info == NULL) {
4779 return OMX_ErrorInsufficientResources;
4780 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004781#endif
4782
Arun Menon906de572013-06-18 17:01:40 -07004783 for (i=0; i < drv_ctx.ip_buf.actualcount; i++) {
4784 drv_ctx.ptr_inputbuffer [i].pmem_fd = -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004785#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07004786 drv_ctx.ip_buf_ion_info[i].ion_device_fd = -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004787#endif
Shalaj Jain273b3e02012-06-22 19:08:03 -07004788 }
4789 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004790
Arun Menon906de572013-06-18 17:01:40 -07004791 for (i=0; i< drv_ctx.ip_buf.actualcount; i++) {
4792 if (BITMASK_ABSENT(&m_inp_bm_count,i)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004793 DEBUG_PRINT_LOW("Free Input Buffer Index %d",i);
Arun Menon906de572013-06-18 17:01:40 -07004794 break;
4795 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004796 }
Arun Menon906de572013-06-18 17:01:40 -07004797
4798 if (i < drv_ctx.ip_buf.actualcount) {
4799 struct v4l2_buffer buf;
4800 struct v4l2_plane plane;
4801 int rc;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004802 DEBUG_PRINT_LOW("Allocate input Buffer");
Arun Menon906de572013-06-18 17:01:40 -07004803#ifdef USE_ION
4804 drv_ctx.ip_buf_ion_info[i].ion_device_fd = alloc_map_ion_memory(
4805 drv_ctx.ip_buf.buffer_size,drv_ctx.op_buf.alignment,
4806 &drv_ctx.ip_buf_ion_info[i].ion_alloc_data,
4807 &drv_ctx.ip_buf_ion_info[i].fd_ion_data, secure_mode ? ION_SECURE : 0);
4808 if (drv_ctx.ip_buf_ion_info[i].ion_device_fd < 0) {
4809 return OMX_ErrorInsufficientResources;
4810 }
4811 pmem_fd = drv_ctx.ip_buf_ion_info[i].fd_ion_data.fd;
4812#else
4813 pmem_fd = open (MEM_DEVICE,O_RDWR);
4814
4815 if (pmem_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004816 DEBUG_PRINT_ERROR("open failed for pmem/adsp for input buffer");
Arun Menon906de572013-06-18 17:01:40 -07004817 return OMX_ErrorInsufficientResources;
4818 }
4819
4820 if (pmem_fd == 0) {
4821 pmem_fd = open (MEM_DEVICE,O_RDWR);
4822
4823 if (pmem_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004824 DEBUG_PRINT_ERROR("open failed for pmem/adsp for input buffer");
Arun Menon906de572013-06-18 17:01:40 -07004825 return OMX_ErrorInsufficientResources;
4826 }
4827 }
4828
4829 if (!align_pmem_buffers(pmem_fd, drv_ctx.ip_buf.buffer_size,
4830 drv_ctx.ip_buf.alignment)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004831 DEBUG_PRINT_ERROR("align_pmem_buffers() failed");
Arun Menon906de572013-06-18 17:01:40 -07004832 close(pmem_fd);
4833 return OMX_ErrorInsufficientResources;
4834 }
4835#endif
4836 if (!secure_mode) {
4837 buf_addr = (unsigned char *)mmap(NULL,
4838 drv_ctx.ip_buf.buffer_size,
4839 PROT_READ|PROT_WRITE, MAP_SHARED, pmem_fd, 0);
4840
4841 if (buf_addr == MAP_FAILED) {
4842 close(pmem_fd);
4843#ifdef USE_ION
4844 free_ion_memory(&drv_ctx.ip_buf_ion_info[i]);
4845#endif
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004846 DEBUG_PRINT_ERROR("Map Failed to allocate input buffer");
Arun Menon906de572013-06-18 17:01:40 -07004847 return OMX_ErrorInsufficientResources;
4848 }
4849 }
4850 *bufferHdr = (m_inp_mem_ptr + i);
4851 if (secure_mode)
4852 drv_ctx.ptr_inputbuffer [i].bufferaddr = *bufferHdr;
4853 else
4854 drv_ctx.ptr_inputbuffer [i].bufferaddr = buf_addr;
4855 drv_ctx.ptr_inputbuffer [i].pmem_fd = pmem_fd;
4856 drv_ctx.ptr_inputbuffer [i].buffer_len = drv_ctx.ip_buf.buffer_size;
4857 drv_ctx.ptr_inputbuffer [i].mmaped_size = drv_ctx.ip_buf.buffer_size;
4858 drv_ctx.ptr_inputbuffer [i].offset = 0;
4859
4860
4861 buf.index = i;
4862 buf.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
4863 buf.memory = V4L2_MEMORY_USERPTR;
4864 plane.bytesused = 0;
4865 plane.length = drv_ctx.ptr_inputbuffer [i].mmaped_size;
4866 plane.m.userptr = (unsigned long)drv_ctx.ptr_inputbuffer[i].bufferaddr;
4867 plane.reserved[0] =drv_ctx.ptr_inputbuffer [i].pmem_fd;
4868 plane.reserved[1] = 0;
4869 plane.data_offset = drv_ctx.ptr_inputbuffer[i].offset;
4870 buf.m.planes = &plane;
4871 buf.length = 1;
4872
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004873 DEBUG_PRINT_LOW("Set the input Buffer Idx: %d Addr: %p", i,
Arun Menon906de572013-06-18 17:01:40 -07004874 drv_ctx.ptr_inputbuffer[i].bufferaddr);
4875
4876 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_PREPARE_BUF, &buf);
4877
4878 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004879 DEBUG_PRINT_ERROR("Failed to prepare bufs");
Arun Menon906de572013-06-18 17:01:40 -07004880 /*TODO: How to handle this case */
4881 return OMX_ErrorInsufficientResources;
4882 }
4883
4884 input = *bufferHdr;
4885 BITMASK_SET(&m_inp_bm_count,i);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004886 DEBUG_PRINT_LOW("Buffer address %p of pmem",*bufferHdr);
Arun Menon906de572013-06-18 17:01:40 -07004887 if (secure_mode)
4888 input->pBuffer = (OMX_U8 *)drv_ctx.ptr_inputbuffer [i].pmem_fd;
4889 else
4890 input->pBuffer = (OMX_U8 *)buf_addr;
4891 input->nSize = sizeof(OMX_BUFFERHEADERTYPE);
4892 input->nVersion.nVersion = OMX_SPEC_VERSION;
4893 input->nAllocLen = drv_ctx.ip_buf.buffer_size;
4894 input->pAppPrivate = appData;
4895 input->nInputPortIndex = OMX_CORE_INPUT_PORT_INDEX;
4896 input->pInputPortPrivate = (void *)&drv_ctx.ptr_inputbuffer [i];
4897
4898 if (drv_ctx.disable_dmx) {
4899 eRet = allocate_desc_buffer(i);
4900 }
4901 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004902 DEBUG_PRINT_ERROR("ERROR:Input Buffer Index not found");
Arun Menon906de572013-06-18 17:01:40 -07004903 eRet = OMX_ErrorInsufficientResources;
4904 }
4905 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004906}
4907
4908
4909/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07004910 FUNCTION
4911 omx_vdec::AllocateOutputBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07004912
Arun Menon906de572013-06-18 17:01:40 -07004913 DESCRIPTION
4914 Helper fn for AllocateBuffer in the output pin
Shalaj Jain273b3e02012-06-22 19:08:03 -07004915
Arun Menon906de572013-06-18 17:01:40 -07004916 PARAMETERS
4917 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004918
Arun Menon906de572013-06-18 17:01:40 -07004919 RETURN VALUE
4920 OMX Error None if everything went well.
Shalaj Jain273b3e02012-06-22 19:08:03 -07004921
Arun Menon906de572013-06-18 17:01:40 -07004922 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07004923OMX_ERRORTYPE omx_vdec::allocate_output_buffer(
Arun Menon906de572013-06-18 17:01:40 -07004924 OMX_IN OMX_HANDLETYPE hComp,
4925 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
4926 OMX_IN OMX_U32 port,
4927 OMX_IN OMX_PTR appData,
4928 OMX_IN OMX_U32 bytes)
Shalaj Jain273b3e02012-06-22 19:08:03 -07004929{
Arun Menon906de572013-06-18 17:01:40 -07004930 OMX_ERRORTYPE eRet = OMX_ErrorNone;
4931 OMX_BUFFERHEADERTYPE *bufHdr= NULL; // buffer header
4932 unsigned i= 0; // Temporary counter
4933 struct vdec_setbuffer_cmd setbuffers;
4934 int extra_idx = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004935#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07004936 int ion_device_fd =-1;
4937 struct ion_allocation_data ion_alloc_data;
4938 struct ion_fd_data fd_ion_data;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004939#endif
Arun Menon906de572013-06-18 17:01:40 -07004940 if (!m_out_mem_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004941 DEBUG_PRINT_HIGH("Allocate o/p buffer Header: Cnt(%d) Sz(%d)",
Arun Menon906de572013-06-18 17:01:40 -07004942 drv_ctx.op_buf.actualcount,
4943 drv_ctx.op_buf.buffer_size);
4944 int nBufHdrSize = 0;
4945 int nPlatformEntrySize = 0;
4946 int nPlatformListSize = 0;
4947 int nPMEMInfoSize = 0;
4948 int pmem_fd = -1;
4949 unsigned char *pmem_baseaddress = NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004950
Arun Menon906de572013-06-18 17:01:40 -07004951 OMX_QCOM_PLATFORM_PRIVATE_LIST *pPlatformList;
4952 OMX_QCOM_PLATFORM_PRIVATE_ENTRY *pPlatformEntry;
4953 OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *pPMEMInfo;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004954
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004955 DEBUG_PRINT_LOW("Allocating First Output Buffer(%d)",
Arun Menon906de572013-06-18 17:01:40 -07004956 drv_ctx.op_buf.actualcount);
4957 nBufHdrSize = drv_ctx.op_buf.actualcount *
4958 sizeof(OMX_BUFFERHEADERTYPE);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004959
Arun Menon906de572013-06-18 17:01:40 -07004960 nPMEMInfoSize = drv_ctx.op_buf.actualcount *
4961 sizeof(OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO);
4962 nPlatformListSize = drv_ctx.op_buf.actualcount *
4963 sizeof(OMX_QCOM_PLATFORM_PRIVATE_LIST);
4964 nPlatformEntrySize = drv_ctx.op_buf.actualcount *
4965 sizeof(OMX_QCOM_PLATFORM_PRIVATE_ENTRY);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004966
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004967 DEBUG_PRINT_LOW("TotalBufHdr %d BufHdrSize %d PMEM %d PL %d",nBufHdrSize,
Arun Menon906de572013-06-18 17:01:40 -07004968 sizeof(OMX_BUFFERHEADERTYPE),
4969 nPMEMInfoSize,
4970 nPlatformListSize);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004971 DEBUG_PRINT_LOW("PE %d OutputBuffer Count %d",nPlatformEntrySize,
Arun Menon906de572013-06-18 17:01:40 -07004972 drv_ctx.op_buf.actualcount);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004973#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07004974 ion_device_fd = alloc_map_ion_memory(
4975 drv_ctx.op_buf.buffer_size * drv_ctx.op_buf.actualcount,
4976 drv_ctx.op_buf.alignment,
4977 &ion_alloc_data, &fd_ion_data, secure_mode ? ION_SECURE : 0);
4978 if (ion_device_fd < 0) {
4979 return OMX_ErrorInsufficientResources;
4980 }
4981 pmem_fd = fd_ion_data.fd;
Shalaj Jain273b3e02012-06-22 19:08:03 -07004982#else
Arun Menon906de572013-06-18 17:01:40 -07004983 pmem_fd = open (MEM_DEVICE,O_RDWR);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004984
Arun Menon906de572013-06-18 17:01:40 -07004985 if (pmem_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004986 DEBUG_PRINT_ERROR("ERROR:pmem fd for output buffer %d",
Arun Menon906de572013-06-18 17:01:40 -07004987 drv_ctx.op_buf.buffer_size);
4988 return OMX_ErrorInsufficientResources;
4989 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07004990
Arun Menon906de572013-06-18 17:01:40 -07004991 if (pmem_fd == 0) {
4992 pmem_fd = open (MEM_DEVICE,O_RDWR);
Shalaj Jain273b3e02012-06-22 19:08:03 -07004993
Arun Menon906de572013-06-18 17:01:40 -07004994 if (pmem_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07004995 DEBUG_PRINT_ERROR("ERROR:pmem fd for output buffer %d",
Arun Menon906de572013-06-18 17:01:40 -07004996 drv_ctx.op_buf.buffer_size);
4997 return OMX_ErrorInsufficientResources;
4998 }
4999 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005000
Arun Menon906de572013-06-18 17:01:40 -07005001 if (!align_pmem_buffers(pmem_fd, drv_ctx.op_buf.buffer_size *
5002 drv_ctx.op_buf.actualcount,
5003 drv_ctx.op_buf.alignment)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005004 DEBUG_PRINT_ERROR("align_pmem_buffers() failed");
Arun Menon906de572013-06-18 17:01:40 -07005005 close(pmem_fd);
5006 return OMX_ErrorInsufficientResources;
5007 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005008#endif
Arun Menon906de572013-06-18 17:01:40 -07005009 if (!secure_mode) {
5010 pmem_baseaddress = (unsigned char *)mmap(NULL,
5011 (drv_ctx.op_buf.buffer_size *
5012 drv_ctx.op_buf.actualcount),
5013 PROT_READ|PROT_WRITE,MAP_SHARED,pmem_fd,0);
5014 if (pmem_baseaddress == MAP_FAILED) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005015 DEBUG_PRINT_ERROR("MMAP failed for Size %d",
Arun Menon906de572013-06-18 17:01:40 -07005016 drv_ctx.op_buf.buffer_size);
5017 close(pmem_fd);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005018#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07005019 free_ion_memory(&drv_ctx.op_buf_ion_info[i]);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005020#endif
Arun Menon906de572013-06-18 17:01:40 -07005021 return OMX_ErrorInsufficientResources;
5022 }
5023 }
5024 m_out_mem_ptr = (OMX_BUFFERHEADERTYPE *)calloc(nBufHdrSize,1);
5025 // Alloc mem for platform specific info
5026 char *pPtr=NULL;
5027 pPtr = (char*) calloc(nPlatformListSize + nPlatformEntrySize +
5028 nPMEMInfoSize,1);
5029 drv_ctx.ptr_outputbuffer = (struct vdec_bufferpayload *)\
5030 calloc (sizeof(struct vdec_bufferpayload),
5031 drv_ctx.op_buf.actualcount);
5032 drv_ctx.ptr_respbuffer = (struct vdec_output_frameinfo *)\
5033 calloc (sizeof (struct vdec_output_frameinfo),
5034 drv_ctx.op_buf.actualcount);
5035#ifdef USE_ION
5036 drv_ctx.op_buf_ion_info = (struct vdec_ion *)\
5037 calloc (sizeof(struct vdec_ion),
5038 drv_ctx.op_buf.actualcount);
5039#endif
5040
5041 if (m_out_mem_ptr && pPtr && drv_ctx.ptr_outputbuffer
5042 && drv_ctx.ptr_respbuffer) {
5043 drv_ctx.ptr_outputbuffer[0].mmaped_size =
5044 (drv_ctx.op_buf.buffer_size *
5045 drv_ctx.op_buf.actualcount);
5046 bufHdr = m_out_mem_ptr;
5047 m_platform_list = (OMX_QCOM_PLATFORM_PRIVATE_LIST *)(pPtr);
5048 m_platform_entry= (OMX_QCOM_PLATFORM_PRIVATE_ENTRY *)
5049 (((char *) m_platform_list) + nPlatformListSize);
5050 m_pmem_info = (OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *)
5051 (((char *) m_platform_entry) + nPlatformEntrySize);
5052 pPlatformList = m_platform_list;
5053 pPlatformEntry = m_platform_entry;
5054 pPMEMInfo = m_pmem_info;
5055
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005056 DEBUG_PRINT_LOW("Memory Allocation Succeeded for OUT port%p",m_out_mem_ptr);
Arun Menon906de572013-06-18 17:01:40 -07005057
5058 // Settting the entire storage nicely
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005059 DEBUG_PRINT_LOW("bHdr %p OutMem %p PE %p",bufHdr, m_out_mem_ptr,pPlatformEntry);
5060 DEBUG_PRINT_LOW(" Pmem Info = %p",pPMEMInfo);
Arun Menon906de572013-06-18 17:01:40 -07005061 for (i=0; i < drv_ctx.op_buf.actualcount ; i++) {
5062 bufHdr->nSize = sizeof(OMX_BUFFERHEADERTYPE);
5063 bufHdr->nVersion.nVersion = OMX_SPEC_VERSION;
5064 // Set the values when we determine the right HxW param
5065 bufHdr->nAllocLen = bytes;
5066 bufHdr->nFilledLen = 0;
5067 bufHdr->pAppPrivate = appData;
5068 bufHdr->nOutputPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
5069 // Platform specific PMEM Information
5070 // Initialize the Platform Entry
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005071 //DEBUG_PRINT_LOW("Initializing the Platform Entry for %d",i);
Arun Menon906de572013-06-18 17:01:40 -07005072 pPlatformEntry->type = OMX_QCOM_PLATFORM_PRIVATE_PMEM;
5073 pPlatformEntry->entry = pPMEMInfo;
5074 // Initialize the Platform List
5075 pPlatformList->nEntries = 1;
5076 pPlatformList->entryList = pPlatformEntry;
5077 // Keep pBuffer NULL till vdec is opened
5078 bufHdr->pBuffer = NULL;
5079 bufHdr->nOffset = 0;
5080
5081 pPMEMInfo->offset = drv_ctx.op_buf.buffer_size*i;
5082 pPMEMInfo->pmem_fd = 0;
5083 bufHdr->pPlatformPrivate = pPlatformList;
5084
5085 drv_ctx.ptr_outputbuffer[i].pmem_fd = pmem_fd;
5086 m_pmem_info[i].pmem_fd = pmem_fd;
5087#ifdef USE_ION
5088 drv_ctx.op_buf_ion_info[i].ion_device_fd = ion_device_fd;
5089 drv_ctx.op_buf_ion_info[i].ion_alloc_data = ion_alloc_data;
5090 drv_ctx.op_buf_ion_info[i].fd_ion_data = fd_ion_data;
5091#endif
5092
5093 /*Create a mapping between buffers*/
5094 bufHdr->pOutputPortPrivate = &drv_ctx.ptr_respbuffer[i];
5095 drv_ctx.ptr_respbuffer[i].client_data = (void *)\
5096 &drv_ctx.ptr_outputbuffer[i];
5097 drv_ctx.ptr_outputbuffer[i].offset = drv_ctx.op_buf.buffer_size*i;
5098 drv_ctx.ptr_outputbuffer[i].bufferaddr =
5099 pmem_baseaddress + (drv_ctx.op_buf.buffer_size*i);
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05305100 m_pmem_info[i].size = drv_ctx.ptr_outputbuffer[i].buffer_len;
5101 m_pmem_info[i].mapped_size = drv_ctx.ptr_outputbuffer[i].mmaped_size;
5102 m_pmem_info[i].buffer = drv_ctx.ptr_outputbuffer[i].bufferaddr;
Arun Menon906de572013-06-18 17:01:40 -07005103
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005104 DEBUG_PRINT_LOW("pmem_fd = %d offset = %d address = %p",
Arun Menon906de572013-06-18 17:01:40 -07005105 pmem_fd, drv_ctx.ptr_outputbuffer[i].offset,
5106 drv_ctx.ptr_outputbuffer[i].bufferaddr);
5107 // Move the buffer and buffer header pointers
5108 bufHdr++;
5109 pPMEMInfo++;
5110 pPlatformEntry++;
5111 pPlatformList++;
5112 }
5113 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005114 DEBUG_PRINT_ERROR("Output buf mem alloc failed[0x%p][0x%p]",\
Arun Menon906de572013-06-18 17:01:40 -07005115 m_out_mem_ptr, pPtr);
5116 if (m_out_mem_ptr) {
5117 free(m_out_mem_ptr);
5118 m_out_mem_ptr = NULL;
5119 }
5120 if (pPtr) {
5121 free(pPtr);
5122 pPtr = NULL;
5123 }
5124 if (drv_ctx.ptr_outputbuffer) {
5125 free(drv_ctx.ptr_outputbuffer);
5126 drv_ctx.ptr_outputbuffer = NULL;
5127 }
5128 if (drv_ctx.ptr_respbuffer) {
5129 free(drv_ctx.ptr_respbuffer);
5130 drv_ctx.ptr_respbuffer = NULL;
5131 }
5132#ifdef USE_ION
5133 if (drv_ctx.op_buf_ion_info) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005134 DEBUG_PRINT_LOW("Free o/p ion context");
Arun Menon906de572013-06-18 17:01:40 -07005135 free(drv_ctx.op_buf_ion_info);
5136 drv_ctx.op_buf_ion_info = NULL;
5137 }
5138#endif
5139 eRet = OMX_ErrorInsufficientResources;
5140 }
5141 if (eRet == OMX_ErrorNone)
5142 eRet = allocate_extradata();
5143 }
5144
5145 for (i=0; i< drv_ctx.op_buf.actualcount; i++) {
5146 if (BITMASK_ABSENT(&m_out_bm_count,i)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005147 DEBUG_PRINT_LOW("Found a Free Output Buffer %d",i);
Arun Menon906de572013-06-18 17:01:40 -07005148 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005149 }
5150 }
Arun Menon906de572013-06-18 17:01:40 -07005151
5152 if (eRet == OMX_ErrorNone) {
5153 if (i < drv_ctx.op_buf.actualcount) {
5154 struct v4l2_buffer buf;
5155 struct v4l2_plane plane[VIDEO_MAX_PLANES];
5156 int rc;
5157 m_pmem_info[i].offset = drv_ctx.ptr_outputbuffer[i].offset;
5158
5159 drv_ctx.ptr_outputbuffer[i].buffer_len =
5160 drv_ctx.op_buf.buffer_size;
5161
5162 *bufferHdr = (m_out_mem_ptr + i );
5163 if (secure_mode) {
5164 drv_ctx.ptr_outputbuffer[i].bufferaddr = *bufferHdr;
5165 }
5166 drv_ctx.ptr_outputbuffer[i].mmaped_size = drv_ctx.op_buf.buffer_size;
5167
5168 buf.index = i;
5169 buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
5170 buf.memory = V4L2_MEMORY_USERPTR;
5171 plane[0].length = drv_ctx.op_buf.buffer_size;
5172 plane[0].m.userptr = (unsigned long)drv_ctx.ptr_outputbuffer[i].bufferaddr -
5173 (unsigned long)drv_ctx.ptr_outputbuffer[i].offset;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005174#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07005175 plane[0].reserved[0] = drv_ctx.op_buf_ion_info[i].fd_ion_data.fd;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005176#endif
Arun Menon906de572013-06-18 17:01:40 -07005177 plane[0].reserved[1] = drv_ctx.ptr_outputbuffer[i].offset;
5178 plane[0].data_offset = 0;
5179 extra_idx = EXTRADATA_IDX(drv_ctx.num_planes);
5180 if (extra_idx && (extra_idx < VIDEO_MAX_PLANES)) {
5181 plane[extra_idx].length = drv_ctx.extradata_info.buffer_size;
5182 plane[extra_idx].m.userptr = (long unsigned int) (drv_ctx.extradata_info.uaddr + i * drv_ctx.extradata_info.buffer_size);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005183#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07005184 plane[extra_idx].reserved[0] = drv_ctx.extradata_info.ion.fd_ion_data.fd;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005185#endif
Arun Menon906de572013-06-18 17:01:40 -07005186 plane[extra_idx].reserved[1] = i * drv_ctx.extradata_info.buffer_size;
5187 plane[extra_idx].data_offset = 0;
5188 } else if (extra_idx >= VIDEO_MAX_PLANES) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005189 DEBUG_PRINT_ERROR("Extradata index higher than allowed: %d", extra_idx);
Arun Menon906de572013-06-18 17:01:40 -07005190 return OMX_ErrorBadParameter;
5191 }
5192 buf.m.planes = plane;
5193 buf.length = drv_ctx.num_planes;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005194 DEBUG_PRINT_LOW("Set the Output Buffer Idx: %d Addr: %p", i, drv_ctx.ptr_outputbuffer[i].bufferaddr);
Arun Menon906de572013-06-18 17:01:40 -07005195 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_PREPARE_BUF, &buf);
5196 if (rc) {
5197 /*TODO: How to handle this case */
5198 return OMX_ErrorInsufficientResources;
5199 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005200
Arun Menon906de572013-06-18 17:01:40 -07005201 if (i == (drv_ctx.op_buf.actualcount -1 ) && !streaming[CAPTURE_PORT]) {
5202 enum v4l2_buf_type buf_type;
5203 buf_type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
5204 rc=ioctl(drv_ctx.video_driver_fd, VIDIOC_STREAMON,&buf_type);
5205 if (rc) {
5206 return OMX_ErrorInsufficientResources;
5207 } else {
5208 streaming[CAPTURE_PORT] = true;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005209 DEBUG_PRINT_LOW("STREAMON Successful");
Arun Menon906de572013-06-18 17:01:40 -07005210 }
5211 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005212
Arun Menon906de572013-06-18 17:01:40 -07005213 (*bufferHdr)->pBuffer = (OMX_U8*)drv_ctx.ptr_outputbuffer[i].bufferaddr;
5214 (*bufferHdr)->pAppPrivate = appData;
5215 BITMASK_SET(&m_out_bm_count,i);
5216 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005217 DEBUG_PRINT_ERROR("All the Output Buffers have been Allocated ; Returning Insufficient");
Arun Menon906de572013-06-18 17:01:40 -07005218 eRet = OMX_ErrorInsufficientResources;
5219 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005220 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005221
Arun Menon906de572013-06-18 17:01:40 -07005222 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005223}
5224
5225
5226// AllocateBuffer -- API Call
5227/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005228 FUNCTION
5229 omx_vdec::AllocateBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07005230
Arun Menon906de572013-06-18 17:01:40 -07005231 DESCRIPTION
5232 Returns zero if all the buffers released..
Shalaj Jain273b3e02012-06-22 19:08:03 -07005233
Arun Menon906de572013-06-18 17:01:40 -07005234 PARAMETERS
5235 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005236
Arun Menon906de572013-06-18 17:01:40 -07005237 RETURN VALUE
5238 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07005239
Arun Menon906de572013-06-18 17:01:40 -07005240 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005241OMX_ERRORTYPE omx_vdec::allocate_buffer(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07005242 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
5243 OMX_IN OMX_U32 port,
5244 OMX_IN OMX_PTR appData,
5245 OMX_IN OMX_U32 bytes)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005246{
5247 unsigned i = 0;
5248 OMX_ERRORTYPE eRet = OMX_ErrorNone; // OMX return type
5249
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005250 DEBUG_PRINT_LOW("Allocate buffer on port %d", (int)port);
Arun Menon906de572013-06-18 17:01:40 -07005251 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005252 DEBUG_PRINT_ERROR("Allocate Buf in Invalid State");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005253 return OMX_ErrorInvalidState;
5254 }
5255
Arun Menon906de572013-06-18 17:01:40 -07005256 if (port == OMX_CORE_INPUT_PORT_INDEX) {
5257 if (arbitrary_bytes) {
5258 eRet = allocate_input_heap_buffer (hComp,bufferHdr,port,appData,bytes);
5259 } else {
5260 eRet = allocate_input_buffer(hComp,bufferHdr,port,appData,bytes);
5261 }
5262 } else if (port == OMX_CORE_OUTPUT_PORT_INDEX) {
Vinay Kaliada4f4422013-01-09 10:45:03 -08005263 eRet = client_buffers.allocate_buffers_color_convert(hComp,bufferHdr,port,
5264 appData,bytes);
Arun Menon906de572013-06-18 17:01:40 -07005265 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005266 DEBUG_PRINT_ERROR("Error: Invalid Port Index received %d",(int)port);
Arun Menon906de572013-06-18 17:01:40 -07005267 eRet = OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005268 }
5269 DEBUG_PRINT_LOW("Checking for Output Allocate buffer Done");
Arun Menon906de572013-06-18 17:01:40 -07005270 if (eRet == OMX_ErrorNone) {
5271 if (allocate_done()) {
5272 if (BITMASK_PRESENT(&m_flags,OMX_COMPONENT_IDLE_PENDING)) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07005273 // Send the callback now
5274 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_IDLE_PENDING);
5275 post_event(OMX_CommandStateSet,OMX_StateIdle,
Arun Menon906de572013-06-18 17:01:40 -07005276 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005277 }
5278 }
Arun Menon906de572013-06-18 17:01:40 -07005279 if (port == OMX_CORE_INPUT_PORT_INDEX && m_inp_bPopulated) {
5280 if (BITMASK_PRESENT(&m_flags,OMX_COMPONENT_INPUT_ENABLE_PENDING)) {
5281 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_INPUT_ENABLE_PENDING);
5282 post_event(OMX_CommandPortEnable,
Shalaj Jain273b3e02012-06-22 19:08:03 -07005283 OMX_CORE_INPUT_PORT_INDEX,
5284 OMX_COMPONENT_GENERATE_EVENT);
Arun Menon906de572013-06-18 17:01:40 -07005285 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005286 }
Arun Menon906de572013-06-18 17:01:40 -07005287 if (port == OMX_CORE_OUTPUT_PORT_INDEX && m_out_bPopulated) {
5288 if (BITMASK_PRESENT(&m_flags,OMX_COMPONENT_OUTPUT_ENABLE_PENDING)) {
5289 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_OUTPUT_ENABLE_PENDING);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005290 post_event(OMX_CommandPortEnable,
Arun Menon906de572013-06-18 17:01:40 -07005291 OMX_CORE_OUTPUT_PORT_INDEX,
5292 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005293 }
5294 }
5295 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005296 DEBUG_PRINT_LOW("Allocate Buffer exit with ret Code %d",eRet);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005297 return eRet;
5298}
5299
5300// Free Buffer - API call
5301/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005302 FUNCTION
5303 omx_vdec::FreeBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07005304
Arun Menon906de572013-06-18 17:01:40 -07005305 DESCRIPTION
Shalaj Jain273b3e02012-06-22 19:08:03 -07005306
Arun Menon906de572013-06-18 17:01:40 -07005307 PARAMETERS
5308 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005309
Arun Menon906de572013-06-18 17:01:40 -07005310 RETURN VALUE
5311 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07005312
Arun Menon906de572013-06-18 17:01:40 -07005313 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005314OMX_ERRORTYPE omx_vdec::free_buffer(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07005315 OMX_IN OMX_U32 port,
5316 OMX_IN OMX_BUFFERHEADERTYPE* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005317{
5318 OMX_ERRORTYPE eRet = OMX_ErrorNone;
5319 unsigned int nPortIndex;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005320 DEBUG_PRINT_LOW("In for decoder free_buffer");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005321
Arun Menon906de572013-06-18 17:01:40 -07005322 if (m_state == OMX_StateIdle &&
5323 (BITMASK_PRESENT(&m_flags ,OMX_COMPONENT_LOADING_PENDING))) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005324 DEBUG_PRINT_LOW(" free buffer while Component in Loading pending");
Arun Menon906de572013-06-18 17:01:40 -07005325 } else if ((m_inp_bEnabled == OMX_FALSE && port == OMX_CORE_INPUT_PORT_INDEX)||
5326 (m_out_bEnabled == OMX_FALSE && port == OMX_CORE_OUTPUT_PORT_INDEX)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005327 DEBUG_PRINT_LOW("Free Buffer while port %lu disabled", port);
Arun Menon906de572013-06-18 17:01:40 -07005328 } else if ((port == OMX_CORE_INPUT_PORT_INDEX &&
5329 BITMASK_PRESENT(&m_flags, OMX_COMPONENT_INPUT_ENABLE_PENDING)) ||
5330 (port == OMX_CORE_OUTPUT_PORT_INDEX &&
5331 BITMASK_PRESENT(&m_flags, OMX_COMPONENT_OUTPUT_ENABLE_PENDING))) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005332 DEBUG_PRINT_LOW("Free Buffer while port %lu enable pending", port);
Arun Menon906de572013-06-18 17:01:40 -07005333 } else if (m_state == OMX_StateExecuting || m_state == OMX_StatePause) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005334 DEBUG_PRINT_ERROR("Invalid state to free buffer,ports need to be disabled");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005335 post_event(OMX_EventError,
Arun Menon906de572013-06-18 17:01:40 -07005336 OMX_ErrorPortUnpopulated,
5337 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005338
5339 return OMX_ErrorIncorrectStateOperation;
Arun Menon906de572013-06-18 17:01:40 -07005340 } else if (m_state != OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005341 DEBUG_PRINT_ERROR("Invalid state to free buffer,port lost Buffers");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005342 post_event(OMX_EventError,
Arun Menon906de572013-06-18 17:01:40 -07005343 OMX_ErrorPortUnpopulated,
5344 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005345 }
5346
Arun Menon906de572013-06-18 17:01:40 -07005347 if (port == OMX_CORE_INPUT_PORT_INDEX) {
5348 /*Check if arbitrary bytes*/
5349 if (!arbitrary_bytes && !input_use_buffer)
5350 nPortIndex = buffer - m_inp_mem_ptr;
5351 else
5352 nPortIndex = buffer - m_inp_heap_ptr;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005353
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005354 DEBUG_PRINT_LOW("free_buffer on i/p port - Port idx %d", nPortIndex);
Arun Menon906de572013-06-18 17:01:40 -07005355 if (nPortIndex < drv_ctx.ip_buf.actualcount) {
5356 // Clear the bit associated with it.
5357 BITMASK_CLEAR(&m_inp_bm_count,nPortIndex);
5358 BITMASK_CLEAR(&m_heap_inp_bm_count,nPortIndex);
5359 if (input_use_buffer == true) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07005360
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005361 DEBUG_PRINT_LOW("Free pmem Buffer index %d",nPortIndex);
Arun Menon906de572013-06-18 17:01:40 -07005362 if (m_phdr_pmem_ptr)
5363 free_input_buffer(m_phdr_pmem_ptr[nPortIndex]);
5364 } else {
5365 if (arbitrary_bytes) {
5366 if (m_phdr_pmem_ptr)
5367 free_input_buffer(nPortIndex,m_phdr_pmem_ptr[nPortIndex]);
5368 else
5369 free_input_buffer(nPortIndex,NULL);
5370 } else
5371 free_input_buffer(buffer);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005372 }
Arun Menon906de572013-06-18 17:01:40 -07005373 m_inp_bPopulated = OMX_FALSE;
Surajit Podder12aefac2013-08-06 18:43:32 +05305374 if(release_input_done())
5375 release_buffers(this, VDEC_BUFFER_TYPE_INPUT);
Arun Menon906de572013-06-18 17:01:40 -07005376 /*Free the Buffer Header*/
5377 if (release_input_done()) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005378 DEBUG_PRINT_HIGH("ALL input buffers are freed/released");
Arun Menon906de572013-06-18 17:01:40 -07005379 free_input_buffer_header();
5380 }
5381 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005382 DEBUG_PRINT_ERROR("Error: free_buffer ,Port Index Invalid");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005383 eRet = OMX_ErrorBadPortIndex;
5384 }
5385
Arun Menon906de572013-06-18 17:01:40 -07005386 if (BITMASK_PRESENT((&m_flags),OMX_COMPONENT_INPUT_DISABLE_PENDING)
5387 && release_input_done()) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005388 DEBUG_PRINT_LOW("MOVING TO DISABLED STATE");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005389 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_INPUT_DISABLE_PENDING);
5390 post_event(OMX_CommandPortDisable,
Arun Menon906de572013-06-18 17:01:40 -07005391 OMX_CORE_INPUT_PORT_INDEX,
5392 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005393 }
Arun Menon906de572013-06-18 17:01:40 -07005394 } else if (port == OMX_CORE_OUTPUT_PORT_INDEX) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07005395 // check if the buffer is valid
Vinay Kaliada4f4422013-01-09 10:45:03 -08005396 nPortIndex = buffer - client_buffers.get_il_buf_hdr();
Arun Menon906de572013-06-18 17:01:40 -07005397 if (nPortIndex < drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005398 DEBUG_PRINT_LOW("free_buffer on o/p port - Port idx %d", nPortIndex);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005399 // Clear the bit associated with it.
5400 BITMASK_CLEAR(&m_out_bm_count,nPortIndex);
5401 m_out_bPopulated = OMX_FALSE;
Vinay Kaliada4f4422013-01-09 10:45:03 -08005402 client_buffers.free_output_buffer (buffer);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005403
Surajit Podder12aefac2013-08-06 18:43:32 +05305404 if(release_output_done()) {
5405 release_buffers(this, VDEC_BUFFER_TYPE_OUTPUT);
5406 }
Arun Menon906de572013-06-18 17:01:40 -07005407 if (release_output_done()) {
5408 free_output_buffer_header();
Shalaj Jain273b3e02012-06-22 19:08:03 -07005409 }
Arun Menon906de572013-06-18 17:01:40 -07005410 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005411 DEBUG_PRINT_ERROR("Error: free_buffer , Port Index Invalid");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005412 eRet = OMX_ErrorBadPortIndex;
5413 }
Arun Menon906de572013-06-18 17:01:40 -07005414 if (BITMASK_PRESENT((&m_flags),OMX_COMPONENT_OUTPUT_DISABLE_PENDING)
5415 && release_output_done()) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005416 DEBUG_PRINT_LOW("FreeBuffer : If any Disable event pending,post it");
Shalaj Jain273b3e02012-06-22 19:08:03 -07005417
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005418 DEBUG_PRINT_LOW("MOVING TO DISABLED STATE");
Arun Menon906de572013-06-18 17:01:40 -07005419 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_OUTPUT_DISABLE_PENDING);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005420#ifdef _ANDROID_ICS_
Arun Menon906de572013-06-18 17:01:40 -07005421 if (m_enable_android_native_buffers) {
5422 DEBUG_PRINT_LOW("FreeBuffer - outport disabled: reset native buffers");
5423 memset(&native_buffer, 0 ,(sizeof(struct nativebuffer) * MAX_NUM_INPUT_OUTPUT_BUFFERS));
5424 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005425#endif
5426
Arun Menon906de572013-06-18 17:01:40 -07005427 post_event(OMX_CommandPortDisable,
5428 OMX_CORE_OUTPUT_PORT_INDEX,
5429 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005430 }
Arun Menon906de572013-06-18 17:01:40 -07005431 } else {
Shalaj Jain273b3e02012-06-22 19:08:03 -07005432 eRet = OMX_ErrorBadPortIndex;
5433 }
Arun Menon906de572013-06-18 17:01:40 -07005434 if ((eRet == OMX_ErrorNone) &&
5435 (BITMASK_PRESENT(&m_flags ,OMX_COMPONENT_LOADING_PENDING))) {
5436 if (release_done()) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07005437 // Send the callback now
5438 BITMASK_CLEAR((&m_flags),OMX_COMPONENT_LOADING_PENDING);
5439 post_event(OMX_CommandStateSet, OMX_StateLoaded,
Arun Menon906de572013-06-18 17:01:40 -07005440 OMX_COMPONENT_GENERATE_EVENT);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005441 }
5442 }
5443 return eRet;
5444}
5445
5446
5447/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005448 FUNCTION
5449 omx_vdec::EmptyThisBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07005450
Arun Menon906de572013-06-18 17:01:40 -07005451 DESCRIPTION
5452 This routine is used to push the encoded video frames to
5453 the video decoder.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005454
Arun Menon906de572013-06-18 17:01:40 -07005455 PARAMETERS
5456 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005457
Arun Menon906de572013-06-18 17:01:40 -07005458 RETURN VALUE
5459 OMX Error None if everything went successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005460
Arun Menon906de572013-06-18 17:01:40 -07005461 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005462OMX_ERRORTYPE omx_vdec::empty_this_buffer(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07005463 OMX_IN OMX_BUFFERHEADERTYPE* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005464{
Arun Menon906de572013-06-18 17:01:40 -07005465 OMX_ERRORTYPE ret1 = OMX_ErrorNone;
5466 unsigned int nBufferIndex = drv_ctx.ip_buf.actualcount;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005467
Arun Menon906de572013-06-18 17:01:40 -07005468 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005469 DEBUG_PRINT_ERROR("Empty this buffer in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07005470 return OMX_ErrorInvalidState;
5471 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005472
Arun Menon906de572013-06-18 17:01:40 -07005473 if (buffer == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005474 DEBUG_PRINT_ERROR("ERROR:ETB Buffer is NULL");
Arun Menon906de572013-06-18 17:01:40 -07005475 return OMX_ErrorBadParameter;
5476 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005477
Arun Menon906de572013-06-18 17:01:40 -07005478 if (!m_inp_bEnabled) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005479 DEBUG_PRINT_ERROR("ERROR:ETB incorrect state operation, input port is disabled.");
Arun Menon906de572013-06-18 17:01:40 -07005480 return OMX_ErrorIncorrectStateOperation;
5481 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005482
Arun Menon906de572013-06-18 17:01:40 -07005483 if (buffer->nInputPortIndex != OMX_CORE_INPUT_PORT_INDEX) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005484 DEBUG_PRINT_ERROR("ERROR:ETB invalid port in header %lu", buffer->nInputPortIndex);
Arun Menon906de572013-06-18 17:01:40 -07005485 return OMX_ErrorBadPortIndex;
5486 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005487
5488#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -07005489 if (iDivXDrmDecrypt) {
5490 OMX_ERRORTYPE drmErr = iDivXDrmDecrypt->Decrypt(buffer);
5491 if (drmErr != OMX_ErrorNone) {
5492 // this error can be ignored
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005493 DEBUG_PRINT_LOW("ERROR:iDivXDrmDecrypt->Decrypt %d", drmErr);
Arun Menon906de572013-06-18 17:01:40 -07005494 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005495 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005496#endif //_ANDROID_
Arun Menon906de572013-06-18 17:01:40 -07005497 if (perf_flag) {
5498 if (!latency) {
5499 dec_time.stop();
5500 latency = dec_time.processing_time_us();
5501 dec_time.start();
5502 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005503 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005504
Arun Menon906de572013-06-18 17:01:40 -07005505 if (arbitrary_bytes) {
5506 nBufferIndex = buffer - m_inp_heap_ptr;
5507 } else {
5508 if (input_use_buffer == true) {
5509 nBufferIndex = buffer - m_inp_heap_ptr;
5510 m_inp_mem_ptr[nBufferIndex].nFilledLen = m_inp_heap_ptr[nBufferIndex].nFilledLen;
5511 m_inp_mem_ptr[nBufferIndex].nTimeStamp = m_inp_heap_ptr[nBufferIndex].nTimeStamp;
5512 m_inp_mem_ptr[nBufferIndex].nFlags = m_inp_heap_ptr[nBufferIndex].nFlags;
5513 buffer = &m_inp_mem_ptr[nBufferIndex];
5514 DEBUG_PRINT_LOW("Non-Arbitrary mode - buffer address is: malloc %p, pmem%p in Index %d, buffer %p of size %lu",
5515 &m_inp_heap_ptr[nBufferIndex], &m_inp_mem_ptr[nBufferIndex],nBufferIndex, buffer, buffer->nFilledLen);
5516 } else {
5517 nBufferIndex = buffer - m_inp_mem_ptr;
5518 }
5519 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005520
Arun Menon906de572013-06-18 17:01:40 -07005521 if (nBufferIndex > drv_ctx.ip_buf.actualcount ) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005522 DEBUG_PRINT_ERROR("ERROR:ETB nBufferIndex is invalid");
Arun Menon906de572013-06-18 17:01:40 -07005523 return OMX_ErrorBadParameter;
5524 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005525
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07005526 if (buffer->nFlags & OMX_BUFFERFLAG_CODECCONFIG) {
5527 codec_config_flag = true;
5528 DEBUG_PRINT_LOW("%s: codec_config buffer", __FUNCTION__);
5529 }
5530
Arun Menon906de572013-06-18 17:01:40 -07005531 DEBUG_PRINT_LOW("[ETB] BHdr(%p) pBuf(%p) nTS(%lld) nFL(%lu)",
5532 buffer, buffer->pBuffer, buffer->nTimeStamp, buffer->nFilledLen);
5533 if (arbitrary_bytes) {
5534 post_event ((unsigned)hComp,(unsigned)buffer,
Shalaj Jain273b3e02012-06-22 19:08:03 -07005535 OMX_COMPONENT_GENERATE_ETB_ARBITRARY);
Arun Menon906de572013-06-18 17:01:40 -07005536 } else {
Arun Menon906de572013-06-18 17:01:40 -07005537 post_event ((unsigned)hComp,(unsigned)buffer,OMX_COMPONENT_GENERATE_ETB);
5538 }
5539 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005540}
5541
5542/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005543 FUNCTION
5544 omx_vdec::empty_this_buffer_proxy
Shalaj Jain273b3e02012-06-22 19:08:03 -07005545
Arun Menon906de572013-06-18 17:01:40 -07005546 DESCRIPTION
5547 This routine is used to push the encoded video frames to
5548 the video decoder.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005549
Arun Menon906de572013-06-18 17:01:40 -07005550 PARAMETERS
5551 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005552
Arun Menon906de572013-06-18 17:01:40 -07005553 RETURN VALUE
5554 OMX Error None if everything went successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005555
Arun Menon906de572013-06-18 17:01:40 -07005556 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005557OMX_ERRORTYPE omx_vdec::empty_this_buffer_proxy(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07005558 OMX_IN OMX_BUFFERHEADERTYPE* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005559{
Arun Menon906de572013-06-18 17:01:40 -07005560 int push_cnt = 0,i=0;
5561 unsigned nPortIndex = 0;
5562 OMX_ERRORTYPE ret = OMX_ErrorNone;
5563 struct vdec_input_frameinfo frameinfo;
5564 struct vdec_bufferpayload *temp_buffer;
5565 struct vdec_seqheader seq_header;
5566 bool port_setting_changed = true;
5567 bool not_coded_vop = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005568
Arun Menon906de572013-06-18 17:01:40 -07005569 /*Should we generate a Aync error event*/
5570 if (buffer == NULL || buffer->pInputPortPrivate == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005571 DEBUG_PRINT_ERROR("ERROR:empty_this_buffer_proxy is invalid");
Arun Menon906de572013-06-18 17:01:40 -07005572 return OMX_ErrorBadParameter;
5573 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005574
Arun Menon906de572013-06-18 17:01:40 -07005575 nPortIndex = buffer-((OMX_BUFFERHEADERTYPE *)m_inp_mem_ptr);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005576
Arun Menon906de572013-06-18 17:01:40 -07005577 if (nPortIndex > drv_ctx.ip_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005578 DEBUG_PRINT_ERROR("ERROR:empty_this_buffer_proxy invalid nPortIndex[%u]",
Arun Menon906de572013-06-18 17:01:40 -07005579 nPortIndex);
5580 return OMX_ErrorBadParameter;
5581 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005582
Arun Menon906de572013-06-18 17:01:40 -07005583 pending_input_buffers++;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005584
Arun Menon906de572013-06-18 17:01:40 -07005585 /* return zero length and not an EOS buffer */
5586 if (!arbitrary_bytes && (buffer->nFilledLen == 0) &&
5587 ((buffer->nFlags & OMX_BUFFERFLAG_EOS) == 0)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005588 DEBUG_PRINT_HIGH("return zero legth buffer");
Arun Menon906de572013-06-18 17:01:40 -07005589 post_event ((unsigned int)buffer,VDEC_S_SUCCESS,
5590 OMX_COMPONENT_GENERATE_EBD);
5591 return OMX_ErrorNone;
5592 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005593
5594
Arun Menon906de572013-06-18 17:01:40 -07005595 if (codec_type_parse == CODEC_TYPE_MPEG4 || codec_type_parse == CODEC_TYPE_DIVX) {
5596 mp4StreamType psBits;
5597 psBits.data = (unsigned char *)(buffer->pBuffer + buffer->nOffset);
5598 psBits.numBytes = buffer->nFilledLen;
5599 mp4_headerparser.parseHeader(&psBits);
5600 not_coded_vop = mp4_headerparser.is_notcodec_vop(
5601 (buffer->pBuffer + buffer->nOffset),buffer->nFilledLen);
5602 if (not_coded_vop) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005603 DEBUG_PRINT_HIGH("Found Not coded vop len %lu frame number %u",
Arun Menon906de572013-06-18 17:01:40 -07005604 buffer->nFilledLen,frame_count);
5605 if (buffer->nFlags & OMX_BUFFERFLAG_EOS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005606 DEBUG_PRINT_HIGH("Eos and Not coded Vop set len to zero");
Arun Menon906de572013-06-18 17:01:40 -07005607 not_coded_vop = false;
5608 buffer->nFilledLen = 0;
5609 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005610 }
5611 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005612
Arun Menon906de572013-06-18 17:01:40 -07005613 if (input_flush_progress == true
Shalaj Jain273b3e02012-06-22 19:08:03 -07005614
Arun Menon906de572013-06-18 17:01:40 -07005615 || not_coded_vop
Shalaj Jain273b3e02012-06-22 19:08:03 -07005616
Arun Menon906de572013-06-18 17:01:40 -07005617 ) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005618 DEBUG_PRINT_LOW("Flush in progress return buffer ");
Arun Menon906de572013-06-18 17:01:40 -07005619 post_event ((unsigned int)buffer,VDEC_S_SUCCESS,
5620 OMX_COMPONENT_GENERATE_EBD);
5621 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005622 }
5623
Arun Menon906de572013-06-18 17:01:40 -07005624 temp_buffer = (struct vdec_bufferpayload *)buffer->pInputPortPrivate;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005625
Surajit Podderd2644d52013-08-28 17:59:06 +05305626 if ((temp_buffer - drv_ctx.ptr_inputbuffer) > (int)drv_ctx.ip_buf.actualcount) {
Arun Menon906de572013-06-18 17:01:40 -07005627 return OMX_ErrorBadParameter;
5628 }
5629 /* If its first frame, H264 codec and reject is true, then parse the nal
5630 and get the profile. Based on this, reject the clip playback */
5631 if (first_frame == 0 && codec_type_parse == CODEC_TYPE_H264 &&
5632 m_reject_avc_1080p_mp) {
5633 first_frame = 1;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005634 DEBUG_PRINT_ERROR("Parse nal to get the profile");
Arun Menon906de572013-06-18 17:01:40 -07005635 h264_parser->parse_nal((OMX_U8*)buffer->pBuffer, buffer->nFilledLen,
5636 NALU_TYPE_SPS);
5637 m_profile = h264_parser->get_profile();
5638 ret = is_video_session_supported();
5639 if (ret) {
5640 post_event ((unsigned int)buffer,VDEC_S_SUCCESS,OMX_COMPONENT_GENERATE_EBD);
5641 post_event(OMX_EventError, OMX_ErrorInvalidState,OMX_COMPONENT_GENERATE_EVENT);
5642 /* Move the state to Invalid to avoid queueing of pending ETB to the driver */
5643 m_state = OMX_StateInvalid;
5644 return OMX_ErrorNone;
5645 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005646 }
5647
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005648 DEBUG_PRINT_LOW("ETBProxy: bufhdr = %p, bufhdr->pBuffer = %p", buffer, buffer->pBuffer);
Arun Menon906de572013-06-18 17:01:40 -07005649 /*for use buffer we need to memcpy the data*/
5650 temp_buffer->buffer_len = buffer->nFilledLen;
5651
5652 if (input_use_buffer) {
5653 if (buffer->nFilledLen <= temp_buffer->buffer_len) {
5654 if (arbitrary_bytes) {
5655 memcpy (temp_buffer->bufferaddr, (buffer->pBuffer + buffer->nOffset),buffer->nFilledLen);
5656 } else {
5657 memcpy (temp_buffer->bufferaddr, (m_inp_heap_ptr[nPortIndex].pBuffer + m_inp_heap_ptr[nPortIndex].nOffset),
5658 buffer->nFilledLen);
5659 }
5660 } else {
5661 return OMX_ErrorBadParameter;
5662 }
5663
5664 }
5665
5666 frameinfo.bufferaddr = temp_buffer->bufferaddr;
5667 frameinfo.client_data = (void *) buffer;
5668 frameinfo.datalen = temp_buffer->buffer_len;
5669 frameinfo.flags = 0;
5670 frameinfo.offset = buffer->nOffset;
5671 frameinfo.pmem_fd = temp_buffer->pmem_fd;
5672 frameinfo.pmem_offset = temp_buffer->offset;
5673 frameinfo.timestamp = buffer->nTimeStamp;
5674 if (drv_ctx.disable_dmx && m_desc_buffer_ptr && m_desc_buffer_ptr[nPortIndex].buf_addr) {
5675 DEBUG_PRINT_LOW("ETB: dmx enabled");
5676 if (m_demux_entries == 0) {
5677 extract_demux_addr_offsets(buffer);
5678 }
5679
5680 DEBUG_PRINT_LOW("ETB: handle_demux_data - entries=%lu",m_demux_entries);
5681 handle_demux_data(buffer);
5682 frameinfo.desc_addr = (OMX_U8 *)m_desc_buffer_ptr[nPortIndex].buf_addr;
5683 frameinfo.desc_size = m_desc_buffer_ptr[nPortIndex].desc_data_size;
5684 } else {
5685 frameinfo.desc_addr = NULL;
5686 frameinfo.desc_size = 0;
5687 }
5688 if (!arbitrary_bytes) {
5689 frameinfo.flags |= buffer->nFlags;
5690 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005691
5692#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -07005693 if (m_debug_timestamp) {
5694 if (arbitrary_bytes) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005695 DEBUG_PRINT_LOW("Inserting TIMESTAMP (%lld) into queue", buffer->nTimeStamp);
Arun Menon906de572013-06-18 17:01:40 -07005696 m_timestamp_list.insert_ts(buffer->nTimeStamp);
5697 } else if (!arbitrary_bytes && !(buffer->nFlags & OMX_BUFFERFLAG_CODECCONFIG)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005698 DEBUG_PRINT_LOW("Inserting TIMESTAMP (%lld) into queue", buffer->nTimeStamp);
Arun Menon906de572013-06-18 17:01:40 -07005699 m_timestamp_list.insert_ts(buffer->nTimeStamp);
5700 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005701 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005702#endif
5703
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07005704log_input_buffers((const char *)temp_buffer->bufferaddr, temp_buffer->buffer_len);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005705
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07005706if (buffer->nFlags & QOMX_VIDEO_BUFFERFLAG_EOSEQ) {
Arun Menon906de572013-06-18 17:01:40 -07005707 frameinfo.flags |= QOMX_VIDEO_BUFFERFLAG_EOSEQ;
5708 buffer->nFlags &= ~QOMX_VIDEO_BUFFERFLAG_EOSEQ;
5709 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005710
Arun Menon906de572013-06-18 17:01:40 -07005711 if (temp_buffer->buffer_len == 0 || (buffer->nFlags & OMX_BUFFERFLAG_EOS)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005712 DEBUG_PRINT_HIGH("Rxd i/p EOS, Notify Driver that EOS has been reached");
Arun Menon906de572013-06-18 17:01:40 -07005713 frameinfo.flags |= VDEC_BUFFERFLAG_EOS;
5714 h264_scratch.nFilledLen = 0;
5715 nal_count = 0;
5716 look_ahead_nal = false;
5717 frame_count = 0;
5718 if (m_frame_parser.mutils)
5719 m_frame_parser.mutils->initialize_frame_checking_environment();
5720 m_frame_parser.flush();
5721 h264_last_au_ts = LLONG_MAX;
5722 h264_last_au_flags = 0;
5723 memset(m_demux_offsets, 0, ( sizeof(OMX_U32) * 8192) );
5724 m_demux_entries = 0;
5725 }
5726 struct v4l2_buffer buf;
5727 struct v4l2_plane plane;
5728 memset( (void *)&buf, 0, sizeof(buf));
5729 memset( (void *)&plane, 0, sizeof(plane));
5730 int rc;
5731 unsigned long print_count;
5732 if (temp_buffer->buffer_len == 0 || (buffer->nFlags & OMX_BUFFERFLAG_EOS)) {
Deva Ramasubramanianc1c7c122013-09-10 21:50:43 -07005733 buf.flags = V4L2_QCOM_BUF_FLAG_EOS;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005734 DEBUG_PRINT_HIGH("INPUT EOS reached") ;
Arun Menon906de572013-06-18 17:01:40 -07005735 }
5736 OMX_ERRORTYPE eRet = OMX_ErrorNone;
5737 buf.index = nPortIndex;
5738 buf.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
5739 buf.memory = V4L2_MEMORY_USERPTR;
5740 plane.bytesused = temp_buffer->buffer_len;
5741 plane.length = drv_ctx.ip_buf.buffer_size;
5742 plane.m.userptr = (unsigned long)temp_buffer->bufferaddr -
5743 (unsigned long)temp_buffer->offset;
5744 plane.reserved[0] = temp_buffer->pmem_fd;
5745 plane.reserved[1] = temp_buffer->offset;
5746 plane.data_offset = 0;
5747 buf.m.planes = &plane;
5748 buf.length = 1;
5749 if (frameinfo.timestamp >= LLONG_MAX) {
5750 buf.flags |= V4L2_QCOM_BUF_TIMESTAMP_INVALID;
5751 }
5752 //assumption is that timestamp is in milliseconds
5753 buf.timestamp.tv_sec = frameinfo.timestamp / 1000000;
5754 buf.timestamp.tv_usec = (frameinfo.timestamp % 1000000);
5755 buf.flags |= (buffer->nFlags & OMX_BUFFERFLAG_CODECCONFIG) ? V4L2_QCOM_BUF_FLAG_CODECCONFIG: 0;
5756 buf.flags |= (buffer->nFlags & OMX_BUFFERFLAG_DECODEONLY) ? V4L2_QCOM_BUF_FLAG_DECODEONLY: 0;
Deva Ramasubramanian46a17952012-08-24 11:35:26 -07005757
Arun Menon906de572013-06-18 17:01:40 -07005758 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_QBUF, &buf);
5759 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005760 DEBUG_PRINT_ERROR("Failed to qbuf Input buffer to driver");
Arun Menon906de572013-06-18 17:01:40 -07005761 return OMX_ErrorHardware;
5762 }
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07005763 if (codec_config_flag && !(buffer->nFlags & OMX_BUFFERFLAG_CODECCONFIG)) {
5764 codec_config_flag = false;
5765 }
Arun Menon906de572013-06-18 17:01:40 -07005766 if (!streaming[OUTPUT_PORT]) {
5767 enum v4l2_buf_type buf_type;
5768 int ret,r;
Vinay Kalia85793762012-06-14 19:12:34 -07005769
Arun Menon906de572013-06-18 17:01:40 -07005770 buf_type=V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005771 DEBUG_PRINT_LOW("send_command_proxy(): Idle-->Executing");
Arun Menon906de572013-06-18 17:01:40 -07005772 ret=ioctl(drv_ctx.video_driver_fd, VIDIOC_STREAMON,&buf_type);
5773 if (!ret) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005774 DEBUG_PRINT_HIGH("Streamon on OUTPUT Plane was successful");
Arun Menon906de572013-06-18 17:01:40 -07005775 streaming[OUTPUT_PORT] = true;
5776 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005777 DEBUG_PRINT_ERROR("Failed to call streamon on OUTPUT");
Arun Menon906de572013-06-18 17:01:40 -07005778 DEBUG_PRINT_LOW("If Stream on failed no buffer should be queued");
5779 post_event ((unsigned int)buffer,VDEC_S_SUCCESS,
5780 OMX_COMPONENT_GENERATE_EBD);
5781 return OMX_ErrorBadParameter;
5782 }
5783 }
5784 DEBUG_PRINT_LOW("[ETBP] pBuf(%p) nTS(%lld) Sz(%d)",
5785 frameinfo.bufferaddr, frameinfo.timestamp, frameinfo.datalen);
5786 time_stamp_dts.insert_timestamp(buffer);
Shalaj Jain273b3e02012-06-22 19:08:03 -07005787
Arun Menon906de572013-06-18 17:01:40 -07005788 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005789}
5790
5791/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005792 FUNCTION
5793 omx_vdec::FillThisBuffer
Shalaj Jain273b3e02012-06-22 19:08:03 -07005794
Arun Menon906de572013-06-18 17:01:40 -07005795 DESCRIPTION
5796 IL client uses this method to release the frame buffer
5797 after displaying them.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005798
Arun Menon906de572013-06-18 17:01:40 -07005799 PARAMETERS
5800 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005801
Arun Menon906de572013-06-18 17:01:40 -07005802 RETURN VALUE
5803 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07005804
Arun Menon906de572013-06-18 17:01:40 -07005805 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005806OMX_ERRORTYPE omx_vdec::fill_this_buffer(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07005807 OMX_IN OMX_BUFFERHEADERTYPE* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005808{
Arun Menonbdb80b02013-08-12 17:45:54 -07005809 if (dynamic_buf_mode) {
5810 private_handle_t *handle = NULL;
5811 struct VideoDecoderOutputMetaData *meta;
Arun Menonbdb80b02013-08-12 17:45:54 -07005812 unsigned int nPortIndex = 0;
5813
5814 if (!buffer || !buffer->pBuffer) {
5815 DEBUG_PRINT_ERROR("%s: invalid params: %p %p", __FUNCTION__, buffer, buffer->pBuffer);
5816 return OMX_ErrorBadParameter;
5817 }
5818
5819 //get the buffer type and fd info
5820 meta = (struct VideoDecoderOutputMetaData *)buffer->pBuffer;
5821 handle = (private_handle_t *)meta->pHandle;
Arun Menonb49abf22013-12-14 21:38:10 -08005822 DEBUG_PRINT_LOW("FTB: metabuf: %p buftype: %d bufhndl: %p ", meta, meta->eType, meta->pHandle);
5823
5824 if (!handle) {
5825 DEBUG_PRINT_ERROR("FTB: Error: IL client passed an invalid buf handle - %p", handle);
5826 return OMX_ErrorBadParameter;
5827 }
Arun Menonbdb80b02013-08-12 17:45:54 -07005828 //Fill outputbuffer with buffer details, this will be sent to f/w during VIDIOC_QBUF
5829 nPortIndex = buffer-((OMX_BUFFERHEADERTYPE *)client_buffers.get_il_buf_hdr());
5830 drv_ctx.ptr_outputbuffer[nPortIndex].pmem_fd = handle->fd;
Arun Menon50ab1bf2014-01-08 18:02:19 -08005831 drv_ctx.ptr_outputbuffer[nPortIndex].bufferaddr = (OMX_U8*) buffer;
ApurupaPattapuf693a4d2013-12-04 16:07:07 -08005832
5833 //Store private handle from GraphicBuffer
5834 native_buffer[nPortIndex].privatehandle = handle;
5835 native_buffer[nPortIndex].nativehandle = handle;
Arun Menonbdb80b02013-08-12 17:45:54 -07005836 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005837
Arun Menon906de572013-06-18 17:01:40 -07005838 if (m_state == OMX_StateInvalid) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005839 DEBUG_PRINT_ERROR("FTB in Invalid State");
Arun Menon906de572013-06-18 17:01:40 -07005840 return OMX_ErrorInvalidState;
5841 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005842
Arun Menon906de572013-06-18 17:01:40 -07005843 if (!m_out_bEnabled) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005844 DEBUG_PRINT_ERROR("ERROR:FTB incorrect state operation, output port is disabled.");
Arun Menon906de572013-06-18 17:01:40 -07005845 return OMX_ErrorIncorrectStateOperation;
5846 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005847
Arun Menon906de572013-06-18 17:01:40 -07005848 if (buffer == NULL ||
Surajit Podderd2644d52013-08-28 17:59:06 +05305849 ((buffer - client_buffers.get_il_buf_hdr()) >= (int)drv_ctx.op_buf.actualcount)) {
Arun Menon906de572013-06-18 17:01:40 -07005850 return OMX_ErrorBadParameter;
5851 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005852
Arun Menon906de572013-06-18 17:01:40 -07005853 if (buffer->nOutputPortIndex != OMX_CORE_OUTPUT_PORT_INDEX) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005854 DEBUG_PRINT_ERROR("ERROR:FTB invalid port in header %lu", buffer->nOutputPortIndex);
Arun Menon906de572013-06-18 17:01:40 -07005855 return OMX_ErrorBadPortIndex;
5856 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005857
Arun Menon906de572013-06-18 17:01:40 -07005858 DEBUG_PRINT_LOW("[FTB] bufhdr = %p, bufhdr->pBuffer = %p", buffer, buffer->pBuffer);
5859 post_event((unsigned) hComp, (unsigned)buffer, m_fill_output_msg);
5860 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005861}
5862/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005863 FUNCTION
5864 omx_vdec::fill_this_buffer_proxy
Shalaj Jain273b3e02012-06-22 19:08:03 -07005865
Arun Menon906de572013-06-18 17:01:40 -07005866 DESCRIPTION
5867 IL client uses this method to release the frame buffer
5868 after displaying them.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005869
Arun Menon906de572013-06-18 17:01:40 -07005870 PARAMETERS
5871 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005872
Arun Menon906de572013-06-18 17:01:40 -07005873 RETURN VALUE
5874 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07005875
Arun Menon906de572013-06-18 17:01:40 -07005876 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005877OMX_ERRORTYPE omx_vdec::fill_this_buffer_proxy(
Arun Menon906de572013-06-18 17:01:40 -07005878 OMX_IN OMX_HANDLETYPE hComp,
5879 OMX_IN OMX_BUFFERHEADERTYPE* bufferAdd)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005880{
Arun Menon906de572013-06-18 17:01:40 -07005881 OMX_ERRORTYPE nRet = OMX_ErrorNone;
5882 OMX_BUFFERHEADERTYPE *buffer = bufferAdd;
5883 unsigned nPortIndex = 0;
5884 struct vdec_fillbuffer_cmd fillbuffer;
5885 struct vdec_bufferpayload *ptr_outputbuffer = NULL;
5886 struct vdec_output_frameinfo *ptr_respbuffer = NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005887
Arun Menon906de572013-06-18 17:01:40 -07005888 nPortIndex = buffer-((OMX_BUFFERHEADERTYPE *)client_buffers.get_il_buf_hdr());
Shalaj Jain273b3e02012-06-22 19:08:03 -07005889
Arun Menon906de572013-06-18 17:01:40 -07005890 if (bufferAdd == NULL || nPortIndex > drv_ctx.op_buf.actualcount)
5891 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005892
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005893 DEBUG_PRINT_LOW("FTBProxy: bufhdr = %p, bufhdr->pBuffer = %p",
Arun Menon906de572013-06-18 17:01:40 -07005894 bufferAdd, bufferAdd->pBuffer);
5895 /*Return back the output buffer to client*/
5896 if (m_out_bEnabled != OMX_TRUE || output_flush_progress == true) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005897 DEBUG_PRINT_LOW("Output Buffers return flush/disable condition");
Arun Menon906de572013-06-18 17:01:40 -07005898 buffer->nFilledLen = 0;
5899 m_cb.FillBufferDone (hComp,m_app_data,buffer);
5900 return OMX_ErrorNone;
5901 }
Arun Menon50ab1bf2014-01-08 18:02:19 -08005902
5903 if (dynamic_buf_mode) {
5904 //map the buffer handle based on the size set on output port definition.
5905 if (!secure_mode) {
5906 drv_ctx.ptr_outputbuffer[nPortIndex].bufferaddr =
5907 (OMX_U8*)mmap(0, drv_ctx.op_buf.buffer_size,
5908 PROT_READ|PROT_WRITE, MAP_SHARED,
5909 drv_ctx.ptr_outputbuffer[nPortIndex].pmem_fd, 0);
5910 }
5911 drv_ctx.ptr_outputbuffer[nPortIndex].offset = 0;
5912 drv_ctx.ptr_outputbuffer[nPortIndex].buffer_len = drv_ctx.op_buf.buffer_size;
5913 drv_ctx.ptr_outputbuffer[nPortIndex].mmaped_size = drv_ctx.op_buf.buffer_size;
5914 buf_ref_add(drv_ctx.ptr_outputbuffer[nPortIndex].pmem_fd,
5915 drv_ctx.ptr_outputbuffer[nPortIndex].offset);
5916 }
5917
Arun Menon906de572013-06-18 17:01:40 -07005918 pending_output_buffers++;
5919 buffer = client_buffers.get_dr_buf_hdr(bufferAdd);
5920 ptr_respbuffer = (struct vdec_output_frameinfo*)buffer->pOutputPortPrivate;
5921 if (ptr_respbuffer) {
5922 ptr_outputbuffer = (struct vdec_bufferpayload*)ptr_respbuffer->client_data;
5923 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005924
Arun Menon906de572013-06-18 17:01:40 -07005925 if (ptr_respbuffer == NULL || ptr_outputbuffer == NULL) {
5926 DEBUG_PRINT_ERROR("resp buffer or outputbuffer is NULL");
5927 buffer->nFilledLen = 0;
5928 m_cb.FillBufferDone (hComp,m_app_data,buffer);
5929 pending_output_buffers--;
5930 return OMX_ErrorBadParameter;
5931 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07005932
Arun Menon906de572013-06-18 17:01:40 -07005933 int rc = 0;
5934 struct v4l2_buffer buf;
5935 struct v4l2_plane plane[VIDEO_MAX_PLANES];
5936 memset( (void *)&buf, 0, sizeof(buf));
5937 memset( (void *)plane, 0, (sizeof(struct v4l2_plane)*VIDEO_MAX_PLANES));
5938 int extra_idx = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005939
Arun Menon906de572013-06-18 17:01:40 -07005940 buf.index = nPortIndex;
5941 buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
5942 buf.memory = V4L2_MEMORY_USERPTR;
5943 plane[0].bytesused = buffer->nFilledLen;
5944 plane[0].length = drv_ctx.op_buf.buffer_size;
5945 plane[0].m.userptr =
5946 (unsigned long)drv_ctx.ptr_outputbuffer[nPortIndex].bufferaddr -
5947 (unsigned long)drv_ctx.ptr_outputbuffer[nPortIndex].offset;
5948 plane[0].reserved[0] = drv_ctx.ptr_outputbuffer[nPortIndex].pmem_fd;
5949 plane[0].reserved[1] = drv_ctx.ptr_outputbuffer[nPortIndex].offset;
5950 plane[0].data_offset = 0;
5951 extra_idx = EXTRADATA_IDX(drv_ctx.num_planes);
5952 if (extra_idx && (extra_idx < VIDEO_MAX_PLANES)) {
5953 plane[extra_idx].bytesused = 0;
5954 plane[extra_idx].length = drv_ctx.extradata_info.buffer_size;
5955 plane[extra_idx].m.userptr = (long unsigned int) (drv_ctx.extradata_info.uaddr + nPortIndex * drv_ctx.extradata_info.buffer_size);
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07005956#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07005957 plane[extra_idx].reserved[0] = drv_ctx.extradata_info.ion.fd_ion_data.fd;
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07005958#endif
Arun Menon906de572013-06-18 17:01:40 -07005959 plane[extra_idx].reserved[1] = nPortIndex * drv_ctx.extradata_info.buffer_size;
5960 plane[extra_idx].data_offset = 0;
5961 } else if (extra_idx >= VIDEO_MAX_PLANES) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005962 DEBUG_PRINT_ERROR("Extradata index higher than expected: %d", extra_idx);
Arun Menon906de572013-06-18 17:01:40 -07005963 return OMX_ErrorBadParameter;
5964 }
5965 buf.m.planes = plane;
5966 buf.length = drv_ctx.num_planes;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005967 DEBUG_PRINT_LOW("SENDING FTB TO F/W - fd[0] = %d fd[1] = %d offset[1] = %d",
Arun Menonbdb80b02013-08-12 17:45:54 -07005968 plane[0].reserved[0],plane[extra_idx].reserved[0], plane[extra_idx].reserved[1]);
5969
Arun Menon906de572013-06-18 17:01:40 -07005970 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_QBUF, &buf);
5971 if (rc) {
5972 /*TODO: How to handle this case */
5973 DEBUG_PRINT_ERROR("Failed to qbuf to driver");
5974 }
Arun Menon906de572013-06-18 17:01:40 -07005975return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07005976}
5977
5978/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07005979 FUNCTION
5980 omx_vdec::SetCallbacks
Shalaj Jain273b3e02012-06-22 19:08:03 -07005981
Arun Menon906de572013-06-18 17:01:40 -07005982 DESCRIPTION
5983 Set the callbacks.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005984
Arun Menon906de572013-06-18 17:01:40 -07005985 PARAMETERS
5986 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005987
Arun Menon906de572013-06-18 17:01:40 -07005988 RETURN VALUE
5989 OMX Error None if everything successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07005990
Arun Menon906de572013-06-18 17:01:40 -07005991 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07005992OMX_ERRORTYPE omx_vdec::set_callbacks(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07005993 OMX_IN OMX_CALLBACKTYPE* callbacks,
5994 OMX_IN OMX_PTR appData)
Shalaj Jain273b3e02012-06-22 19:08:03 -07005995{
5996
Arun Menon906de572013-06-18 17:01:40 -07005997 m_cb = *callbacks;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07005998 DEBUG_PRINT_LOW("Callbacks Set %p %p %p",m_cb.EmptyBufferDone,\
Arun Menon906de572013-06-18 17:01:40 -07005999 m_cb.EventHandler,m_cb.FillBufferDone);
6000 m_app_data = appData;
6001 return OMX_ErrorNotImplemented;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006002}
6003
6004/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07006005 FUNCTION
6006 omx_vdec::ComponentDeInit
Shalaj Jain273b3e02012-06-22 19:08:03 -07006007
Arun Menon906de572013-06-18 17:01:40 -07006008 DESCRIPTION
6009 Destroys the component and release memory allocated to the heap.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006010
Arun Menon906de572013-06-18 17:01:40 -07006011 PARAMETERS
6012 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006013
Arun Menon906de572013-06-18 17:01:40 -07006014 RETURN VALUE
6015 OMX Error None if everything successful.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006016
Arun Menon906de572013-06-18 17:01:40 -07006017 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07006018OMX_ERRORTYPE omx_vdec::component_deinit(OMX_IN OMX_HANDLETYPE hComp)
6019{
6020#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -07006021 if (iDivXDrmDecrypt) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006022 delete iDivXDrmDecrypt;
6023 iDivXDrmDecrypt=NULL;
6024 }
6025#endif //_ANDROID_
6026
Shalaj Jain286b0062013-02-21 20:35:48 -08006027 unsigned i = 0;
Arun Menon906de572013-06-18 17:01:40 -07006028 if (OMX_StateLoaded != m_state) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006029 DEBUG_PRINT_ERROR("WARNING:Rxd DeInit,OMX not in LOADED state %d",\
Arun Menon906de572013-06-18 17:01:40 -07006030 m_state);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006031 DEBUG_PRINT_ERROR("Playback Ended - FAILED");
Arun Menon906de572013-06-18 17:01:40 -07006032 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006033 DEBUG_PRINT_HIGH("Playback Ended - PASSED");
Shalaj Jain273b3e02012-06-22 19:08:03 -07006034 }
6035
6036 /*Check if the output buffers have to be cleaned up*/
Arun Menon906de572013-06-18 17:01:40 -07006037 if (m_out_mem_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006038 DEBUG_PRINT_LOW("Freeing the Output Memory");
Arun Menon906de572013-06-18 17:01:40 -07006039 for (i = 0; i < drv_ctx.op_buf.actualcount; i++ ) {
6040 free_output_buffer (&m_out_mem_ptr[i]);
Shalaj Jain273b3e02012-06-22 19:08:03 -07006041 }
6042#ifdef _ANDROID_ICS_
6043 memset(&native_buffer, 0, (sizeof(nativebuffer) * MAX_NUM_INPUT_OUTPUT_BUFFERS));
6044#endif
6045 }
6046
6047 /*Check if the input buffers have to be cleaned up*/
Arun Menon906de572013-06-18 17:01:40 -07006048 if (m_inp_mem_ptr || m_inp_heap_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006049 DEBUG_PRINT_LOW("Freeing the Input Memory");
Arun Menon906de572013-06-18 17:01:40 -07006050 for (i = 0; i<drv_ctx.ip_buf.actualcount; i++ ) {
6051 if (m_inp_mem_ptr)
6052 free_input_buffer (i,&m_inp_mem_ptr[i]);
6053 else
6054 free_input_buffer (i,NULL);
Shalaj Jain273b3e02012-06-22 19:08:03 -07006055 }
6056 }
6057 free_input_buffer_header();
6058 free_output_buffer_header();
Arun Menon906de572013-06-18 17:01:40 -07006059 if (h264_scratch.pBuffer) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006060 free(h264_scratch.pBuffer);
6061 h264_scratch.pBuffer = NULL;
6062 }
6063
Arun Menon906de572013-06-18 17:01:40 -07006064 if (h264_parser) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006065 delete h264_parser;
Arun Menon906de572013-06-18 17:01:40 -07006066 h264_parser = NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006067 }
6068
Leena Winterrowddb9eaca2013-08-23 10:40:41 -07006069 if (m_frame_parser.mutils) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006070 DEBUG_PRINT_LOW("Free utils parser");
Leena Winterrowddb9eaca2013-08-23 10:40:41 -07006071 delete (m_frame_parser.mutils);
6072 m_frame_parser.mutils = NULL;
6073 }
6074
Arun Menon906de572013-06-18 17:01:40 -07006075 if (m_platform_list) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006076 free(m_platform_list);
6077 m_platform_list = NULL;
6078 }
Arun Menon906de572013-06-18 17:01:40 -07006079 if (m_vendor_config.pData) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006080 free(m_vendor_config.pData);
6081 m_vendor_config.pData = NULL;
6082 }
6083
6084 // Reset counters in mesg queues
6085 m_ftb_q.m_size=0;
6086 m_cmd_q.m_size=0;
6087 m_etb_q.m_size=0;
6088 m_ftb_q.m_read = m_ftb_q.m_write =0;
6089 m_cmd_q.m_read = m_cmd_q.m_write =0;
6090 m_etb_q.m_read = m_etb_q.m_write =0;
6091#ifdef _ANDROID_
Arun Menon906de572013-06-18 17:01:40 -07006092 if (m_debug_timestamp) {
6093 m_timestamp_list.reset_ts_list();
Shalaj Jain273b3e02012-06-22 19:08:03 -07006094 }
6095#endif
6096
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006097 DEBUG_PRINT_LOW("Calling VDEC_IOCTL_STOP_NEXT_MSG");
Shalaj Jain273b3e02012-06-22 19:08:03 -07006098 //(void)ioctl(drv_ctx.video_driver_fd, VDEC_IOCTL_STOP_NEXT_MSG,
Arun Menon906de572013-06-18 17:01:40 -07006099 // NULL);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006100 DEBUG_PRINT_HIGH("Close the driver instance");
Arun Menon906de572013-06-18 17:01:40 -07006101
Jayasena Sangaraboina51230642013-08-21 18:02:13 -07006102 if (m_debug.infile) {
6103 fclose(m_debug.infile);
6104 m_debug.infile = NULL;
6105 }
6106 if (m_debug.outfile) {
6107 fclose(m_debug.outfile);
6108 m_debug.outfile = NULL;
6109 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006110#ifdef OUTPUT_EXTRADATA_LOG
Shalaj Jainaf08f302013-03-18 13:15:35 -07006111 if (outputExtradataFile)
6112 fclose (outputExtradataFile);
Shalaj Jain273b3e02012-06-22 19:08:03 -07006113#endif
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006114 DEBUG_PRINT_HIGH("omx_vdec::component_deinit() complete");
Arun Menon906de572013-06-18 17:01:40 -07006115 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006116}
6117
6118/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07006119 FUNCTION
6120 omx_vdec::UseEGLImage
Shalaj Jain273b3e02012-06-22 19:08:03 -07006121
Arun Menon906de572013-06-18 17:01:40 -07006122 DESCRIPTION
6123 OMX Use EGL Image method implementation <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006124
Arun Menon906de572013-06-18 17:01:40 -07006125 PARAMETERS
6126 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006127
Arun Menon906de572013-06-18 17:01:40 -07006128 RETURN VALUE
6129 Not Implemented error.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006130
Arun Menon906de572013-06-18 17:01:40 -07006131 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07006132OMX_ERRORTYPE omx_vdec::use_EGL_image(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07006133 OMX_INOUT OMX_BUFFERHEADERTYPE** bufferHdr,
6134 OMX_IN OMX_U32 port,
6135 OMX_IN OMX_PTR appData,
6136 OMX_IN void* eglImage)
Shalaj Jain273b3e02012-06-22 19:08:03 -07006137{
Arun Menon906de572013-06-18 17:01:40 -07006138 OMX_QCOM_PLATFORM_PRIVATE_LIST pmem_list;
6139 OMX_QCOM_PLATFORM_PRIVATE_ENTRY pmem_entry;
6140 OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO pmem_info;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006141
6142#ifdef USE_EGL_IMAGE_GPU
Arun Menon906de572013-06-18 17:01:40 -07006143 PFNEGLQUERYIMAGEQUALCOMMPROC egl_queryfunc;
6144 EGLint fd = -1, offset = 0,pmemPtr = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006145#else
Arun Menon906de572013-06-18 17:01:40 -07006146 int fd = -1, offset = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006147#endif
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006148 DEBUG_PRINT_HIGH("use EGL image support for decoder");
Arun Menon906de572013-06-18 17:01:40 -07006149 if (!bufferHdr || !eglImage|| port != OMX_CORE_OUTPUT_PORT_INDEX) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006150 DEBUG_PRINT_ERROR("");
Arun Menon906de572013-06-18 17:01:40 -07006151 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006152#ifdef USE_EGL_IMAGE_GPU
Arun Menon906de572013-06-18 17:01:40 -07006153 if (m_display_id == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006154 DEBUG_PRINT_ERROR("Display ID is not set by IL client");
Shalaj Jain273b3e02012-06-22 19:08:03 -07006155 return OMX_ErrorInsufficientResources;
Arun Menon906de572013-06-18 17:01:40 -07006156 }
6157 egl_queryfunc = (PFNEGLQUERYIMAGEQUALCOMMPROC)
6158 eglGetProcAddress("eglQueryImageKHR");
6159 egl_queryfunc(m_display_id, eglImage, EGL_BUFFER_HANDLE_QCOM,&fd);
6160 egl_queryfunc(m_display_id, eglImage, EGL_BUFFER_OFFSET_QCOM,&offset);
6161 egl_queryfunc(m_display_id, eglImage, EGL_BITMAP_POINTER_KHR,&pmemPtr);
Shalaj Jain273b3e02012-06-22 19:08:03 -07006162#else //with OMX test app
6163 struct temp_egl {
6164 int pmem_fd;
6165 int offset;
6166 };
6167 struct temp_egl *temp_egl_id = NULL;
6168 void * pmemPtr = (void *) eglImage;
6169 temp_egl_id = (struct temp_egl *)eglImage;
Arun Menon906de572013-06-18 17:01:40 -07006170 if (temp_egl_id != NULL) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006171 fd = temp_egl_id->pmem_fd;
6172 offset = temp_egl_id->offset;
6173 }
6174#endif
6175 if (fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006176 DEBUG_PRINT_ERROR("Improper pmem fd by EGL client %d",fd);
Shalaj Jain273b3e02012-06-22 19:08:03 -07006177 return OMX_ErrorInsufficientResources;
Arun Menon906de572013-06-18 17:01:40 -07006178 }
6179 pmem_info.pmem_fd = (OMX_U32) fd;
6180 pmem_info.offset = (OMX_U32) offset;
6181 pmem_entry.entry = (void *) &pmem_info;
6182 pmem_entry.type = OMX_QCOM_PLATFORM_PRIVATE_PMEM;
6183 pmem_list.entryList = &pmem_entry;
6184 pmem_list.nEntries = 1;
6185 ouput_egl_buffers = true;
6186 if (OMX_ErrorNone != use_buffer(hComp,bufferHdr, port,
6187 (void *)&pmem_list, drv_ctx.op_buf.buffer_size,
6188 (OMX_U8 *)pmemPtr)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006189 DEBUG_PRINT_ERROR("use buffer call failed for egl image");
Arun Menon906de572013-06-18 17:01:40 -07006190 return OMX_ErrorInsufficientResources;
6191 }
6192 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006193}
6194
6195/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07006196 FUNCTION
6197 omx_vdec::ComponentRoleEnum
Shalaj Jain273b3e02012-06-22 19:08:03 -07006198
Arun Menon906de572013-06-18 17:01:40 -07006199 DESCRIPTION
6200 OMX Component Role Enum method implementation.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006201
Arun Menon906de572013-06-18 17:01:40 -07006202 PARAMETERS
6203 <TBD>.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006204
Arun Menon906de572013-06-18 17:01:40 -07006205 RETURN VALUE
6206 OMX Error None if everything is successful.
6207 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07006208OMX_ERRORTYPE omx_vdec::component_role_enum(OMX_IN OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07006209 OMX_OUT OMX_U8* role,
6210 OMX_IN OMX_U32 index)
Shalaj Jain273b3e02012-06-22 19:08:03 -07006211{
Arun Menon906de572013-06-18 17:01:40 -07006212 OMX_ERRORTYPE eRet = OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006213
Arun Menon906de572013-06-18 17:01:40 -07006214 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg4",OMX_MAX_STRINGNAME_SIZE)) {
6215 if ((0 == index) && role) {
6216 strlcpy((char *)role, "video_decoder.mpeg4",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006217 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006218 } else {
6219 eRet = OMX_ErrorNoMore;
6220 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006221 }
Arun Menon906de572013-06-18 17:01:40 -07006222 if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.mpeg2",OMX_MAX_STRINGNAME_SIZE)) {
6223 if ((0 == index) && role) {
6224 strlcpy((char *)role, "video_decoder.mpeg2",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006225 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006226 } else {
6227 eRet = OMX_ErrorNoMore;
6228 }
6229 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.h263",OMX_MAX_STRINGNAME_SIZE)) {
6230 if ((0 == index) && role) {
6231 strlcpy((char *)role, "video_decoder.h263",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006232 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006233 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006234 DEBUG_PRINT_LOW("No more roles");
Arun Menon906de572013-06-18 17:01:40 -07006235 eRet = OMX_ErrorNoMore;
6236 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006237 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006238
Arun Menon906de572013-06-18 17:01:40 -07006239 else if ((!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx",OMX_MAX_STRINGNAME_SIZE)) ||
6240 (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.divx311",OMX_MAX_STRINGNAME_SIZE))
6241 )
Shalaj Jain273b3e02012-06-22 19:08:03 -07006242
Shalaj Jain273b3e02012-06-22 19:08:03 -07006243 {
Arun Menon906de572013-06-18 17:01:40 -07006244 if ((0 == index) && role) {
6245 strlcpy((char *)role, "video_decoder.divx",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006246 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006247 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006248 DEBUG_PRINT_LOW("No more roles");
Arun Menon906de572013-06-18 17:01:40 -07006249 eRet = OMX_ErrorNoMore;
6250 }
6251 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.avc",OMX_MAX_STRINGNAME_SIZE)) {
6252 if ((0 == index) && role) {
6253 strlcpy((char *)role, "video_decoder.avc",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006254 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006255 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006256 DEBUG_PRINT_LOW("No more roles");
Arun Menon906de572013-06-18 17:01:40 -07006257 eRet = OMX_ErrorNoMore;
6258 }
6259 } else if ( (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vc1",OMX_MAX_STRINGNAME_SIZE)) ||
6260 (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.wmv",OMX_MAX_STRINGNAME_SIZE))
6261 ) {
6262 if ((0 == index) && role) {
6263 strlcpy((char *)role, "video_decoder.vc1",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006264 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006265 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006266 DEBUG_PRINT_LOW("No more roles");
Arun Menon906de572013-06-18 17:01:40 -07006267 eRet = OMX_ErrorNoMore;
6268 }
6269 } else if (!strncmp(drv_ctx.kind, "OMX.qcom.video.decoder.vp8",OMX_MAX_STRINGNAME_SIZE)) {
6270 if ((0 == index) && role) {
6271 strlcpy((char *)role, "video_decoder.vp8",OMX_MAX_STRINGNAME_SIZE);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006272 DEBUG_PRINT_LOW("component_role_enum: role %s",role);
Arun Menon906de572013-06-18 17:01:40 -07006273 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006274 DEBUG_PRINT_LOW("No more roles");
Arun Menon906de572013-06-18 17:01:40 -07006275 eRet = OMX_ErrorNoMore;
6276 }
6277 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006278 DEBUG_PRINT_ERROR("ERROR:Querying Role on Unknown Component");
Arun Menon906de572013-06-18 17:01:40 -07006279 eRet = OMX_ErrorInvalidComponentName;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006280 }
Arun Menon906de572013-06-18 17:01:40 -07006281 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006282}
6283
6284
6285
6286
6287/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07006288 FUNCTION
6289 omx_vdec::AllocateDone
Shalaj Jain273b3e02012-06-22 19:08:03 -07006290
Arun Menon906de572013-06-18 17:01:40 -07006291 DESCRIPTION
6292 Checks if entire buffer pool is allocated by IL Client or not.
6293 Need this to move to IDLE state.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006294
Arun Menon906de572013-06-18 17:01:40 -07006295 PARAMETERS
6296 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006297
Arun Menon906de572013-06-18 17:01:40 -07006298 RETURN VALUE
6299 true/false.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006300
Arun Menon906de572013-06-18 17:01:40 -07006301 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07006302bool omx_vdec::allocate_done(void)
6303{
Arun Menon906de572013-06-18 17:01:40 -07006304 bool bRet = false;
6305 bool bRet_In = false;
6306 bool bRet_Out = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006307
Arun Menon906de572013-06-18 17:01:40 -07006308 bRet_In = allocate_input_done();
6309 bRet_Out = allocate_output_done();
Shalaj Jain273b3e02012-06-22 19:08:03 -07006310
Arun Menon906de572013-06-18 17:01:40 -07006311 if (bRet_In && bRet_Out) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006312 bRet = true;
6313 }
Arun Menon906de572013-06-18 17:01:40 -07006314
6315 return bRet;
6316}
6317/* ======================================================================
6318 FUNCTION
6319 omx_vdec::AllocateInputDone
6320
6321 DESCRIPTION
6322 Checks if I/P buffer pool is allocated by IL Client or not.
6323
6324 PARAMETERS
6325 None.
6326
6327 RETURN VALUE
6328 true/false.
6329
6330 ========================================================================== */
6331bool omx_vdec::allocate_input_done(void)
6332{
6333 bool bRet = false;
6334 unsigned i=0;
6335
6336 if (m_inp_mem_ptr == NULL) {
6337 return bRet;
6338 }
6339 if (m_inp_mem_ptr ) {
6340 for (; i<drv_ctx.ip_buf.actualcount; i++) {
6341 if (BITMASK_ABSENT(&m_inp_bm_count,i)) {
6342 break;
6343 }
6344 }
6345 }
6346 if (i == drv_ctx.ip_buf.actualcount) {
6347 bRet = true;
6348 DEBUG_PRINT_HIGH("Allocate done for all i/p buffers");
6349 }
6350 if (i==drv_ctx.ip_buf.actualcount && m_inp_bEnabled) {
6351 m_inp_bPopulated = OMX_TRUE;
6352 }
6353 return bRet;
6354}
6355/* ======================================================================
6356 FUNCTION
6357 omx_vdec::AllocateOutputDone
6358
6359 DESCRIPTION
6360 Checks if entire O/P buffer pool is allocated by IL Client or not.
6361
6362 PARAMETERS
6363 None.
6364
6365 RETURN VALUE
6366 true/false.
6367
6368 ========================================================================== */
6369bool omx_vdec::allocate_output_done(void)
6370{
6371 bool bRet = false;
6372 unsigned j=0;
6373
6374 if (m_out_mem_ptr == NULL) {
6375 return bRet;
6376 }
6377
6378 if (m_out_mem_ptr) {
6379 for (; j < drv_ctx.op_buf.actualcount; j++) {
6380 if (BITMASK_ABSENT(&m_out_bm_count,j)) {
6381 break;
6382 }
6383 }
6384 }
6385
6386 if (j == drv_ctx.op_buf.actualcount) {
6387 bRet = true;
6388 DEBUG_PRINT_HIGH("Allocate done for all o/p buffers");
6389 if (m_out_bEnabled)
6390 m_out_bPopulated = OMX_TRUE;
6391 }
6392
6393 return bRet;
6394}
6395
6396/* ======================================================================
6397 FUNCTION
6398 omx_vdec::ReleaseDone
6399
6400 DESCRIPTION
6401 Checks if IL client has released all the buffers.
6402
6403 PARAMETERS
6404 None.
6405
6406 RETURN VALUE
6407 true/false
6408
6409 ========================================================================== */
6410bool omx_vdec::release_done(void)
6411{
6412 bool bRet = false;
6413
6414 if (release_input_done()) {
6415 if (release_output_done()) {
6416 bRet = true;
6417 }
6418 }
6419 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006420}
6421
6422
6423/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07006424 FUNCTION
6425 omx_vdec::ReleaseOutputDone
Shalaj Jain273b3e02012-06-22 19:08:03 -07006426
Arun Menon906de572013-06-18 17:01:40 -07006427 DESCRIPTION
6428 Checks if IL client has released all the buffers.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006429
Arun Menon906de572013-06-18 17:01:40 -07006430 PARAMETERS
6431 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006432
Arun Menon906de572013-06-18 17:01:40 -07006433 RETURN VALUE
6434 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07006435
Arun Menon906de572013-06-18 17:01:40 -07006436 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07006437bool omx_vdec::release_output_done(void)
6438{
Arun Menon906de572013-06-18 17:01:40 -07006439 bool bRet = false;
6440 unsigned i=0,j=0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006441
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006442 DEBUG_PRINT_LOW("Value of m_out_mem_ptr %p",m_inp_mem_ptr);
Arun Menon906de572013-06-18 17:01:40 -07006443 if (m_out_mem_ptr) {
6444 for (; j < drv_ctx.op_buf.actualcount ; j++) {
6445 if (BITMASK_PRESENT(&m_out_bm_count,j)) {
6446 break;
6447 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006448 }
Arun Menon906de572013-06-18 17:01:40 -07006449 if (j == drv_ctx.op_buf.actualcount) {
6450 m_out_bm_count = 0;
6451 bRet = true;
6452 }
6453 } else {
6454 m_out_bm_count = 0;
6455 bRet = true;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006456 }
Arun Menon906de572013-06-18 17:01:40 -07006457 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006458}
6459/* ======================================================================
Arun Menon906de572013-06-18 17:01:40 -07006460 FUNCTION
6461 omx_vdec::ReleaseInputDone
Shalaj Jain273b3e02012-06-22 19:08:03 -07006462
Arun Menon906de572013-06-18 17:01:40 -07006463 DESCRIPTION
6464 Checks if IL client has released all the buffers.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006465
Arun Menon906de572013-06-18 17:01:40 -07006466 PARAMETERS
6467 None.
Shalaj Jain273b3e02012-06-22 19:08:03 -07006468
Arun Menon906de572013-06-18 17:01:40 -07006469 RETURN VALUE
6470 true/false
Shalaj Jain273b3e02012-06-22 19:08:03 -07006471
Arun Menon906de572013-06-18 17:01:40 -07006472 ========================================================================== */
Shalaj Jain273b3e02012-06-22 19:08:03 -07006473bool omx_vdec::release_input_done(void)
6474{
Arun Menon906de572013-06-18 17:01:40 -07006475 bool bRet = false;
6476 unsigned i=0,j=0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006477
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006478 DEBUG_PRINT_LOW("Value of m_inp_mem_ptr %p",m_inp_mem_ptr);
Arun Menon906de572013-06-18 17:01:40 -07006479 if (m_inp_mem_ptr) {
6480 for (; j<drv_ctx.ip_buf.actualcount; j++) {
6481 if ( BITMASK_PRESENT(&m_inp_bm_count,j)) {
6482 break;
6483 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006484 }
Arun Menon906de572013-06-18 17:01:40 -07006485 if (j==drv_ctx.ip_buf.actualcount) {
6486 bRet = true;
6487 }
6488 } else {
6489 bRet = true;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006490 }
Arun Menon906de572013-06-18 17:01:40 -07006491 return bRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006492}
6493
6494OMX_ERRORTYPE omx_vdec::fill_buffer_done(OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07006495 OMX_BUFFERHEADERTYPE * buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07006496{
Arun Menon906de572013-06-18 17:01:40 -07006497 OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *pPMEMInfo = NULL;
Surajit Podderd2644d52013-08-28 17:59:06 +05306498 if (!buffer || (buffer - m_out_mem_ptr) >= (int)drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006499 DEBUG_PRINT_ERROR("[FBD] ERROR in ptr(%p)", buffer);
Arun Menon906de572013-06-18 17:01:40 -07006500 return OMX_ErrorBadParameter;
6501 } else if (output_flush_progress) {
6502 DEBUG_PRINT_LOW("FBD: Buffer (%p) flushed", buffer);
6503 buffer->nFilledLen = 0;
6504 buffer->nTimeStamp = 0;
6505 buffer->nFlags &= ~OMX_BUFFERFLAG_EXTRADATA;
6506 buffer->nFlags &= ~QOMX_VIDEO_BUFFERFLAG_EOSEQ;
6507 buffer->nFlags &= ~OMX_BUFFERFLAG_DATACORRUPT;
Praneeth Paladugu594e6822013-04-19 10:47:28 -07006508 }
6509
Arun Menon906de572013-06-18 17:01:40 -07006510 if (m_debug_extradata) {
6511 if (buffer->nFlags & QOMX_VIDEO_BUFFERFLAG_EOSEQ) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006512 DEBUG_PRINT_HIGH("");
6513 DEBUG_PRINT_HIGH("***************************************************");
6514 DEBUG_PRINT_HIGH("FillBufferDone: End Of Sequence Received");
6515 DEBUG_PRINT_HIGH("***************************************************");
Arun Menon906de572013-06-18 17:01:40 -07006516 }
6517
6518 if (buffer->nFlags & OMX_BUFFERFLAG_DATACORRUPT) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006519 DEBUG_PRINT_HIGH("");
6520 DEBUG_PRINT_HIGH("***************************************************");
6521 DEBUG_PRINT_HIGH("FillBufferDone: OMX_BUFFERFLAG_DATACORRUPT Received");
6522 DEBUG_PRINT_HIGH("***************************************************");
Arun Menon906de572013-06-18 17:01:40 -07006523 }
Praneeth Paladugu594e6822013-04-19 10:47:28 -07006524 }
Praneeth Paladugu594e6822013-04-19 10:47:28 -07006525
6526
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006527 DEBUG_PRINT_LOW("fill_buffer_done: bufhdr = %p, bufhdr->pBuffer = %p",
Arun Menon906de572013-06-18 17:01:40 -07006528 buffer, buffer->pBuffer);
6529 pending_output_buffers --;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006530
Arun Menon906de572013-06-18 17:01:40 -07006531 if (buffer->nFlags & OMX_BUFFERFLAG_EOS) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006532 DEBUG_PRINT_HIGH("Output EOS has been reached");
Arun Menon906de572013-06-18 17:01:40 -07006533 if (!output_flush_progress)
6534 post_event((unsigned)NULL, (unsigned)NULL,
6535 OMX_COMPONENT_GENERATE_EOS_DONE);
6536
6537 if (psource_frame) {
6538 m_cb.EmptyBufferDone(&m_cmp, m_app_data, psource_frame);
6539 psource_frame = NULL;
6540 }
6541 if (pdest_frame) {
6542 pdest_frame->nFilledLen = 0;
6543 m_input_free_q.insert_entry((unsigned) pdest_frame,(unsigned)NULL,
6544 (unsigned)NULL);
6545 pdest_frame = NULL;
6546 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006547 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006548
Shalaj Jain273b3e02012-06-22 19:08:03 -07006549
Praneeth Paladugudd29c282013-09-12 15:41:47 -07006550 if (!output_flush_progress && (buffer->nFilledLen > 0)) {
6551 DEBUG_PRINT_LOW("Processing extradata");
6552 handle_extradata(buffer);
6553 }
6554
Arun Menon906de572013-06-18 17:01:40 -07006555 /* For use buffer we need to copy the data */
6556 if (!output_flush_progress) {
6557 /* This is the error check for non-recoverable errros */
6558 bool is_duplicate_ts_valid = true;
6559 bool is_interlaced = (drv_ctx.interlace != VDEC_InterlaceFrameProgressive);
Deva Ramasubramaniane47e05b2013-04-24 15:23:29 -07006560
Arun Menon906de572013-06-18 17:01:40 -07006561 if (output_capability == V4L2_PIX_FMT_MPEG4 ||
6562 output_capability == V4L2_PIX_FMT_MPEG2 ||
6563 output_capability == V4L2_PIX_FMT_DIVX ||
6564 output_capability == V4L2_PIX_FMT_DIVX_311)
6565 is_duplicate_ts_valid = false;
Deva Ramasubramaniane47e05b2013-04-24 15:23:29 -07006566
Arun Menon906de572013-06-18 17:01:40 -07006567 if (output_capability == V4L2_PIX_FMT_H264 && is_interlaced) {
Arun Menon7b6fd642014-02-13 16:48:36 -08006568 if (buffer->nFlags & QOMX_VIDEO_BUFFERFLAG_MBAFF) {
Arun Menon906de572013-06-18 17:01:40 -07006569 is_interlaced = false;
Rajeshwar Kurapaty46a24f02013-07-09 15:13:41 +05306570 }
Arun Menon906de572013-06-18 17:01:40 -07006571 }
Rajeshwar Kurapaty46a24f02013-07-09 15:13:41 +05306572
Arun Menon906de572013-06-18 17:01:40 -07006573 if (buffer->nFilledLen > 0) {
6574 time_stamp_dts.get_next_timestamp(buffer,
6575 is_interlaced && is_duplicate_ts_valid);
6576 if (m_debug_timestamp) {
6577 {
6578 OMX_TICKS expected_ts = 0;
6579 m_timestamp_list.pop_min_ts(expected_ts);
6580 if (is_interlaced && is_duplicate_ts_valid) {
6581 m_timestamp_list.pop_min_ts(expected_ts);
6582 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006583 DEBUG_PRINT_LOW("Current timestamp (%lld),Popped TIMESTAMP (%lld) from list",
Arun Menon906de572013-06-18 17:01:40 -07006584 buffer->nTimeStamp, expected_ts);
6585
6586 if (buffer->nTimeStamp != expected_ts) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006587 DEBUG_PRINT_ERROR("ERROR in omx_vdec::async_message_process timestamp Check");
Arun Menon906de572013-06-18 17:01:40 -07006588 }
6589 }
Rajeshwar Kurapaty46a24f02013-07-09 15:13:41 +05306590 }
Arun Menon906de572013-06-18 17:01:40 -07006591 } else {
Arun Menon906de572013-06-18 17:01:40 -07006592 time_stamp_dts.remove_time_stamp(
6593 buffer->nTimeStamp,
6594 is_interlaced && is_duplicate_ts_valid);
Rajeshwar Kurapaty46a24f02013-07-09 15:13:41 +05306595 }
Arun Menon906de572013-06-18 17:01:40 -07006596
6597
Praneeth Paladugu8f12e822013-03-11 18:47:58 -07006598 }
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08006599
Arun Menon906de572013-06-18 17:01:40 -07006600 if (m_cb.FillBufferDone) {
6601 if (buffer->nFilledLen > 0) {
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08006602 if (arbitrary_bytes)
Arun Menon906de572013-06-18 17:01:40 -07006603 adjust_timestamp(buffer->nTimeStamp);
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08006604 else
6605 set_frame_rate(buffer->nTimeStamp);
6606
Arun Menon906de572013-06-18 17:01:40 -07006607 if (perf_flag) {
6608 if (!proc_frms) {
6609 dec_time.stop();
6610 latency = dec_time.processing_time_us() - latency;
6611 DEBUG_PRINT_HIGH(">>> FBD Metrics: Latency(%.2f)mS", latency / 1e3);
6612 dec_time.start();
6613 fps_metrics.start();
6614 }
6615 proc_frms++;
6616 if (buffer->nFlags & OMX_BUFFERFLAG_EOS) {
6617 OMX_U64 proc_time = 0;
6618 fps_metrics.stop();
6619 proc_time = fps_metrics.processing_time_us();
6620 DEBUG_PRINT_HIGH(">>> FBD Metrics: proc_frms(%lu) proc_time(%.2f)S fps(%.2f)",
Shalaj Jain273b3e02012-06-22 19:08:03 -07006621 proc_frms, (float)proc_time / 1e6,
6622 (float)(1e6 * proc_frms) / proc_time);
Arun Menon906de572013-06-18 17:01:40 -07006623 proc_frms = 0;
6624 }
6625 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006626
6627#ifdef OUTPUT_EXTRADATA_LOG
Arun Menon906de572013-06-18 17:01:40 -07006628 if (outputExtradataFile) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006629
Arun Menon906de572013-06-18 17:01:40 -07006630 OMX_OTHER_EXTRADATATYPE *p_extra = NULL;
6631 p_extra = (OMX_OTHER_EXTRADATATYPE *)
6632 ((unsigned)(buffer->pBuffer + buffer->nOffset +
6633 buffer->nFilledLen + 3)&(~3));
6634 while (p_extra &&
6635 (OMX_U8*)p_extra < (buffer->pBuffer + buffer->nAllocLen) ) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006636 DEBUG_PRINT_LOW("WRITING extradata, size=%d,type=%d",p_extra->nSize, p_extra->eType);
Arun Menon906de572013-06-18 17:01:40 -07006637 fwrite (p_extra,1,p_extra->nSize,outputExtradataFile);
6638 if (p_extra->eType == OMX_ExtraDataNone) {
6639 break;
6640 }
6641 p_extra = (OMX_OTHER_EXTRADATATYPE *) (((OMX_U8 *) p_extra) + p_extra->nSize);
6642 }
6643 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006644#endif
Arun Menon906de572013-06-18 17:01:40 -07006645 }
6646 if (buffer->nFlags & OMX_BUFFERFLAG_EOS) {
6647 prev_ts = LLONG_MAX;
6648 rst_prev_ts = true;
6649 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006650
Arun Menon906de572013-06-18 17:01:40 -07006651 pPMEMInfo = (OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *)
6652 ((OMX_QCOM_PLATFORM_PRIVATE_LIST *)
6653 buffer->pPlatformPrivate)->entryList->entry;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006654 DEBUG_PRINT_LOW("Before FBD callback Accessed Pmeminfo %lu",pPMEMInfo->pmem_fd);
Arun Menon906de572013-06-18 17:01:40 -07006655 OMX_BUFFERHEADERTYPE *il_buffer;
6656 il_buffer = client_buffers.get_il_buf_hdr(buffer);
vivek mehtaa75c69f2014-01-10 21:50:37 -08006657
vivek mehta79cff222014-01-22 12:17:07 -08006658 if (il_buffer && m_last_rendered_TS >= 0) {
6659 int current_framerate = (int)(drv_ctx.frame_rate.fps_numerator /drv_ctx.frame_rate.fps_denominator);
Manikanta Kanamarlapudifb53b262014-01-20 16:12:47 +05306660 OMX_TICKS ts_delta = (OMX_TICKS)llabs(il_buffer->nTimeStamp - m_last_rendered_TS);
vivek mehta79cff222014-01-22 12:17:07 -08006661
6662 // Current frame can be send for rendering if
6663 // (a) current FPS is <= 60
6664 // (b) is the next frame after the frame with TS 0
6665 // (c) is the first frame after seek
6666 // (d) the delta TS b\w two consecutive frames is > 16 ms
6667 // (e) its TS is equal to previous frame TS
6668 // (f) if marked EOS
6669
6670 if(current_framerate <= 60 || m_last_rendered_TS == 0 ||
6671 il_buffer->nTimeStamp == 0 || ts_delta >= 16000 ||
6672 ts_delta == 0 || (il_buffer->nFlags & OMX_BUFFERFLAG_EOS)) {
vivek mehtaa75c69f2014-01-10 21:50:37 -08006673 m_last_rendered_TS = il_buffer->nTimeStamp;
vivek mehta79cff222014-01-22 12:17:07 -08006674 } else {
vivek mehtaa75c69f2014-01-10 21:50:37 -08006675 //mark for droping
vivek mehtaa75c69f2014-01-10 21:50:37 -08006676 buffer->nFilledLen = 0;
vivek mehta79cff222014-01-22 12:17:07 -08006677 }
6678
6679 DEBUG_PRINT_LOW(" -- %s Frame -- info:: fps(%d) lastRenderTime(%lld) bufferTs(%lld) ts_delta(%d)",
6680 buffer->nFilledLen? "Rendering":"Dropping",current_framerate,m_last_rendered_TS,
6681 il_buffer->nTimeStamp,ts_delta);
vivek mehtaa75c69f2014-01-10 21:50:37 -08006682 }
6683
vivek mehta79cff222014-01-22 12:17:07 -08006684 if (il_buffer) {
Arun Menon9230eb82014-02-11 19:19:02 -08006685 log_output_buffers(il_buffer);
6686 if (dynamic_buf_mode) {
6687 unsigned int nPortIndex = 0;
6688 nPortIndex = buffer-((OMX_BUFFERHEADERTYPE *)client_buffers.get_il_buf_hdr());
6689
6690 if (!secure_mode) {
6691 munmap(drv_ctx.ptr_outputbuffer[nPortIndex].bufferaddr,
6692 drv_ctx.ptr_outputbuffer[nPortIndex].mmaped_size);
6693 }
6694
6695 //Clear graphic buffer handles in dynamic mode
6696 native_buffer[nPortIndex].privatehandle = NULL;
6697 native_buffer[nPortIndex].nativehandle = NULL;
6698 }
Arun Menon906de572013-06-18 17:01:40 -07006699 m_cb.FillBufferDone (hComp,m_app_data,il_buffer);
vivek mehta79cff222014-01-22 12:17:07 -08006700 } else {
Arun Menon906de572013-06-18 17:01:40 -07006701 DEBUG_PRINT_ERROR("Invalid buffer address from get_il_buf_hdr");
6702 return OMX_ErrorBadParameter;
6703 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006704 DEBUG_PRINT_LOW("After Fill Buffer Done callback %lu",pPMEMInfo->pmem_fd);
Arun Menon906de572013-06-18 17:01:40 -07006705 } else {
6706 return OMX_ErrorBadParameter;
Vinay Kaliada4f4422013-01-09 10:45:03 -08006707 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006708
Praveen Chavancf924182013-12-06 23:16:23 -08006709#ifdef ADAPTIVE_PLAYBACK_SUPPORTED
Pushkaraj Patil8f98adf2014-02-12 13:32:00 +05306710 if (m_smoothstreaming_mode && m_out_mem_ptr) {
Praveen Chavancf924182013-12-06 23:16:23 -08006711 OMX_U32 buf_index = buffer - m_out_mem_ptr;
6712 BufferDim_t dim;
Pushkaraj Patil8f98adf2014-02-12 13:32:00 +05306713 private_handle_t *private_handle = NULL;
Praveen Chavancf924182013-12-06 23:16:23 -08006714 dim.sliceWidth = drv_ctx.video_resolution.frame_width;
6715 dim.sliceHeight = drv_ctx.video_resolution.frame_height;
Pushkaraj Patil8f98adf2014-02-12 13:32:00 +05306716 if (native_buffer[buf_index].privatehandle)
6717 private_handle = native_buffer[buf_index].privatehandle;
Praveen Chavancf924182013-12-06 23:16:23 -08006718 if (private_handle) {
6719 DEBUG_PRINT_LOW("set metadata: update buf-geometry with stride %d slice %d",
6720 dim.sliceWidth, dim.sliceHeight);
6721 setMetaData(private_handle, UPDATE_BUFFER_GEOMETRY, (void*)&dim);
6722 }
6723 }
6724#endif
6725
Arun Menon906de572013-06-18 17:01:40 -07006726 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006727}
6728
6729OMX_ERRORTYPE omx_vdec::empty_buffer_done(OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07006730 OMX_BUFFERHEADERTYPE* buffer)
Shalaj Jain273b3e02012-06-22 19:08:03 -07006731{
6732
Surajit Podderd2644d52013-08-28 17:59:06 +05306733 if (buffer == NULL || ((buffer - m_inp_mem_ptr) > (int)drv_ctx.ip_buf.actualcount)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006734 DEBUG_PRINT_ERROR("empty_buffer_done: ERROR bufhdr = %p", buffer);
Arun Menon906de572013-06-18 17:01:40 -07006735 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006736 }
6737
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006738 DEBUG_PRINT_LOW("empty_buffer_done: bufhdr = %p, bufhdr->pBuffer = %p",
Arun Menon906de572013-06-18 17:01:40 -07006739 buffer, buffer->pBuffer);
Shalaj Jain273b3e02012-06-22 19:08:03 -07006740 pending_input_buffers--;
6741
Arun Menon906de572013-06-18 17:01:40 -07006742 if (arbitrary_bytes) {
6743 if (pdest_frame == NULL && input_flush_progress == false) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006744 DEBUG_PRINT_LOW("Push input from buffer done address of Buffer %p",buffer);
Arun Menon906de572013-06-18 17:01:40 -07006745 pdest_frame = buffer;
6746 buffer->nFilledLen = 0;
6747 buffer->nTimeStamp = LLONG_MAX;
6748 push_input_buffer (hComp);
6749 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006750 DEBUG_PRINT_LOW("Push buffer into freeq address of Buffer %p",buffer);
Arun Menon906de572013-06-18 17:01:40 -07006751 buffer->nFilledLen = 0;
6752 if (!m_input_free_q.insert_entry((unsigned)buffer,
6753 (unsigned)NULL, (unsigned)NULL)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006754 DEBUG_PRINT_ERROR("ERROR:i/p free Queue is FULL Error");
Arun Menon906de572013-06-18 17:01:40 -07006755 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07006756 }
Arun Menon906de572013-06-18 17:01:40 -07006757 } else if (m_cb.EmptyBufferDone) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006758 buffer->nFilledLen = 0;
Arun Menon906de572013-06-18 17:01:40 -07006759 if (input_use_buffer == true) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006760 buffer = &m_inp_heap_ptr[buffer-m_inp_mem_ptr];
6761 }
6762 m_cb.EmptyBufferDone(hComp ,m_app_data, buffer);
6763 }
6764 return OMX_ErrorNone;
6765}
6766
Shalaj Jain273b3e02012-06-22 19:08:03 -07006767int omx_vdec::async_message_process (void *context, void* message)
6768{
Arun Menon906de572013-06-18 17:01:40 -07006769 omx_vdec* omx = NULL;
6770 struct vdec_msginfo *vdec_msg = NULL;
6771 OMX_BUFFERHEADERTYPE* omxhdr = NULL;
6772 struct v4l2_buffer *v4l2_buf_ptr = NULL;
6773 struct vdec_output_frameinfo *output_respbuf = NULL;
6774 int rc=1;
6775 if (context == NULL || message == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006776 DEBUG_PRINT_ERROR("FATAL ERROR in omx_vdec::async_message_process NULL Check");
Arun Menon906de572013-06-18 17:01:40 -07006777 return -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006778 }
Arun Menon906de572013-06-18 17:01:40 -07006779 vdec_msg = (struct vdec_msginfo *)message;
Shalaj Jain273b3e02012-06-22 19:08:03 -07006780
Arun Menon906de572013-06-18 17:01:40 -07006781 omx = reinterpret_cast<omx_vdec*>(context);
Vinay Kaliab9e98102013-04-02 19:31:43 -07006782
Arun Menon906de572013-06-18 17:01:40 -07006783 switch (vdec_msg->msgcode) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07006784
Arun Menon906de572013-06-18 17:01:40 -07006785 case VDEC_MSG_EVT_HW_ERROR:
6786 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6787 OMX_COMPONENT_GENERATE_HARDWARE_ERROR);
6788 break;
6789
6790 case VDEC_MSG_RESP_START_DONE:
6791 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6792 OMX_COMPONENT_GENERATE_START_DONE);
6793 break;
6794
6795 case VDEC_MSG_RESP_STOP_DONE:
6796 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6797 OMX_COMPONENT_GENERATE_STOP_DONE);
6798 break;
6799
6800 case VDEC_MSG_RESP_RESUME_DONE:
6801 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6802 OMX_COMPONENT_GENERATE_RESUME_DONE);
6803 break;
6804
6805 case VDEC_MSG_RESP_PAUSE_DONE:
6806 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6807 OMX_COMPONENT_GENERATE_PAUSE_DONE);
6808 break;
6809
6810 case VDEC_MSG_RESP_FLUSH_INPUT_DONE:
6811 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6812 OMX_COMPONENT_GENERATE_EVENT_INPUT_FLUSH);
6813 break;
6814 case VDEC_MSG_RESP_FLUSH_OUTPUT_DONE:
6815 omx->post_event ((unsigned)NULL, vdec_msg->status_code,\
6816 OMX_COMPONENT_GENERATE_EVENT_OUTPUT_FLUSH);
6817 break;
6818 case VDEC_MSG_RESP_INPUT_FLUSHED:
6819 case VDEC_MSG_RESP_INPUT_BUFFER_DONE:
6820
6821 /* omxhdr = (OMX_BUFFERHEADERTYPE* )
6822 vdec_msg->msgdata.input_frame_clientdata; */
6823
6824 v4l2_buf_ptr = (v4l2_buffer*)vdec_msg->msgdata.input_frame_clientdata;
6825 omxhdr=omx->m_inp_mem_ptr+v4l2_buf_ptr->index;
6826 if (omxhdr == NULL ||
Surajit Podderd2644d52013-08-28 17:59:06 +05306827 ((omxhdr - omx->m_inp_mem_ptr) > (int)omx->drv_ctx.ip_buf.actualcount) ) {
Arun Menon906de572013-06-18 17:01:40 -07006828 omxhdr = NULL;
6829 vdec_msg->status_code = VDEC_S_EFATAL;
6830 }
6831 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_INPUT_UNSUPPORTED) {
6832 DEBUG_PRINT_HIGH("Unsupported input");
6833 omx->omx_report_error ();
6834 }
6835 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_DATA_CORRUPT) {
6836 vdec_msg->status_code = VDEC_S_INPUT_BITSTREAM_ERR;
6837 }
6838 omx->post_event ((unsigned int)omxhdr,vdec_msg->status_code,
6839 OMX_COMPONENT_GENERATE_EBD);
6840 break;
6841 case VDEC_MSG_EVT_INFO_FIELD_DROPPED:
6842 int64_t *timestamp;
6843 timestamp = (int64_t *) malloc(sizeof(int64_t));
6844 if (timestamp) {
6845 *timestamp = vdec_msg->msgdata.output_frame.time_stamp;
6846 omx->post_event ((unsigned int)timestamp, vdec_msg->status_code,
6847 OMX_COMPONENT_GENERATE_INFO_FIELD_DROPPED);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006848 DEBUG_PRINT_HIGH("Field dropped time stamp is %lld",
Arun Menon906de572013-06-18 17:01:40 -07006849 vdec_msg->msgdata.output_frame.time_stamp);
6850 }
6851 break;
6852 case VDEC_MSG_RESP_OUTPUT_FLUSHED:
6853 case VDEC_MSG_RESP_OUTPUT_BUFFER_DONE:
6854
6855 v4l2_buf_ptr = (v4l2_buffer*)vdec_msg->msgdata.output_frame.client_data;
6856 omxhdr=omx->m_out_mem_ptr+v4l2_buf_ptr->index;
6857 DEBUG_PRINT_LOW("[RespBufDone] Buf(%p) Ts(%lld) Pic_type(%u)",
6858 omxhdr, vdec_msg->msgdata.output_frame.time_stamp,
6859 vdec_msg->msgdata.output_frame.pic_type);
6860
6861 if (omxhdr && omxhdr->pOutputPortPrivate &&
Surajit Podderd2644d52013-08-28 17:59:06 +05306862 ((omxhdr - omx->m_out_mem_ptr) < (int)omx->drv_ctx.op_buf.actualcount) &&
Arun Menon906de572013-06-18 17:01:40 -07006863 (((struct vdec_output_frameinfo *)omxhdr->pOutputPortPrivate
Surajit Podderd2644d52013-08-28 17:59:06 +05306864 - omx->drv_ctx.ptr_respbuffer) < (int)omx->drv_ctx.op_buf.actualcount)) {
Arun Menonbdb80b02013-08-12 17:45:54 -07006865 if (omx->dynamic_buf_mode && vdec_msg->msgdata.output_frame.len) {
6866 vdec_msg->msgdata.output_frame.len = omxhdr->nAllocLen;
6867 }
Arun Menon906de572013-06-18 17:01:40 -07006868 if ( vdec_msg->msgdata.output_frame.len <= omxhdr->nAllocLen) {
6869 omxhdr->nFilledLen = vdec_msg->msgdata.output_frame.len;
6870 omxhdr->nOffset = vdec_msg->msgdata.output_frame.offset;
6871 omxhdr->nTimeStamp = vdec_msg->msgdata.output_frame.time_stamp;
6872 omxhdr->nFlags = 0;
6873
Deva Ramasubramanianc1c7c122013-09-10 21:50:43 -07006874 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_EOS) {
Arun Menon906de572013-06-18 17:01:40 -07006875 omxhdr->nFlags |= OMX_BUFFERFLAG_EOS;
6876 //rc = -1;
6877 }
6878 if (omxhdr->nFilledLen) {
6879 omxhdr->nFlags |= OMX_BUFFERFLAG_ENDOFFRAME;
6880 }
6881 if (v4l2_buf_ptr->flags & V4L2_BUF_FLAG_KEYFRAME || v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_IDRFRAME) {
6882 omxhdr->nFlags |= OMX_BUFFERFLAG_SYNCFRAME;
6883 } else {
6884 omxhdr->nFlags &= ~OMX_BUFFERFLAG_SYNCFRAME;
6885 }
6886 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_EOSEQ) {
6887 omxhdr->nFlags |= QOMX_VIDEO_BUFFERFLAG_EOSEQ;
6888 }
6889 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_DECODEONLY) {
6890 omxhdr->nFlags |= OMX_BUFFERFLAG_DECODEONLY;
6891 }
Arun Menon7b6fd642014-02-13 16:48:36 -08006892
6893 if (v4l2_buf_ptr->flags & V4L2_MSM_BUF_FLAG_MBAFF) {
6894 omxhdr->nFlags |= QOMX_VIDEO_BUFFERFLAG_MBAFF;
6895 }
6896
Arun Menonbdb80b02013-08-12 17:45:54 -07006897 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_READONLY) {
Arun Menone50f6ef2013-09-30 15:08:27 -07006898 omxhdr->nFlags |= OMX_BUFFERFLAG_READONLY;
Arun Menonbdb80b02013-08-12 17:45:54 -07006899 DEBUG_PRINT_LOW("F_B_D: READONLY BUFFER - REFERENCE WITH F/W fd = %d",
6900 omx->drv_ctx.ptr_outputbuffer[v4l2_buf_ptr->index].pmem_fd);
6901 }
Arun Menonbdb80b02013-08-12 17:45:54 -07006902 if (omx->dynamic_buf_mode && !(v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_READONLY)) {
6903 omx->buf_ref_remove(omx->drv_ctx.ptr_outputbuffer[v4l2_buf_ptr->index].pmem_fd,
6904 omxhdr->nOffset);
6905 }
Arun Menon906de572013-06-18 17:01:40 -07006906 if (omxhdr && (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_DROP_FRAME) &&
6907 !(v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_DECODEONLY) &&
Deva Ramasubramanianc1c7c122013-09-10 21:50:43 -07006908 !(v4l2_buf_ptr->flags & V4L2_QCOM_BUF_FLAG_EOS)) {
Praneeth Paladugu17364df2013-07-30 11:34:16 -07006909 omx->time_stamp_dts.remove_time_stamp(
6910 omxhdr->nTimeStamp,
6911 (omx->drv_ctx.interlace != VDEC_InterlaceFrameProgressive)
6912 ?true:false);
Arun Menon906de572013-06-18 17:01:40 -07006913 omx->post_event ((unsigned)NULL,(unsigned int)omxhdr,
6914 OMX_COMPONENT_GENERATE_FTB);
6915 break;
6916 }
6917 if (v4l2_buf_ptr->flags & V4L2_QCOM_BUF_DATA_CORRUPT) {
6918 omxhdr->nFlags |= OMX_BUFFERFLAG_DATACORRUPT;
6919 }
6920 vdec_msg->msgdata.output_frame.bufferaddr =
6921 omx->drv_ctx.ptr_outputbuffer[v4l2_buf_ptr->index].bufferaddr;
6922 int format_notably_changed = 0;
6923 if (omxhdr->nFilledLen &&
Surajit Podderd2644d52013-08-28 17:59:06 +05306924 (omxhdr->nFilledLen != (unsigned)omx->prev_n_filled_len)) {
Arun Menon906de572013-06-18 17:01:40 -07006925 if ((vdec_msg->msgdata.output_frame.framesize.bottom != omx->drv_ctx.video_resolution.frame_height) ||
6926 (vdec_msg->msgdata.output_frame.framesize.right != omx->drv_ctx.video_resolution.frame_width)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006927 DEBUG_PRINT_HIGH("Height/Width information has changed");
Arun Menon906de572013-06-18 17:01:40 -07006928 omx->drv_ctx.video_resolution.frame_height = vdec_msg->msgdata.output_frame.framesize.bottom;
6929 omx->drv_ctx.video_resolution.frame_width = vdec_msg->msgdata.output_frame.framesize.right;
6930 format_notably_changed = 1;
6931 }
6932 }
6933 if (omxhdr->nFilledLen && (((unsigned)omx->rectangle.nLeft !=
6934 vdec_msg->msgdata.output_frame.framesize.left)
6935 || ((unsigned)omx->rectangle.nTop != vdec_msg->msgdata.output_frame.framesize.top)
6936 || (omx->rectangle.nWidth != vdec_msg->msgdata.output_frame.framesize.right)
6937 || (omx->rectangle.nHeight != vdec_msg->msgdata.output_frame.framesize.bottom))) {
6938 if ((vdec_msg->msgdata.output_frame.framesize.bottom != omx->drv_ctx.video_resolution.frame_height) ||
6939 (vdec_msg->msgdata.output_frame.framesize.right != omx->drv_ctx.video_resolution.frame_width)) {
6940 omx->drv_ctx.video_resolution.frame_height = vdec_msg->msgdata.output_frame.framesize.bottom;
6941 omx->drv_ctx.video_resolution.frame_width = vdec_msg->msgdata.output_frame.framesize.right;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006942 DEBUG_PRINT_HIGH("Height/Width information has changed. W: %d --> %d, H: %d --> %d",
Arun Menon906de572013-06-18 17:01:40 -07006943 omx->drv_ctx.video_resolution.frame_width, vdec_msg->msgdata.output_frame.framesize.right,
6944 omx->drv_ctx.video_resolution.frame_height, vdec_msg->msgdata.output_frame.framesize.bottom);
6945 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006946 DEBUG_PRINT_HIGH("Crop information changed. W: %lu --> %d, H: %lu -> %d",
Arun Menon906de572013-06-18 17:01:40 -07006947 omx->rectangle.nWidth, vdec_msg->msgdata.output_frame.framesize.right,
6948 omx->rectangle.nHeight, vdec_msg->msgdata.output_frame.framesize.bottom);
Jayasena Sangaraboina20283de2013-08-13 11:41:41 -07006949 if (vdec_msg->msgdata.output_frame.framesize.left + vdec_msg->msgdata.output_frame.framesize.right >=
6950 omx->drv_ctx.video_resolution.frame_width) {
6951 vdec_msg->msgdata.output_frame.framesize.left = 0;
6952 if (vdec_msg->msgdata.output_frame.framesize.right > omx->drv_ctx.video_resolution.frame_width) {
6953 vdec_msg->msgdata.output_frame.framesize.right = omx->drv_ctx.video_resolution.frame_width;
6954 }
6955 }
6956 if (vdec_msg->msgdata.output_frame.framesize.top + vdec_msg->msgdata.output_frame.framesize.bottom >=
6957 omx->drv_ctx.video_resolution.frame_height) {
6958 vdec_msg->msgdata.output_frame.framesize.top = 0;
6959 if (vdec_msg->msgdata.output_frame.framesize.bottom > omx->drv_ctx.video_resolution.frame_height) {
6960 vdec_msg->msgdata.output_frame.framesize.bottom = omx->drv_ctx.video_resolution.frame_height;
6961 }
6962 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006963 DEBUG_PRINT_LOW("omx_vdec: Adjusted Dim L: %d, T: %d, R: %d, B: %d, W: %d, H: %d",
Jayasena Sangaraboina20283de2013-08-13 11:41:41 -07006964 vdec_msg->msgdata.output_frame.framesize.left,
6965 vdec_msg->msgdata.output_frame.framesize.top,
6966 vdec_msg->msgdata.output_frame.framesize.right,
6967 vdec_msg->msgdata.output_frame.framesize.bottom,
6968 omx->drv_ctx.video_resolution.frame_width,
6969 omx->drv_ctx.video_resolution.frame_height);
Arun Menon906de572013-06-18 17:01:40 -07006970 omx->rectangle.nLeft = vdec_msg->msgdata.output_frame.framesize.left;
6971 omx->rectangle.nTop = vdec_msg->msgdata.output_frame.framesize.top;
6972 omx->rectangle.nWidth = vdec_msg->msgdata.output_frame.framesize.right;
6973 omx->rectangle.nHeight = vdec_msg->msgdata.output_frame.framesize.bottom;
6974 format_notably_changed = 1;
6975 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07006976 DEBUG_PRINT_HIGH("Left: %d, Right: %d, top: %d, Bottom: %d",
Jayasena Sangaraboina20283de2013-08-13 11:41:41 -07006977 vdec_msg->msgdata.output_frame.framesize.left,vdec_msg->msgdata.output_frame.framesize.right,
6978 vdec_msg->msgdata.output_frame.framesize.top, vdec_msg->msgdata.output_frame.framesize.bottom);
Arun Menon906de572013-06-18 17:01:40 -07006979 if (format_notably_changed) {
6980 if (omx->is_video_session_supported()) {
Surajit Podderd2644d52013-08-28 17:59:06 +05306981 omx->post_event (0, vdec_msg->status_code,
Arun Menon906de572013-06-18 17:01:40 -07006982 OMX_COMPONENT_GENERATE_UNSUPPORTED_SETTING);
6983 } else {
6984 if (!omx->client_buffers.update_buffer_req()) {
6985 DEBUG_PRINT_ERROR("Setting c2D buffer requirements failed");
6986 }
6987 omx->post_event (OMX_CORE_OUTPUT_PORT_INDEX, OMX_IndexConfigCommonOutputCrop,
6988 OMX_COMPONENT_GENERATE_PORT_RECONFIG);
6989 }
6990 }
6991 if (omxhdr->nFilledLen)
6992 omx->prev_n_filled_len = omxhdr->nFilledLen;
6993
6994 output_respbuf = (struct vdec_output_frameinfo *)\
6995 omxhdr->pOutputPortPrivate;
6996 output_respbuf->len = vdec_msg->msgdata.output_frame.len;
6997 output_respbuf->offset = vdec_msg->msgdata.output_frame.offset;
6998 if (v4l2_buf_ptr->flags & V4L2_BUF_FLAG_KEYFRAME) {
6999 output_respbuf->pic_type = PICTURE_TYPE_I;
7000 }
7001 if (v4l2_buf_ptr->flags & V4L2_BUF_FLAG_PFRAME) {
7002 output_respbuf->pic_type = PICTURE_TYPE_P;
7003 }
7004 if (v4l2_buf_ptr->flags & V4L2_BUF_FLAG_BFRAME) {
7005 output_respbuf->pic_type = PICTURE_TYPE_B;
7006 }
7007
7008 if (omx->output_use_buffer)
7009 memcpy ( omxhdr->pBuffer, (void *)
7010 ((unsigned long)vdec_msg->msgdata.output_frame.bufferaddr +
7011 (unsigned long)vdec_msg->msgdata.output_frame.offset),
7012 vdec_msg->msgdata.output_frame.len);
7013 } else
7014 omxhdr->nFilledLen = 0;
7015 omx->post_event ((unsigned int)omxhdr, vdec_msg->status_code,
7016 OMX_COMPONENT_GENERATE_FBD);
7017 } else if (vdec_msg->msgdata.output_frame.flags & OMX_BUFFERFLAG_EOS)
7018 omx->post_event ((unsigned int)NULL, vdec_msg->status_code,
7019 OMX_COMPONENT_GENERATE_EOS_DONE);
7020 else
7021 omx->post_event ((unsigned int)NULL, vdec_msg->status_code,
7022 OMX_COMPONENT_GENERATE_HARDWARE_ERROR);
7023 break;
7024 case VDEC_MSG_EVT_CONFIG_CHANGED:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007025 DEBUG_PRINT_HIGH("Port settings changed");
Arun Menon906de572013-06-18 17:01:40 -07007026 omx->post_event (OMX_CORE_OUTPUT_PORT_INDEX, OMX_IndexParamPortDefinition,
7027 OMX_COMPONENT_GENERATE_PORT_RECONFIG);
7028 break;
7029 default:
7030 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007031 }
Arun Menon906de572013-06-18 17:01:40 -07007032 return rc;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007033}
7034
7035OMX_ERRORTYPE omx_vdec::empty_this_buffer_proxy_arbitrary (
Arun Menon906de572013-06-18 17:01:40 -07007036 OMX_HANDLETYPE hComp,
7037 OMX_BUFFERHEADERTYPE *buffer
7038 )
Shalaj Jain273b3e02012-06-22 19:08:03 -07007039{
Arun Menon906de572013-06-18 17:01:40 -07007040 unsigned address,p2,id;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007041 DEBUG_PRINT_LOW("Empty this arbitrary");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007042
Arun Menon906de572013-06-18 17:01:40 -07007043 if (buffer == NULL) {
7044 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007045 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007046 DEBUG_PRINT_LOW("ETBProxyArb: bufhdr = %p, bufhdr->pBuffer = %p", buffer, buffer->pBuffer);
7047 DEBUG_PRINT_LOW("ETBProxyArb: nFilledLen %lu, flags %lu, timestamp %lld",
Arun Menon906de572013-06-18 17:01:40 -07007048 buffer->nFilledLen, buffer->nFlags, buffer->nTimeStamp);
7049
7050 /* return zero length and not an EOS buffer */
7051 /* return buffer if input flush in progress */
7052 if ((input_flush_progress == true) || ((buffer->nFilledLen == 0) &&
7053 ((buffer->nFlags & OMX_BUFFERFLAG_EOS) == 0))) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007054 DEBUG_PRINT_HIGH("return zero legth buffer or flush in progress");
Arun Menon906de572013-06-18 17:01:40 -07007055 m_cb.EmptyBufferDone (hComp,m_app_data,buffer);
7056 return OMX_ErrorNone;
7057 }
7058
7059 if (psource_frame == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007060 DEBUG_PRINT_LOW("Set Buffer as source Buffer %p time stamp %lld",buffer,buffer->nTimeStamp);
Arun Menon906de572013-06-18 17:01:40 -07007061 psource_frame = buffer;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007062 DEBUG_PRINT_LOW("Try to Push One Input Buffer ");
Arun Menon906de572013-06-18 17:01:40 -07007063 push_input_buffer (hComp);
7064 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007065 DEBUG_PRINT_LOW("Push the source buffer into pendingq %p",buffer);
Arun Menon906de572013-06-18 17:01:40 -07007066 if (!m_input_pending_q.insert_entry((unsigned)buffer, (unsigned)NULL,
7067 (unsigned)NULL)) {
7068 return OMX_ErrorBadParameter;
7069 }
7070 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007071
Sowmya Pandiri302f5ab2014-04-03 13:41:03 -07007072 if (codec_config_flag && !(buffer->nFlags & OMX_BUFFERFLAG_CODECCONFIG)) {
7073 codec_config_flag = false;
7074 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007075
Arun Menon906de572013-06-18 17:01:40 -07007076 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007077}
7078
7079OMX_ERRORTYPE omx_vdec::push_input_buffer (OMX_HANDLETYPE hComp)
7080{
Arun Menon906de572013-06-18 17:01:40 -07007081 unsigned address,p2,id;
7082 OMX_ERRORTYPE ret = OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007083
Arun Menon906de572013-06-18 17:01:40 -07007084 if (pdest_frame == NULL || psource_frame == NULL) {
7085 /*Check if we have a destination buffer*/
7086 if (pdest_frame == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007087 DEBUG_PRINT_LOW("Get a Destination buffer from the queue");
Arun Menon906de572013-06-18 17:01:40 -07007088 if (m_input_free_q.m_size) {
7089 m_input_free_q.pop_entry(&address,&p2,&id);
7090 pdest_frame = (OMX_BUFFERHEADERTYPE *)address;
7091 pdest_frame->nFilledLen = 0;
7092 pdest_frame->nTimeStamp = LLONG_MAX;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007093 DEBUG_PRINT_LOW("Address of Pmem Buffer %p",pdest_frame);
Arun Menon906de572013-06-18 17:01:40 -07007094 }
7095 }
7096
7097 /*Check if we have a destination buffer*/
7098 if (psource_frame == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007099 DEBUG_PRINT_LOW("Get a source buffer from the queue");
Arun Menon906de572013-06-18 17:01:40 -07007100 if (m_input_pending_q.m_size) {
7101 m_input_pending_q.pop_entry(&address,&p2,&id);
7102 psource_frame = (OMX_BUFFERHEADERTYPE *)address;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007103 DEBUG_PRINT_LOW("Next source Buffer %p time stamp %lld",psource_frame,
Arun Menon906de572013-06-18 17:01:40 -07007104 psource_frame->nTimeStamp);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007105 DEBUG_PRINT_LOW("Next source Buffer flag %lu length %lu",
Arun Menon906de572013-06-18 17:01:40 -07007106 psource_frame->nFlags,psource_frame->nFilledLen);
7107
7108 }
7109 }
7110
Shalaj Jain273b3e02012-06-22 19:08:03 -07007111 }
7112
Arun Menon906de572013-06-18 17:01:40 -07007113 while ((pdest_frame != NULL) && (psource_frame != NULL)) {
7114 switch (codec_type_parse) {
7115 case CODEC_TYPE_MPEG4:
7116 case CODEC_TYPE_H263:
7117 case CODEC_TYPE_MPEG2:
7118 ret = push_input_sc_codec(hComp);
7119 break;
7120 case CODEC_TYPE_H264:
7121 ret = push_input_h264(hComp);
7122 break;
7123 case CODEC_TYPE_VC1:
7124 ret = push_input_vc1(hComp);
7125 break;
7126 default:
7127 break;
7128 }
7129 if (ret != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007130 DEBUG_PRINT_ERROR("Pushing input Buffer Failed");
Arun Menon906de572013-06-18 17:01:40 -07007131 omx_report_error ();
7132 break;
7133 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007134 }
7135
Arun Menon906de572013-06-18 17:01:40 -07007136 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007137}
7138
7139OMX_ERRORTYPE omx_vdec::push_input_sc_codec(OMX_HANDLETYPE hComp)
7140{
Arun Menon906de572013-06-18 17:01:40 -07007141 OMX_U32 partial_frame = 1;
7142 OMX_BOOL generate_ebd = OMX_TRUE;
7143 unsigned address = 0, p2 = 0, id = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007144
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007145 DEBUG_PRINT_LOW("Start Parsing the bit stream address %p TimeStamp %lld",
Arun Menon906de572013-06-18 17:01:40 -07007146 psource_frame,psource_frame->nTimeStamp);
7147 if (m_frame_parser.parse_sc_frame(psource_frame,
7148 pdest_frame,&partial_frame) == -1) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007149 DEBUG_PRINT_ERROR("Error In Parsing Return Error");
Arun Menon906de572013-06-18 17:01:40 -07007150 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007151 }
Arun Menon906de572013-06-18 17:01:40 -07007152
7153 if (partial_frame == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007154 DEBUG_PRINT_LOW("Frame size %lu source %p frame count %d",
Arun Menon906de572013-06-18 17:01:40 -07007155 pdest_frame->nFilledLen,psource_frame,frame_count);
7156
7157
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007158 DEBUG_PRINT_LOW("TimeStamp updated %lld", pdest_frame->nTimeStamp);
Arun Menon906de572013-06-18 17:01:40 -07007159 /*First Parsed buffer will have only header Hence skip*/
7160 if (frame_count == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007161 DEBUG_PRINT_LOW("H263/MPEG4 Codec First Frame ");
Arun Menon906de572013-06-18 17:01:40 -07007162
7163 if (codec_type_parse == CODEC_TYPE_MPEG4 ||
7164 codec_type_parse == CODEC_TYPE_DIVX) {
7165 mp4StreamType psBits;
7166 psBits.data = pdest_frame->pBuffer + pdest_frame->nOffset;
7167 psBits.numBytes = pdest_frame->nFilledLen;
7168 mp4_headerparser.parseHeader(&psBits);
7169 }
7170
7171 frame_count++;
7172 } else {
7173 pdest_frame->nFlags &= ~OMX_BUFFERFLAG_EOS;
7174 if (pdest_frame->nFilledLen) {
7175 /*Push the frame to the Decoder*/
7176 if (empty_this_buffer_proxy(hComp,pdest_frame) != OMX_ErrorNone) {
7177 return OMX_ErrorBadParameter;
7178 }
7179 frame_count++;
7180 pdest_frame = NULL;
7181
7182 if (m_input_free_q.m_size) {
7183 m_input_free_q.pop_entry(&address,&p2,&id);
7184 pdest_frame = (OMX_BUFFERHEADERTYPE *) address;
7185 pdest_frame->nFilledLen = 0;
7186 }
7187 } else if (!(psource_frame->nFlags & OMX_BUFFERFLAG_EOS)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007188 DEBUG_PRINT_ERROR("Zero len buffer return back to POOL");
Arun Menon906de572013-06-18 17:01:40 -07007189 m_input_free_q.insert_entry((unsigned) pdest_frame, (unsigned)NULL,
7190 (unsigned)NULL);
7191 pdest_frame = NULL;
7192 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007193 }
Arun Menon906de572013-06-18 17:01:40 -07007194 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007195 DEBUG_PRINT_LOW("Not a Complete Frame %lu",pdest_frame->nFilledLen);
Arun Menon906de572013-06-18 17:01:40 -07007196 /*Check if Destination Buffer is full*/
7197 if (pdest_frame->nAllocLen ==
7198 pdest_frame->nFilledLen + pdest_frame->nOffset) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007199 DEBUG_PRINT_ERROR("ERROR:Frame Not found though Destination Filled");
Arun Menon906de572013-06-18 17:01:40 -07007200 return OMX_ErrorStreamCorrupt;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007201 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007202 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007203
Arun Menon906de572013-06-18 17:01:40 -07007204 if (psource_frame->nFilledLen == 0) {
7205 if (psource_frame->nFlags & OMX_BUFFERFLAG_EOS) {
7206 if (pdest_frame) {
7207 pdest_frame->nFlags |= psource_frame->nFlags;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007208 DEBUG_PRINT_LOW("Frame Found start Decoding Size =%lu TimeStamp = %lld",
Arun Menon906de572013-06-18 17:01:40 -07007209 pdest_frame->nFilledLen,pdest_frame->nTimeStamp);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007210 DEBUG_PRINT_LOW("Found a frame size = %lu number = %d",
Arun Menon906de572013-06-18 17:01:40 -07007211 pdest_frame->nFilledLen,frame_count++);
7212 /*Push the frame to the Decoder*/
7213 if (empty_this_buffer_proxy(hComp,pdest_frame) != OMX_ErrorNone) {
7214 return OMX_ErrorBadParameter;
7215 }
7216 frame_count++;
7217 pdest_frame = NULL;
7218 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007219 DEBUG_PRINT_LOW("Last frame in else dest addr") ;
Arun Menon906de572013-06-18 17:01:40 -07007220 generate_ebd = OMX_FALSE;
7221 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007222 }
Arun Menon906de572013-06-18 17:01:40 -07007223 if (generate_ebd) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007224 DEBUG_PRINT_LOW("Buffer Consumed return back to client %p",psource_frame);
Arun Menon906de572013-06-18 17:01:40 -07007225 m_cb.EmptyBufferDone (hComp,m_app_data,psource_frame);
7226 psource_frame = NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007227
Arun Menon906de572013-06-18 17:01:40 -07007228 if (m_input_pending_q.m_size) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007229 DEBUG_PRINT_LOW("Pull Next source Buffer %p",psource_frame);
Arun Menon906de572013-06-18 17:01:40 -07007230 m_input_pending_q.pop_entry(&address,&p2,&id);
7231 psource_frame = (OMX_BUFFERHEADERTYPE *) address;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007232 DEBUG_PRINT_LOW("Next source Buffer %p time stamp %lld",psource_frame,
Arun Menon906de572013-06-18 17:01:40 -07007233 psource_frame->nTimeStamp);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007234 DEBUG_PRINT_LOW("Next source Buffer flag %lu length %lu",
Arun Menon906de572013-06-18 17:01:40 -07007235 psource_frame->nFlags,psource_frame->nFilledLen);
7236 }
7237 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007238 }
Arun Menon906de572013-06-18 17:01:40 -07007239 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007240}
7241
7242OMX_ERRORTYPE omx_vdec::push_input_h264 (OMX_HANDLETYPE hComp)
7243{
Arun Menon906de572013-06-18 17:01:40 -07007244 OMX_U32 partial_frame = 1;
7245 unsigned address = 0, p2 = 0, id = 0;
7246 OMX_BOOL isNewFrame = OMX_FALSE;
7247 OMX_BOOL generate_ebd = OMX_TRUE;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007248
Arun Menon906de572013-06-18 17:01:40 -07007249 if (h264_scratch.pBuffer == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007250 DEBUG_PRINT_ERROR("ERROR:H.264 Scratch Buffer not allocated");
Arun Menon906de572013-06-18 17:01:40 -07007251 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007252 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007253 DEBUG_PRINT_LOW("Pending h264_scratch.nFilledLen %lu "
Arun Menon906de572013-06-18 17:01:40 -07007254 "look_ahead_nal %d", h264_scratch.nFilledLen, look_ahead_nal);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007255 DEBUG_PRINT_LOW("Pending pdest_frame->nFilledLen %lu",pdest_frame->nFilledLen);
Arun Menon906de572013-06-18 17:01:40 -07007256 if (h264_scratch.nFilledLen && look_ahead_nal) {
7257 look_ahead_nal = false;
7258 if ((pdest_frame->nAllocLen - pdest_frame->nFilledLen) >=
7259 h264_scratch.nFilledLen) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007260 memcpy ((pdest_frame->pBuffer + pdest_frame->nFilledLen),
7261 h264_scratch.pBuffer,h264_scratch.nFilledLen);
7262 pdest_frame->nFilledLen += h264_scratch.nFilledLen;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007263 DEBUG_PRINT_LOW("Copy the previous NAL (h264 scratch) into Dest frame");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007264 h264_scratch.nFilledLen = 0;
Arun Menon906de572013-06-18 17:01:40 -07007265 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007266 DEBUG_PRINT_ERROR("Error:1: Destination buffer overflow for H264");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007267 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007268 }
Arun Menon906de572013-06-18 17:01:40 -07007269 }
Praveen Chavance0b5e82013-08-08 05:23:34 -07007270
7271 /* If an empty input is queued with EOS, do not coalesce with the destination-frame yet, as this may result
7272 in EOS flag getting associated with the destination
7273 */
7274 if (!psource_frame->nFilledLen && (psource_frame->nFlags & OMX_BUFFERFLAG_EOS) &&
7275 pdest_frame->nFilledLen) {
7276 DEBUG_PRINT_HIGH("delay ETB for 'empty buffer with EOS'");
7277 generate_ebd = OMX_FALSE;
7278 }
7279
Arun Menon906de572013-06-18 17:01:40 -07007280 if (nal_length == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007281 DEBUG_PRINT_LOW("Zero NAL, hence parse using start code");
Arun Menon906de572013-06-18 17:01:40 -07007282 if (m_frame_parser.parse_sc_frame(psource_frame,
7283 &h264_scratch,&partial_frame) == -1) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007284 DEBUG_PRINT_ERROR("Error In Parsing Return Error");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007285 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007286 }
Arun Menon906de572013-06-18 17:01:40 -07007287 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007288 DEBUG_PRINT_LOW("Non-zero NAL length clip, hence parse with NAL size %d ",nal_length);
Arun Menon906de572013-06-18 17:01:40 -07007289 if (m_frame_parser.parse_h264_nallength(psource_frame,
7290 &h264_scratch,&partial_frame) == -1) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007291 DEBUG_PRINT_ERROR("Error In Parsing NAL size, Return Error");
Arun Menon906de572013-06-18 17:01:40 -07007292 return OMX_ErrorBadParameter;
7293 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007294 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007295
Arun Menon906de572013-06-18 17:01:40 -07007296 if (partial_frame == 0) {
7297 if (nal_count == 0 && h264_scratch.nFilledLen == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007298 DEBUG_PRINT_LOW("First NAL with Zero Length, hence Skip");
Arun Menon906de572013-06-18 17:01:40 -07007299 nal_count++;
7300 h264_scratch.nTimeStamp = psource_frame->nTimeStamp;
7301 h264_scratch.nFlags = psource_frame->nFlags;
7302 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007303 DEBUG_PRINT_LOW("Parsed New NAL Length = %lu",h264_scratch.nFilledLen);
Arun Menon906de572013-06-18 17:01:40 -07007304 if (h264_scratch.nFilledLen) {
7305 h264_parser->parse_nal((OMX_U8*)h264_scratch.pBuffer, h264_scratch.nFilledLen,
7306 NALU_TYPE_SPS);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007307#ifndef PROCESS_EXTRADATA_IN_OUTPUT_PORT
Arun Menon906de572013-06-18 17:01:40 -07007308 if (client_extradata & OMX_TIMEINFO_EXTRADATA)
7309 h264_parser->parse_nal((OMX_U8*)h264_scratch.pBuffer,
7310 h264_scratch.nFilledLen, NALU_TYPE_SEI);
7311 else if (client_extradata & OMX_FRAMEINFO_EXTRADATA)
7312 // If timeinfo is present frame info from SEI is already processed
7313 h264_parser->parse_nal((OMX_U8*)h264_scratch.pBuffer,
7314 h264_scratch.nFilledLen, NALU_TYPE_SEI);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007315#endif
Arun Menon906de572013-06-18 17:01:40 -07007316 m_frame_parser.mutils->isNewFrame(&h264_scratch, 0, isNewFrame);
7317 nal_count++;
7318 if (VALID_TS(h264_last_au_ts) && !VALID_TS(pdest_frame->nTimeStamp)) {
7319 pdest_frame->nTimeStamp = h264_last_au_ts;
7320 pdest_frame->nFlags = h264_last_au_flags;
7321#ifdef PANSCAN_HDLR
7322 if (client_extradata & OMX_FRAMEINFO_EXTRADATA)
7323 h264_parser->update_panscan_data(h264_last_au_ts);
7324#endif
7325 }
7326 if (m_frame_parser.mutils->nalu_type == NALU_TYPE_NON_IDR ||
7327 m_frame_parser.mutils->nalu_type == NALU_TYPE_IDR) {
7328 h264_last_au_ts = h264_scratch.nTimeStamp;
7329 h264_last_au_flags = h264_scratch.nFlags;
7330#ifndef PROCESS_EXTRADATA_IN_OUTPUT_PORT
7331 if (client_extradata & OMX_TIMEINFO_EXTRADATA) {
7332 OMX_S64 ts_in_sei = h264_parser->process_ts_with_sei_vui(h264_last_au_ts);
7333 if (!VALID_TS(h264_last_au_ts))
7334 h264_last_au_ts = ts_in_sei;
7335 }
7336#endif
7337 } else
7338 h264_last_au_ts = LLONG_MAX;
7339 }
7340
7341 if (!isNewFrame) {
7342 if ( (pdest_frame->nAllocLen - pdest_frame->nFilledLen) >=
7343 h264_scratch.nFilledLen) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007344 DEBUG_PRINT_LOW("Not a NewFrame Copy into Dest len %lu",
Arun Menon906de572013-06-18 17:01:40 -07007345 h264_scratch.nFilledLen);
7346 memcpy ((pdest_frame->pBuffer + pdest_frame->nFilledLen),
7347 h264_scratch.pBuffer,h264_scratch.nFilledLen);
7348 pdest_frame->nFilledLen += h264_scratch.nFilledLen;
7349 if (m_frame_parser.mutils->nalu_type == NALU_TYPE_EOSEQ)
7350 pdest_frame->nFlags |= QOMX_VIDEO_BUFFERFLAG_EOSEQ;
7351 h264_scratch.nFilledLen = 0;
7352 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007353 DEBUG_PRINT_LOW("Error:2: Destination buffer overflow for H264");
Arun Menon906de572013-06-18 17:01:40 -07007354 return OMX_ErrorBadParameter;
7355 }
Leena Winterrowd5a974ce2013-08-06 15:10:36 -07007356 } else if(h264_scratch.nFilledLen) {
Arun Menon906de572013-06-18 17:01:40 -07007357 look_ahead_nal = true;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007358 DEBUG_PRINT_LOW("Frame Found start Decoding Size =%lu TimeStamp = %llu",
Arun Menon906de572013-06-18 17:01:40 -07007359 pdest_frame->nFilledLen,pdest_frame->nTimeStamp);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007360 DEBUG_PRINT_LOW("Found a frame size = %lu number = %d",
Arun Menon906de572013-06-18 17:01:40 -07007361 pdest_frame->nFilledLen,frame_count++);
7362
7363 if (pdest_frame->nFilledLen == 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007364 DEBUG_PRINT_LOW("Copy the Current Frame since and push it");
Arun Menon906de572013-06-18 17:01:40 -07007365 look_ahead_nal = false;
7366 if ( (pdest_frame->nAllocLen - pdest_frame->nFilledLen) >=
7367 h264_scratch.nFilledLen) {
7368 memcpy ((pdest_frame->pBuffer + pdest_frame->nFilledLen),
7369 h264_scratch.pBuffer,h264_scratch.nFilledLen);
7370 pdest_frame->nFilledLen += h264_scratch.nFilledLen;
7371 h264_scratch.nFilledLen = 0;
7372 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007373 DEBUG_PRINT_ERROR("Error:3: Destination buffer overflow for H264");
Arun Menon906de572013-06-18 17:01:40 -07007374 return OMX_ErrorBadParameter;
7375 }
7376 } else {
7377 if (psource_frame->nFilledLen || h264_scratch.nFilledLen) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007378 DEBUG_PRINT_LOW("Reset the EOS Flag");
Arun Menon906de572013-06-18 17:01:40 -07007379 pdest_frame->nFlags &= ~OMX_BUFFERFLAG_EOS;
7380 }
7381 /*Push the frame to the Decoder*/
7382 if (empty_this_buffer_proxy(hComp,pdest_frame) != OMX_ErrorNone) {
7383 return OMX_ErrorBadParameter;
7384 }
7385 //frame_count++;
7386 pdest_frame = NULL;
7387 if (m_input_free_q.m_size) {
7388 m_input_free_q.pop_entry(&address,&p2,&id);
7389 pdest_frame = (OMX_BUFFERHEADERTYPE *) address;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007390 DEBUG_PRINT_LOW("Pop the next pdest_buffer %p",pdest_frame);
Arun Menon906de572013-06-18 17:01:40 -07007391 pdest_frame->nFilledLen = 0;
7392 pdest_frame->nFlags = 0;
7393 pdest_frame->nTimeStamp = LLONG_MAX;
7394 }
7395 }
7396 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007397 }
Arun Menon906de572013-06-18 17:01:40 -07007398 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007399 DEBUG_PRINT_LOW("Not a Complete Frame, pdest_frame->nFilledLen %lu",pdest_frame->nFilledLen);
Arun Menon906de572013-06-18 17:01:40 -07007400 /*Check if Destination Buffer is full*/
7401 if (h264_scratch.nAllocLen ==
7402 h264_scratch.nFilledLen + h264_scratch.nOffset) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007403 DEBUG_PRINT_ERROR("ERROR: Frame Not found though Destination Filled");
Arun Menon906de572013-06-18 17:01:40 -07007404 return OMX_ErrorStreamCorrupt;
7405 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007406 }
Arun Menon906de572013-06-18 17:01:40 -07007407
7408 if (!psource_frame->nFilledLen) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007409 DEBUG_PRINT_LOW("Buffer Consumed return source %p back to client",psource_frame);
Arun Menon906de572013-06-18 17:01:40 -07007410
7411 if (psource_frame->nFlags & OMX_BUFFERFLAG_EOS) {
7412 if (pdest_frame) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007413 DEBUG_PRINT_LOW("EOS Reached Pass Last Buffer");
Arun Menon906de572013-06-18 17:01:40 -07007414 if ( (pdest_frame->nAllocLen - pdest_frame->nFilledLen) >=
7415 h264_scratch.nFilledLen) {
Leena Winterrowd5a974ce2013-08-06 15:10:36 -07007416 if(pdest_frame->nFilledLen == 0) {
7417 /* No residual frame from before, send whatever
7418 * we have left */
7419 memcpy((pdest_frame->pBuffer + pdest_frame->nFilledLen),
7420 h264_scratch.pBuffer, h264_scratch.nFilledLen);
7421 pdest_frame->nFilledLen += h264_scratch.nFilledLen;
7422 h264_scratch.nFilledLen = 0;
7423 pdest_frame->nTimeStamp = h264_scratch.nTimeStamp;
7424 } else {
7425 m_frame_parser.mutils->isNewFrame(&h264_scratch, 0, isNewFrame);
7426 if(!isNewFrame) {
7427 /* Have a residual frame, but we know that the
7428 * AU in this frame is belonging to whatever
7429 * frame we had left over. So append it */
7430 memcpy ((pdest_frame->pBuffer + pdest_frame->nFilledLen),
7431 h264_scratch.pBuffer,h264_scratch.nFilledLen);
7432 pdest_frame->nFilledLen += h264_scratch.nFilledLen;
7433 h264_scratch.nFilledLen = 0;
7434 pdest_frame->nTimeStamp = h264_last_au_ts;
7435 } else {
7436 /* Completely new frame, let's just push what
7437 * we have now. The resulting EBD would trigger
7438 * another push */
7439 generate_ebd = OMX_FALSE;
7440 pdest_frame->nTimeStamp = h264_last_au_ts;
7441 h264_last_au_ts = h264_scratch.nTimeStamp;
7442 }
7443 }
Arun Menon906de572013-06-18 17:01:40 -07007444 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007445 DEBUG_PRINT_ERROR("ERROR:4: Destination buffer overflow for H264");
Arun Menon906de572013-06-18 17:01:40 -07007446 return OMX_ErrorBadParameter;
7447 }
Leena Winterrowd5a974ce2013-08-06 15:10:36 -07007448
7449 /* Iff we coalesced two buffers, inherit the flags of both bufs */
7450 if(generate_ebd == OMX_TRUE) {
7451 pdest_frame->nFlags = h264_scratch.nFlags | psource_frame->nFlags;
7452 }
Arun Menon906de572013-06-18 17:01:40 -07007453
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007454 DEBUG_PRINT_LOW("pdest_frame->nFilledLen =%lu TimeStamp = %llu",
Arun Menon906de572013-06-18 17:01:40 -07007455 pdest_frame->nFilledLen,pdest_frame->nTimeStamp);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007456 DEBUG_PRINT_LOW("Push AU frame number %d to driver", frame_count++);
Arun Menon906de572013-06-18 17:01:40 -07007457#ifndef PROCESS_EXTRADATA_IN_OUTPUT_PORT
7458 if (client_extradata & OMX_TIMEINFO_EXTRADATA) {
7459 OMX_S64 ts_in_sei = h264_parser->process_ts_with_sei_vui(pdest_frame->nTimeStamp);
7460 if (!VALID_TS(pdest_frame->nTimeStamp))
7461 pdest_frame->nTimeStamp = ts_in_sei;
7462 }
7463#endif
7464 /*Push the frame to the Decoder*/
7465 if (empty_this_buffer_proxy(hComp,pdest_frame) != OMX_ErrorNone) {
7466 return OMX_ErrorBadParameter;
7467 }
7468 frame_count++;
7469 pdest_frame = NULL;
7470 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007471 DEBUG_PRINT_LOW("Last frame in else dest addr %p size %lu",
Arun Menon906de572013-06-18 17:01:40 -07007472 pdest_frame,h264_scratch.nFilledLen);
7473 generate_ebd = OMX_FALSE;
7474 }
7475 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007476 }
Arun Menon906de572013-06-18 17:01:40 -07007477 if (generate_ebd && !psource_frame->nFilledLen) {
7478 m_cb.EmptyBufferDone (hComp,m_app_data,psource_frame);
7479 psource_frame = NULL;
7480 if (m_input_pending_q.m_size) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007481 DEBUG_PRINT_LOW("Pull Next source Buffer %p",psource_frame);
Arun Menon906de572013-06-18 17:01:40 -07007482 m_input_pending_q.pop_entry(&address,&p2,&id);
7483 psource_frame = (OMX_BUFFERHEADERTYPE *) address;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007484 DEBUG_PRINT_LOW("Next source Buffer flag %lu src length %lu",
Arun Menon906de572013-06-18 17:01:40 -07007485 psource_frame->nFlags,psource_frame->nFilledLen);
7486 }
7487 }
7488 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007489}
7490
7491OMX_ERRORTYPE omx_vdec::push_input_vc1 (OMX_HANDLETYPE hComp)
7492{
7493 OMX_U8 *buf, *pdest;
7494 OMX_U32 partial_frame = 1;
7495 OMX_U32 buf_len, dest_len;
7496
Arun Menon906de572013-06-18 17:01:40 -07007497 if (first_frame == 0) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007498 first_frame = 1;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007499 DEBUG_PRINT_LOW("First i/p buffer for VC1 arbitrary bytes");
Arun Menon906de572013-06-18 17:01:40 -07007500 if (!m_vendor_config.pData) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007501 DEBUG_PRINT_LOW("Check profile type in 1st source buffer");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007502 buf = psource_frame->pBuffer;
7503 buf_len = psource_frame->nFilledLen;
7504
7505 if ((*((OMX_U32 *) buf) & VC1_SP_MP_START_CODE_MASK) ==
Arun Menon906de572013-06-18 17:01:40 -07007506 VC1_SP_MP_START_CODE) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007507 m_vc1_profile = VC1_SP_MP_RCV;
Arun Menon906de572013-06-18 17:01:40 -07007508 } else if (*((OMX_U32 *) buf) & VC1_AP_SEQ_START_CODE) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007509 m_vc1_profile = VC1_AP;
Arun Menon906de572013-06-18 17:01:40 -07007510 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007511 DEBUG_PRINT_ERROR("Invalid sequence layer in first buffer");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007512 return OMX_ErrorStreamCorrupt;
7513 }
Arun Menon906de572013-06-18 17:01:40 -07007514 } else {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007515 pdest = pdest_frame->pBuffer + pdest_frame->nFilledLen +
7516 pdest_frame->nOffset;
7517 dest_len = pdest_frame->nAllocLen - (pdest_frame->nFilledLen +
Arun Menon906de572013-06-18 17:01:40 -07007518 pdest_frame->nOffset);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007519
Arun Menon906de572013-06-18 17:01:40 -07007520 if (dest_len < m_vendor_config.nDataSize) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007521 DEBUG_PRINT_ERROR("Destination buffer full");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007522 return OMX_ErrorBadParameter;
Arun Menon906de572013-06-18 17:01:40 -07007523 } else {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007524 memcpy(pdest, m_vendor_config.pData, m_vendor_config.nDataSize);
7525 pdest_frame->nFilledLen += m_vendor_config.nDataSize;
7526 }
7527 }
7528 }
7529
Arun Menon906de572013-06-18 17:01:40 -07007530 switch (m_vc1_profile) {
Shalaj Jain273b3e02012-06-22 19:08:03 -07007531 case VC1_AP:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007532 DEBUG_PRINT_LOW("VC1 AP, hence parse using frame start code");
Arun Menon906de572013-06-18 17:01:40 -07007533 if (push_input_sc_codec(hComp) != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007534 DEBUG_PRINT_ERROR("Error In Parsing VC1 AP start code");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007535 return OMX_ErrorBadParameter;
7536 }
Arun Menon906de572013-06-18 17:01:40 -07007537 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007538
7539 case VC1_SP_MP_RCV:
7540 default:
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007541 DEBUG_PRINT_ERROR("Unsupported VC1 profile in ArbitraryBytes Mode");
Shalaj Jain273b3e02012-06-22 19:08:03 -07007542 return OMX_ErrorBadParameter;
7543 }
7544 return OMX_ErrorNone;
7545}
7546
David Ng38e2d232013-03-15 20:05:58 -07007547#ifndef USE_ION
Shalaj Jain273b3e02012-06-22 19:08:03 -07007548bool omx_vdec::align_pmem_buffers(int pmem_fd, OMX_U32 buffer_size,
Arun Menon906de572013-06-18 17:01:40 -07007549 OMX_U32 alignment)
Shalaj Jain273b3e02012-06-22 19:08:03 -07007550{
Arun Menon906de572013-06-18 17:01:40 -07007551 struct pmem_allocation allocation;
7552 allocation.size = buffer_size;
7553 allocation.align = clip2(alignment);
7554 if (allocation.align < 4096) {
7555 allocation.align = 4096;
7556 }
7557 if (ioctl(pmem_fd, PMEM_ALLOCATE_ALIGNED, &allocation) < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007558 DEBUG_PRINT_ERROR("Aligment(%u) failed with pmem driver Sz(%lu)",
Arun Menon906de572013-06-18 17:01:40 -07007559 allocation.align, allocation.size);
7560 return false;
7561 }
7562 return true;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007563}
David Ng38e2d232013-03-15 20:05:58 -07007564#endif
Shalaj Jain273b3e02012-06-22 19:08:03 -07007565#ifdef USE_ION
7566int omx_vdec::alloc_map_ion_memory(OMX_U32 buffer_size,
Arun Menon906de572013-06-18 17:01:40 -07007567 OMX_U32 alignment, struct ion_allocation_data *alloc_data,
7568 struct ion_fd_data *fd_data, int flag)
Shalaj Jain273b3e02012-06-22 19:08:03 -07007569{
Arun Menon906de572013-06-18 17:01:40 -07007570 int fd = -EINVAL;
7571 int rc = -EINVAL;
7572 int ion_dev_flag;
7573 struct vdec_ion ion_buf_info;
7574 if (!alloc_data || buffer_size <= 0 || !fd_data) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007575 DEBUG_PRINT_ERROR("Invalid arguments to alloc_map_ion_memory");
Arun Menon906de572013-06-18 17:01:40 -07007576 return -EINVAL;
7577 }
7578 ion_dev_flag = O_RDONLY;
7579 fd = open (MEM_DEVICE, ion_dev_flag);
7580 if (fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007581 DEBUG_PRINT_ERROR("opening ion device failed with fd = %d", fd);
Arun Menon906de572013-06-18 17:01:40 -07007582 return fd;
7583 }
7584 alloc_data->flags = 0;
7585 if (!secure_mode && (flag & ION_FLAG_CACHED)) {
7586 alloc_data->flags |= ION_FLAG_CACHED;
7587 }
7588 alloc_data->len = buffer_size;
7589 alloc_data->align = clip2(alignment);
7590 if (alloc_data->align < 4096) {
7591 alloc_data->align = 4096;
7592 }
7593 if ((secure_mode) && (flag & ION_SECURE))
7594 alloc_data->flags |= ION_SECURE;
Vinay Kalia53fa6832012-10-11 17:55:30 -07007595
Arun Menon906de572013-06-18 17:01:40 -07007596 alloc_data->heap_mask = ION_HEAP(ION_IOMMU_HEAP_ID);
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05307597 if (secure_mode && (alloc_data->flags & ION_SECURE))
Arun Menon906de572013-06-18 17:01:40 -07007598 alloc_data->heap_mask = ION_HEAP(MEM_HEAP_ID);
7599 rc = ioctl(fd,ION_IOC_ALLOC,alloc_data);
7600 if (rc || !alloc_data->handle) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007601 DEBUG_PRINT_ERROR("ION ALLOC memory failed ");
Arun Menon906de572013-06-18 17:01:40 -07007602 alloc_data->handle = NULL;
7603 close(fd);
7604 fd = -ENOMEM;
7605 return fd;
7606 }
7607 fd_data->handle = alloc_data->handle;
7608 rc = ioctl(fd,ION_IOC_MAP,fd_data);
7609 if (rc) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007610 DEBUG_PRINT_ERROR("ION MAP failed ");
Arun Menon906de572013-06-18 17:01:40 -07007611 ion_buf_info.ion_alloc_data = *alloc_data;
7612 ion_buf_info.ion_device_fd = fd;
7613 ion_buf_info.fd_ion_data = *fd_data;
7614 free_ion_memory(&ion_buf_info);
7615 fd_data->fd =-1;
Arun Menon906de572013-06-18 17:01:40 -07007616 fd = -ENOMEM;
7617 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007618
Arun Menon906de572013-06-18 17:01:40 -07007619 return fd;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007620}
7621
Arun Menon906de572013-06-18 17:01:40 -07007622void omx_vdec::free_ion_memory(struct vdec_ion *buf_ion_info)
7623{
Shalaj Jain273b3e02012-06-22 19:08:03 -07007624
Arun Menon906de572013-06-18 17:01:40 -07007625 if (!buf_ion_info) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007626 DEBUG_PRINT_ERROR("ION: free called with invalid fd/allocdata");
Arun Menon906de572013-06-18 17:01:40 -07007627 return;
7628 }
7629 if (ioctl(buf_ion_info->ion_device_fd,ION_IOC_FREE,
7630 &buf_ion_info->ion_alloc_data.handle)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007631 DEBUG_PRINT_ERROR("ION: free failed" );
Arun Menon906de572013-06-18 17:01:40 -07007632 }
7633 close(buf_ion_info->ion_device_fd);
7634 buf_ion_info->ion_device_fd = -1;
7635 buf_ion_info->ion_alloc_data.handle = NULL;
7636 buf_ion_info->fd_ion_data.fd = -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007637}
7638#endif
7639void omx_vdec::free_output_buffer_header()
7640{
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007641 DEBUG_PRINT_HIGH("ALL output buffers are freed/released");
Arun Menon906de572013-06-18 17:01:40 -07007642 output_use_buffer = false;
7643 ouput_egl_buffers = false;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007644
Arun Menon906de572013-06-18 17:01:40 -07007645 if (m_out_mem_ptr) {
7646 free (m_out_mem_ptr);
7647 m_out_mem_ptr = NULL;
7648 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007649
Arun Menon906de572013-06-18 17:01:40 -07007650 if (m_platform_list) {
7651 free(m_platform_list);
7652 m_platform_list = NULL;
7653 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007654
Arun Menon906de572013-06-18 17:01:40 -07007655 if (drv_ctx.ptr_respbuffer) {
7656 free (drv_ctx.ptr_respbuffer);
7657 drv_ctx.ptr_respbuffer = NULL;
7658 }
7659 if (drv_ctx.ptr_outputbuffer) {
7660 free (drv_ctx.ptr_outputbuffer);
7661 drv_ctx.ptr_outputbuffer = NULL;
7662 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007663#ifdef USE_ION
7664 if (drv_ctx.op_buf_ion_info) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007665 DEBUG_PRINT_LOW("Free o/p ion context");
Arun Menon906de572013-06-18 17:01:40 -07007666 free(drv_ctx.op_buf_ion_info);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007667 drv_ctx.op_buf_ion_info = NULL;
7668 }
7669#endif
Arun Menonbdb80b02013-08-12 17:45:54 -07007670 if (out_dynamic_list) {
7671 free(out_dynamic_list);
7672 out_dynamic_list = NULL;
7673 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007674}
7675
7676void omx_vdec::free_input_buffer_header()
7677{
7678 input_use_buffer = false;
Arun Menon906de572013-06-18 17:01:40 -07007679 if (arbitrary_bytes) {
Arun Menon906de572013-06-18 17:01:40 -07007680 if (m_inp_heap_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007681 DEBUG_PRINT_LOW("Free input Heap Pointer");
Arun Menon906de572013-06-18 17:01:40 -07007682 free (m_inp_heap_ptr);
7683 m_inp_heap_ptr = NULL;
7684 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007685
Arun Menon906de572013-06-18 17:01:40 -07007686 if (m_phdr_pmem_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007687 DEBUG_PRINT_LOW("Free input pmem header Pointer");
Arun Menon906de572013-06-18 17:01:40 -07007688 free (m_phdr_pmem_ptr);
7689 m_phdr_pmem_ptr = NULL;
7690 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007691 }
Arun Menon906de572013-06-18 17:01:40 -07007692 if (m_inp_mem_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007693 DEBUG_PRINT_LOW("Free input pmem Pointer area");
Arun Menon906de572013-06-18 17:01:40 -07007694 free (m_inp_mem_ptr);
7695 m_inp_mem_ptr = NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007696 }
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07007697 /* We just freed all the buffer headers, every thing in m_input_free_q,
7698 * m_input_pending_q, pdest_frame, and psource_frame is now invalid */
Leena Winterrowd1d2424a2013-08-20 15:26:02 -07007699 while (m_input_free_q.m_size) {
7700 unsigned address, p2, id;
7701 m_input_free_q.pop_entry(&address, &p2, &id);
7702 }
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07007703 while (m_input_pending_q.m_size) {
7704 unsigned address, p2, id;
7705 m_input_pending_q.pop_entry(&address, &p2, &id);
7706 }
7707 pdest_frame = NULL;
7708 psource_frame = NULL;
Arun Menon906de572013-06-18 17:01:40 -07007709 if (drv_ctx.ptr_inputbuffer) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007710 DEBUG_PRINT_LOW("Free Driver Context pointer");
Arun Menon906de572013-06-18 17:01:40 -07007711 free (drv_ctx.ptr_inputbuffer);
7712 drv_ctx.ptr_inputbuffer = NULL;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007713 }
7714#ifdef USE_ION
7715 if (drv_ctx.ip_buf_ion_info) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007716 DEBUG_PRINT_LOW("Free ion context");
Arun Menon906de572013-06-18 17:01:40 -07007717 free(drv_ctx.ip_buf_ion_info);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007718 drv_ctx.ip_buf_ion_info = NULL;
7719 }
7720#endif
7721}
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007722
7723int omx_vdec::stream_off(OMX_U32 port)
Shalaj Jain273b3e02012-06-22 19:08:03 -07007724{
Arun Menon906de572013-06-18 17:01:40 -07007725 enum v4l2_buf_type btype;
7726 int rc = 0;
7727 enum v4l2_ports v4l2_port = OUTPUT_PORT;
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007728
Arun Menon906de572013-06-18 17:01:40 -07007729 if (port == OMX_CORE_INPUT_PORT_INDEX) {
7730 btype = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
7731 v4l2_port = OUTPUT_PORT;
7732 } else if (port == OMX_CORE_OUTPUT_PORT_INDEX) {
7733 btype = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
7734 v4l2_port = CAPTURE_PORT;
7735 } else if (port == OMX_ALL) {
7736 int rc_input = stream_off(OMX_CORE_INPUT_PORT_INDEX);
7737 int rc_output = stream_off(OMX_CORE_OUTPUT_PORT_INDEX);
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007738
Arun Menon906de572013-06-18 17:01:40 -07007739 if (!rc_input)
7740 return rc_input;
7741 else
7742 return rc_output;
7743 }
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007744
Arun Menon906de572013-06-18 17:01:40 -07007745 if (!streaming[v4l2_port]) {
7746 // already streamed off, warn and move on
7747 DEBUG_PRINT_HIGH("Warning: Attempting to stream off on %d port,"
7748 " which is already streamed off", v4l2_port);
7749 return 0;
7750 }
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007751
Arun Menon906de572013-06-18 17:01:40 -07007752 DEBUG_PRINT_HIGH("Streaming off %d port", v4l2_port);
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007753
Arun Menon906de572013-06-18 17:01:40 -07007754 rc = ioctl(drv_ctx.video_driver_fd, VIDIOC_STREAMOFF, &btype);
7755 if (rc) {
7756 /*TODO: How to handle this case */
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007757 DEBUG_PRINT_ERROR("Failed to call streamoff on %d Port", v4l2_port);
Arun Menon906de572013-06-18 17:01:40 -07007758 } else {
7759 streaming[v4l2_port] = false;
7760 }
Deva Ramasubramanianf97488b2012-10-26 18:37:05 -07007761
Arun Menon906de572013-06-18 17:01:40 -07007762 return rc;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007763}
7764
7765OMX_ERRORTYPE omx_vdec::get_buffer_req(vdec_allocatorproperty *buffer_prop)
7766{
Arun Menon906de572013-06-18 17:01:40 -07007767 OMX_ERRORTYPE eRet = OMX_ErrorNone;
7768 struct v4l2_requestbuffers bufreq;
7769 unsigned int buf_size = 0, extra_data_size = 0, client_extra_data_size = 0;
Pushkaraj Patil1ab10292014-02-11 20:10:42 +05307770 unsigned int final_extra_data_size = 0;
Arun Menon906de572013-06-18 17:01:40 -07007771 struct v4l2_format fmt;
7772 int ret = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007773 DEBUG_PRINT_LOW("GetBufReq IN: ActCnt(%d) Size(%d)",
Arun Menon906de572013-06-18 17:01:40 -07007774 buffer_prop->actualcount, buffer_prop->buffer_size);
7775 bufreq.memory = V4L2_MEMORY_USERPTR;
7776 bufreq.count = 1;
7777 if (buffer_prop->buffer_type == VDEC_BUFFER_TYPE_INPUT) {
7778 bufreq.type=V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
7779 fmt.type =V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
7780 fmt.fmt.pix_mp.pixelformat = output_capability;
7781 } else if (buffer_prop->buffer_type == VDEC_BUFFER_TYPE_OUTPUT) {
7782 bufreq.type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
7783 fmt.type =V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
7784 fmt.fmt.pix_mp.pixelformat = capture_capability;
7785 } else {
7786 eRet = OMX_ErrorBadParameter;
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07007787 }
Arun Menon906de572013-06-18 17:01:40 -07007788 if (eRet==OMX_ErrorNone) {
7789 ret = ioctl(drv_ctx.video_driver_fd,VIDIOC_REQBUFS, &bufreq);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007790 }
Arun Menon906de572013-06-18 17:01:40 -07007791 if (ret) {
7792 DEBUG_PRINT_ERROR("Requesting buffer requirements failed");
7793 /*TODO: How to handle this case */
7794 eRet = OMX_ErrorInsufficientResources;
7795 return eRet;
7796 } else {
7797 buffer_prop->actualcount = bufreq.count;
7798 buffer_prop->mincount = bufreq.count;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007799 DEBUG_PRINT_HIGH("Count = %d",bufreq.count);
Shalaj Jain273b3e02012-06-22 19:08:03 -07007800 }
Arun Menon906de572013-06-18 17:01:40 -07007801 DEBUG_PRINT_LOW("GetBufReq IN: ActCnt(%d) Size(%d)",
7802 buffer_prop->actualcount, buffer_prop->buffer_size);
7803
7804 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
7805 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
7806
7807 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_G_FMT, &fmt);
7808
7809 update_resolution(fmt.fmt.pix_mp.width,
7810 fmt.fmt.pix_mp.height,
7811 fmt.fmt.pix_mp.plane_fmt[0].bytesperline,
7812 fmt.fmt.pix_mp.plane_fmt[0].reserved[0]);
7813 if (fmt.type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE)
7814 drv_ctx.num_planes = fmt.fmt.pix_mp.num_planes;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007815 DEBUG_PRINT_HIGH("Buffer Size = %d",fmt.fmt.pix_mp.plane_fmt[0].sizeimage);
Arun Menon906de572013-06-18 17:01:40 -07007816
7817 if (ret) {
7818 /*TODO: How to handle this case */
7819 DEBUG_PRINT_ERROR("Requesting buffer requirements failed");
7820 eRet = OMX_ErrorInsufficientResources;
7821 } else {
7822 int extra_idx = 0;
7823
7824 eRet = is_video_session_supported();
7825 if (eRet)
7826 return eRet;
7827
7828 buffer_prop->buffer_size = fmt.fmt.pix_mp.plane_fmt[0].sizeimage;
7829 buf_size = buffer_prop->buffer_size;
7830 extra_idx = EXTRADATA_IDX(drv_ctx.num_planes);
7831 if (extra_idx && (extra_idx < VIDEO_MAX_PLANES)) {
7832 extra_data_size = fmt.fmt.pix_mp.plane_fmt[extra_idx].sizeimage;
7833 } else if (extra_idx >= VIDEO_MAX_PLANES) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007834 DEBUG_PRINT_ERROR("Extradata index is more than allowed: %d", extra_idx);
Arun Menon906de572013-06-18 17:01:40 -07007835 return OMX_ErrorBadParameter;
7836 }
7837 if (client_extradata & OMX_FRAMEINFO_EXTRADATA) {
7838 DEBUG_PRINT_HIGH("Frame info extra data enabled!");
7839 client_extra_data_size += OMX_FRAMEINFO_EXTRADATA_SIZE;
7840 }
7841 if (client_extradata & OMX_INTERLACE_EXTRADATA) {
7842 client_extra_data_size += OMX_INTERLACE_EXTRADATA_SIZE;
7843 }
7844 if (client_extradata & OMX_PORTDEF_EXTRADATA) {
7845 client_extra_data_size += OMX_PORTDEF_EXTRADATA_SIZE;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007846 DEBUG_PRINT_HIGH("Smooth streaming enabled extra_data_size=%d",
Arun Menon906de572013-06-18 17:01:40 -07007847 client_extra_data_size);
7848 }
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05307849 if (client_extradata & OMX_FRAMEPACK_EXTRADATA) {
7850 client_extra_data_size += OMX_FRAMEPACK_EXTRADATA_SIZE;
7851 DEBUG_PRINT_HIGH("framepack extradata enabled");
7852 }
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08007853 if (client_extradata & OMX_QP_EXTRADATA) {
7854 client_extra_data_size += OMX_QP_EXTRADATA_SIZE;
7855 DEBUG_PRINT_HIGH("QP extradata enabled");
7856 }
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08007857 if (client_extradata & OMX_BITSINFO_EXTRADATA) {
7858 client_extra_data_size += OMX_BITSINFO_EXTRADATA_SIZE;
7859 DEBUG_PRINT_HIGH("Input bits info extradata enabled");
7860 }
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08007861
Arun Menon906de572013-06-18 17:01:40 -07007862 if (client_extra_data_size) {
7863 client_extra_data_size += sizeof(OMX_OTHER_EXTRADATATYPE); //Space for terminator
7864 buf_size = ((buf_size + 3)&(~3)); //Align extradata start address to 64Bit
7865 }
Pushkaraj Patil1ab10292014-02-11 20:10:42 +05307866 final_extra_data_size = (extra_data_size > client_extra_data_size ?
7867 extra_data_size : client_extra_data_size);
7868 drv_ctx.extradata_info.size = buffer_prop->actualcount * final_extra_data_size;
Arun Menon906de572013-06-18 17:01:40 -07007869 drv_ctx.extradata_info.count = buffer_prop->actualcount;
Pushkaraj Patil1ab10292014-02-11 20:10:42 +05307870 drv_ctx.extradata_info.buffer_size = final_extra_data_size;
Arun Menon906de572013-06-18 17:01:40 -07007871 buf_size += client_extra_data_size;
7872 buf_size = (buf_size + buffer_prop->alignment - 1)&(~(buffer_prop->alignment - 1));
7873 DEBUG_PRINT_LOW("GetBufReq UPDATE: ActCnt(%d) Size(%d) BufSize(%d)",
7874 buffer_prop->actualcount, buffer_prop->buffer_size, buf_size);
7875 if (in_reconfig) // BufReq will be set to driver when port is disabled
7876 buffer_prop->buffer_size = buf_size;
7877 else if (buf_size != buffer_prop->buffer_size) {
7878 buffer_prop->buffer_size = buf_size;
7879 eRet = set_buffer_req(buffer_prop);
7880 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007881 }
Arun Menon906de572013-06-18 17:01:40 -07007882 DEBUG_PRINT_LOW("GetBufReq OUT: ActCnt(%d) Size(%d)",
7883 buffer_prop->actualcount, buffer_prop->buffer_size);
7884 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007885}
7886
7887OMX_ERRORTYPE omx_vdec::set_buffer_req(vdec_allocatorproperty *buffer_prop)
7888{
Arun Menon906de572013-06-18 17:01:40 -07007889 OMX_ERRORTYPE eRet = OMX_ErrorNone;
7890 unsigned buf_size = 0;
7891 struct v4l2_format fmt;
7892 struct v4l2_requestbuffers bufreq;
7893 int ret;
7894 DEBUG_PRINT_LOW("SetBufReq IN: ActCnt(%d) Size(%d)",
7895 buffer_prop->actualcount, buffer_prop->buffer_size);
7896 buf_size = (buffer_prop->buffer_size + buffer_prop->alignment - 1)&(~(buffer_prop->alignment - 1));
7897 if (buf_size != buffer_prop->buffer_size) {
7898 DEBUG_PRINT_ERROR("Buffer size alignment error: Requested(%d) Required(%d)",
7899 buffer_prop->buffer_size, buf_size);
7900 eRet = OMX_ErrorBadParameter;
7901 } else {
7902 fmt.fmt.pix_mp.height = drv_ctx.video_resolution.frame_height;
7903 fmt.fmt.pix_mp.width = drv_ctx.video_resolution.frame_width;
Deva Ramasubramanian614f79e2012-08-10 21:42:10 -07007904
Arun Menon906de572013-06-18 17:01:40 -07007905 if (buffer_prop->buffer_type == VDEC_BUFFER_TYPE_INPUT) {
7906 fmt.type =V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
7907 fmt.fmt.pix_mp.pixelformat = output_capability;
Shalaj Jaind3902bb2013-10-07 12:42:55 -07007908 fmt.fmt.pix_mp.plane_fmt[0].sizeimage = buf_size;
Arun Menon906de572013-06-18 17:01:40 -07007909 } else if (buffer_prop->buffer_type == VDEC_BUFFER_TYPE_OUTPUT) {
7910 fmt.type =V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
7911 fmt.fmt.pix_mp.pixelformat = capture_capability;
7912 } else {
7913 eRet = OMX_ErrorBadParameter;
7914 }
Deva Ramasubramanian614f79e2012-08-10 21:42:10 -07007915
Arun Menon906de572013-06-18 17:01:40 -07007916 ret = ioctl(drv_ctx.video_driver_fd, VIDIOC_S_FMT, &fmt);
7917 if (ret) {
7918 /*TODO: How to handle this case */
7919 DEBUG_PRINT_ERROR("Setting buffer requirements (format) failed %d", ret);
7920 eRet = OMX_ErrorInsufficientResources;
7921 }
7922
7923 bufreq.memory = V4L2_MEMORY_USERPTR;
7924 bufreq.count = buffer_prop->actualcount;
7925 if (buffer_prop->buffer_type == VDEC_BUFFER_TYPE_INPUT) {
7926 bufreq.type=V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
7927 } else if (buffer_prop->buffer_type == VDEC_BUFFER_TYPE_OUTPUT) {
7928 bufreq.type=V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
7929 } else {
7930 eRet = OMX_ErrorBadParameter;
7931 }
7932
7933 if (eRet==OMX_ErrorNone) {
7934 ret = ioctl(drv_ctx.video_driver_fd,VIDIOC_REQBUFS, &bufreq);
7935 }
7936
7937 if (ret) {
7938 DEBUG_PRINT_ERROR("Setting buffer requirements (reqbufs) failed %d", ret);
7939 /*TODO: How to handle this case */
7940 eRet = OMX_ErrorInsufficientResources;
7941 } else if (bufreq.count < buffer_prop->actualcount) {
7942 DEBUG_PRINT_ERROR("Driver refused to change the number of buffers"
7943 " on v4l2 port %d to %d (prefers %d)", bufreq.type,
7944 buffer_prop->actualcount, bufreq.count);
7945 eRet = OMX_ErrorInsufficientResources;
7946 } else {
7947 if (!client_buffers.update_buffer_req()) {
7948 DEBUG_PRINT_ERROR("Setting c2D buffer requirements failed");
7949 eRet = OMX_ErrorInsufficientResources;
7950 }
7951 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07007952 }
Arun Menon906de572013-06-18 17:01:40 -07007953 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007954}
7955
Shalaj Jain273b3e02012-06-22 19:08:03 -07007956OMX_ERRORTYPE omx_vdec::update_picture_resolution()
7957{
Arun Menon906de572013-06-18 17:01:40 -07007958 OMX_ERRORTYPE eRet = OMX_ErrorNone;
7959 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07007960}
7961
7962OMX_ERRORTYPE omx_vdec::update_portdef(OMX_PARAM_PORTDEFINITIONTYPE *portDefn)
7963{
Arun Menon906de572013-06-18 17:01:40 -07007964 OMX_ERRORTYPE eRet = OMX_ErrorNone;
7965 if (!portDefn) {
7966 return OMX_ErrorBadParameter;
Vinay Kaliada4f4422013-01-09 10:45:03 -08007967 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007968 DEBUG_PRINT_LOW("omx_vdec::update_portdef");
Arun Menon906de572013-06-18 17:01:40 -07007969 portDefn->nVersion.nVersion = OMX_SPEC_VERSION;
7970 portDefn->nSize = sizeof(portDefn);
7971 portDefn->eDomain = OMX_PortDomainVideo;
7972 if (drv_ctx.frame_rate.fps_denominator > 0)
Deva Ramasubramanian9ba5d832014-01-03 18:32:50 -08007973 portDefn->format.video.xFramerate = (drv_ctx.frame_rate.fps_numerator /
7974 drv_ctx.frame_rate.fps_denominator) << 16; //Q16 format
Arun Menon906de572013-06-18 17:01:40 -07007975 else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007976 DEBUG_PRINT_ERROR("Error: Divide by zero");
Arun Menon906de572013-06-18 17:01:40 -07007977 return OMX_ErrorBadParameter;
Vinay Kaliada4f4422013-01-09 10:45:03 -08007978 }
Arun Menon906de572013-06-18 17:01:40 -07007979 if (0 == portDefn->nPortIndex) {
7980 portDefn->eDir = OMX_DirInput;
7981 portDefn->nBufferCountActual = drv_ctx.ip_buf.actualcount;
7982 portDefn->nBufferCountMin = drv_ctx.ip_buf.mincount;
7983 portDefn->nBufferSize = drv_ctx.ip_buf.buffer_size;
7984 portDefn->format.video.eColorFormat = OMX_COLOR_FormatUnused;
7985 portDefn->format.video.eCompressionFormat = eCompressionFormat;
7986 portDefn->bEnabled = m_inp_bEnabled;
7987 portDefn->bPopulated = m_inp_bPopulated;
7988 } else if (1 == portDefn->nPortIndex) {
7989 unsigned int buf_size = 0;
7990 if (!client_buffers.update_buffer_req()) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007991 DEBUG_PRINT_ERROR("client_buffers.update_buffer_req Failed");
Arun Menon906de572013-06-18 17:01:40 -07007992 return OMX_ErrorHardware;
7993 }
7994 if (!client_buffers.get_buffer_req(buf_size)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07007995 DEBUG_PRINT_ERROR("update buffer requirements");
Arun Menon906de572013-06-18 17:01:40 -07007996 return OMX_ErrorHardware;
7997 }
7998 portDefn->nBufferSize = buf_size;
7999 portDefn->eDir = OMX_DirOutput;
8000 portDefn->nBufferCountActual = drv_ctx.op_buf.actualcount;
8001 portDefn->nBufferCountMin = drv_ctx.op_buf.mincount;
8002 portDefn->format.video.eCompressionFormat = OMX_VIDEO_CodingUnused;
8003 portDefn->bEnabled = m_out_bEnabled;
8004 portDefn->bPopulated = m_out_bPopulated;
8005 if (!client_buffers.get_color_format(portDefn->format.video.eColorFormat)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008006 DEBUG_PRINT_ERROR("Error in getting color format");
Arun Menon906de572013-06-18 17:01:40 -07008007 return OMX_ErrorHardware;
8008 }
8009 } else {
8010 portDefn->eDir = OMX_DirMax;
8011 DEBUG_PRINT_LOW(" get_parameter: Bad Port idx %d",
8012 (int)portDefn->nPortIndex);
8013 eRet = OMX_ErrorBadPortIndex;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008014 }
Arun Menon906de572013-06-18 17:01:40 -07008015 portDefn->format.video.nFrameHeight = drv_ctx.video_resolution.frame_height;
8016 portDefn->format.video.nFrameWidth = drv_ctx.video_resolution.frame_width;
8017 portDefn->format.video.nStride = drv_ctx.video_resolution.stride;
8018 portDefn->format.video.nSliceHeight = drv_ctx.video_resolution.scan_lines;
Praveen Chavandb7776f2014-02-06 18:17:25 -08008019 if ((portDefn->format.video.eColorFormat == OMX_COLOR_FormatYUV420Planar) ||
8020 (portDefn->format.video.eColorFormat == OMX_COLOR_FormatYUV420SemiPlanar)) {
Maheshwar Ajja507d6552014-01-03 14:54:29 +05308021 portDefn->format.video.nStride = drv_ctx.video_resolution.frame_width;
8022 portDefn->format.video.nSliceHeight = drv_ctx.video_resolution.frame_height;
8023 }
8024 DEBUG_PRINT_HIGH("update_portdef(%lu): Width = %lu Height = %lu Stride = %ld "
8025 "SliceHeight = %lu eColorFormat = %lu nBufSize %lu nBufCnt %lu",
8026 portDefn->nPortIndex,
8027 portDefn->format.video.nFrameWidth,
Arun Menon906de572013-06-18 17:01:40 -07008028 portDefn->format.video.nFrameHeight,
8029 portDefn->format.video.nStride,
Maheshwar Ajja507d6552014-01-03 14:54:29 +05308030 portDefn->format.video.nSliceHeight,
8031 portDefn->format.video.eColorFormat,
8032 portDefn->nBufferSize,
8033 portDefn->nBufferCountActual);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008034
Maheshwar Ajja507d6552014-01-03 14:54:29 +05308035 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008036}
8037
8038OMX_ERRORTYPE omx_vdec::allocate_output_headers()
8039{
Arun Menon906de572013-06-18 17:01:40 -07008040 OMX_ERRORTYPE eRet = OMX_ErrorNone;
8041 OMX_BUFFERHEADERTYPE *bufHdr = NULL;
8042 unsigned i= 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008043
Arun Menon906de572013-06-18 17:01:40 -07008044 if (!m_out_mem_ptr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008045 DEBUG_PRINT_HIGH("Use o/p buffer case - Header List allocation");
Arun Menon906de572013-06-18 17:01:40 -07008046 int nBufHdrSize = 0;
8047 int nPlatformEntrySize = 0;
8048 int nPlatformListSize = 0;
8049 int nPMEMInfoSize = 0;
8050 OMX_QCOM_PLATFORM_PRIVATE_LIST *pPlatformList;
8051 OMX_QCOM_PLATFORM_PRIVATE_ENTRY *pPlatformEntry;
8052 OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *pPMEMInfo;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008053
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008054 DEBUG_PRINT_LOW("Setting First Output Buffer(%d)",
Arun Menon906de572013-06-18 17:01:40 -07008055 drv_ctx.op_buf.actualcount);
8056 nBufHdrSize = drv_ctx.op_buf.actualcount *
8057 sizeof(OMX_BUFFERHEADERTYPE);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008058
Arun Menon906de572013-06-18 17:01:40 -07008059 nPMEMInfoSize = drv_ctx.op_buf.actualcount *
8060 sizeof(OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO);
8061 nPlatformListSize = drv_ctx.op_buf.actualcount *
8062 sizeof(OMX_QCOM_PLATFORM_PRIVATE_LIST);
8063 nPlatformEntrySize = drv_ctx.op_buf.actualcount *
8064 sizeof(OMX_QCOM_PLATFORM_PRIVATE_ENTRY);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008065
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008066 DEBUG_PRINT_LOW("TotalBufHdr %d BufHdrSize %d PMEM %d PL %d",nBufHdrSize,
Arun Menon906de572013-06-18 17:01:40 -07008067 sizeof(OMX_BUFFERHEADERTYPE),
8068 nPMEMInfoSize,
8069 nPlatformListSize);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008070 DEBUG_PRINT_LOW("PE %d bmSize %d",nPlatformEntrySize,
Arun Menon906de572013-06-18 17:01:40 -07008071 m_out_bm_count);
8072 m_out_mem_ptr = (OMX_BUFFERHEADERTYPE *)calloc(nBufHdrSize,1);
8073 // Alloc mem for platform specific info
8074 char *pPtr=NULL;
8075 pPtr = (char*) calloc(nPlatformListSize + nPlatformEntrySize +
8076 nPMEMInfoSize,1);
8077 drv_ctx.ptr_outputbuffer = (struct vdec_bufferpayload *) \
8078 calloc (sizeof(struct vdec_bufferpayload),
8079 drv_ctx.op_buf.actualcount);
8080 drv_ctx.ptr_respbuffer = (struct vdec_output_frameinfo *)\
8081 calloc (sizeof (struct vdec_output_frameinfo),
8082 drv_ctx.op_buf.actualcount);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008083#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07008084 drv_ctx.op_buf_ion_info = (struct vdec_ion * ) \
8085 calloc (sizeof(struct vdec_ion),drv_ctx.op_buf.actualcount);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008086#endif
Arun Menonbdb80b02013-08-12 17:45:54 -07008087 if (dynamic_buf_mode) {
8088 out_dynamic_list = (struct dynamic_buf_list *) \
8089 calloc (sizeof(struct dynamic_buf_list), drv_ctx.op_buf.actualcount);
8090 }
Arun Menon906de572013-06-18 17:01:40 -07008091 if (m_out_mem_ptr && pPtr && drv_ctx.ptr_outputbuffer
8092 && drv_ctx.ptr_respbuffer) {
8093 bufHdr = m_out_mem_ptr;
8094 m_platform_list = (OMX_QCOM_PLATFORM_PRIVATE_LIST *)(pPtr);
8095 m_platform_entry= (OMX_QCOM_PLATFORM_PRIVATE_ENTRY *)
8096 (((char *) m_platform_list) + nPlatformListSize);
8097 m_pmem_info = (OMX_QCOM_PLATFORM_PRIVATE_PMEM_INFO *)
8098 (((char *) m_platform_entry) + nPlatformEntrySize);
8099 pPlatformList = m_platform_list;
8100 pPlatformEntry = m_platform_entry;
8101 pPMEMInfo = m_pmem_info;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008102
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008103 DEBUG_PRINT_LOW("Memory Allocation Succeeded for OUT port%p",m_out_mem_ptr);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008104
Arun Menon906de572013-06-18 17:01:40 -07008105 // Settting the entire storage nicely
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008106 DEBUG_PRINT_LOW("bHdr %p OutMem %p PE %p",bufHdr,
Arun Menon906de572013-06-18 17:01:40 -07008107 m_out_mem_ptr,pPlatformEntry);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008108 DEBUG_PRINT_LOW(" Pmem Info = %p",pPMEMInfo);
Arun Menon906de572013-06-18 17:01:40 -07008109 for (i=0; i < drv_ctx.op_buf.actualcount ; i++) {
8110 bufHdr->nSize = sizeof(OMX_BUFFERHEADERTYPE);
8111 bufHdr->nVersion.nVersion = OMX_SPEC_VERSION;
8112 // Set the values when we determine the right HxW param
8113 bufHdr->nAllocLen = 0;
8114 bufHdr->nFilledLen = 0;
8115 bufHdr->pAppPrivate = NULL;
8116 bufHdr->nOutputPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8117 pPlatformEntry->type = OMX_QCOM_PLATFORM_PRIVATE_PMEM;
8118 pPlatformEntry->entry = pPMEMInfo;
8119 // Initialize the Platform List
8120 pPlatformList->nEntries = 1;
8121 pPlatformList->entryList = pPlatformEntry;
8122 // Keep pBuffer NULL till vdec is opened
8123 bufHdr->pBuffer = NULL;
8124 pPMEMInfo->offset = 0;
8125 pPMEMInfo->pmem_fd = 0;
8126 bufHdr->pPlatformPrivate = pPlatformList;
8127 drv_ctx.ptr_outputbuffer[i].pmem_fd = -1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008128#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07008129 drv_ctx.op_buf_ion_info[i].ion_device_fd =-1;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008130#endif
Arun Menon906de572013-06-18 17:01:40 -07008131 /*Create a mapping between buffers*/
8132 bufHdr->pOutputPortPrivate = &drv_ctx.ptr_respbuffer[i];
8133 drv_ctx.ptr_respbuffer[i].client_data = (void *) \
8134 &drv_ctx.ptr_outputbuffer[i];
8135 // Move the buffer and buffer header pointers
8136 bufHdr++;
8137 pPMEMInfo++;
8138 pPlatformEntry++;
8139 pPlatformList++;
8140 }
8141 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008142 DEBUG_PRINT_ERROR("Output buf mem alloc failed[0x%p][0x%p]",\
Arun Menon906de572013-06-18 17:01:40 -07008143 m_out_mem_ptr, pPtr);
8144 if (m_out_mem_ptr) {
8145 free(m_out_mem_ptr);
8146 m_out_mem_ptr = NULL;
8147 }
8148 if (pPtr) {
8149 free(pPtr);
8150 pPtr = NULL;
8151 }
8152 if (drv_ctx.ptr_outputbuffer) {
8153 free(drv_ctx.ptr_outputbuffer);
8154 drv_ctx.ptr_outputbuffer = NULL;
8155 }
8156 if (drv_ctx.ptr_respbuffer) {
8157 free(drv_ctx.ptr_respbuffer);
8158 drv_ctx.ptr_respbuffer = NULL;
8159 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008160#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07008161 if (drv_ctx.op_buf_ion_info) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008162 DEBUG_PRINT_LOW("Free o/p ion context");
Arun Menon906de572013-06-18 17:01:40 -07008163 free(drv_ctx.op_buf_ion_info);
8164 drv_ctx.op_buf_ion_info = NULL;
8165 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008166#endif
Arun Menon906de572013-06-18 17:01:40 -07008167 eRet = OMX_ErrorInsufficientResources;
8168 }
8169 } else {
8170 eRet = OMX_ErrorInsufficientResources;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008171 }
Arun Menon906de572013-06-18 17:01:40 -07008172 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008173}
8174
8175void omx_vdec::complete_pending_buffer_done_cbs()
8176{
Arun Menon906de572013-06-18 17:01:40 -07008177 unsigned p1;
8178 unsigned p2;
8179 unsigned ident;
8180 omx_cmd_queue tmp_q, pending_bd_q;
8181 pthread_mutex_lock(&m_lock);
8182 // pop all pending GENERATE FDB from ftb queue
8183 while (m_ftb_q.m_size) {
8184 m_ftb_q.pop_entry(&p1,&p2,&ident);
8185 if (ident == OMX_COMPONENT_GENERATE_FBD) {
8186 pending_bd_q.insert_entry(p1,p2,ident);
8187 } else {
8188 tmp_q.insert_entry(p1,p2,ident);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008189 }
Arun Menon906de572013-06-18 17:01:40 -07008190 }
8191 //return all non GENERATE FDB to ftb queue
8192 while (tmp_q.m_size) {
8193 tmp_q.pop_entry(&p1,&p2,&ident);
8194 m_ftb_q.insert_entry(p1,p2,ident);
8195 }
8196 // pop all pending GENERATE EDB from etb queue
8197 while (m_etb_q.m_size) {
8198 m_etb_q.pop_entry(&p1,&p2,&ident);
8199 if (ident == OMX_COMPONENT_GENERATE_EBD) {
8200 pending_bd_q.insert_entry(p1,p2,ident);
8201 } else {
8202 tmp_q.insert_entry(p1,p2,ident);
8203 }
8204 }
8205 //return all non GENERATE FDB to etb queue
8206 while (tmp_q.m_size) {
8207 tmp_q.pop_entry(&p1,&p2,&ident);
8208 m_etb_q.insert_entry(p1,p2,ident);
8209 }
8210 pthread_mutex_unlock(&m_lock);
8211 // process all pending buffer dones
8212 while (pending_bd_q.m_size) {
8213 pending_bd_q.pop_entry(&p1,&p2,&ident);
8214 switch (ident) {
8215 case OMX_COMPONENT_GENERATE_EBD:
8216 if (empty_buffer_done(&m_cmp, (OMX_BUFFERHEADERTYPE *)p1) != OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008217 DEBUG_PRINT_ERROR("ERROR: empty_buffer_done() failed!");
Arun Menon906de572013-06-18 17:01:40 -07008218 omx_report_error ();
8219 }
8220 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008221
Arun Menon906de572013-06-18 17:01:40 -07008222 case OMX_COMPONENT_GENERATE_FBD:
8223 if (fill_buffer_done(&m_cmp, (OMX_BUFFERHEADERTYPE *)p1) != OMX_ErrorNone ) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008224 DEBUG_PRINT_ERROR("ERROR: fill_buffer_done() failed!");
Arun Menon906de572013-06-18 17:01:40 -07008225 omx_report_error ();
8226 }
8227 break;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008228 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008229 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008230}
8231
8232void omx_vdec::set_frame_rate(OMX_S64 act_timestamp)
8233{
Arun Menon906de572013-06-18 17:01:40 -07008234 OMX_U32 new_frame_interval = 0;
8235 if (VALID_TS(act_timestamp) && VALID_TS(prev_ts) && act_timestamp != prev_ts
8236 && llabs(act_timestamp - prev_ts) > 2000) {
8237 new_frame_interval = client_set_fps ? frm_int :
8238 llabs(act_timestamp - prev_ts);
8239 if (new_frame_interval < frm_int || frm_int == 0) {
8240 frm_int = new_frame_interval;
8241 if (frm_int) {
8242 drv_ctx.frame_rate.fps_numerator = 1e6;
8243 drv_ctx.frame_rate.fps_denominator = frm_int;
8244 DEBUG_PRINT_LOW("set_frame_rate: frm_int(%lu) fps(%f)",
8245 frm_int, drv_ctx.frame_rate.fps_numerator /
8246 (float)drv_ctx.frame_rate.fps_denominator);
Deva Ramasubramaniane47e05b2013-04-24 15:23:29 -07008247
Arun Menon906de572013-06-18 17:01:40 -07008248 /* We need to report the difference between this FBD and the previous FBD
8249 * back to the driver for clock scaling purposes. */
8250 struct v4l2_outputparm oparm;
8251 /*XXX: we're providing timing info as seconds per frame rather than frames
8252 * per second.*/
8253 oparm.timeperframe.numerator = drv_ctx.frame_rate.fps_denominator;
8254 oparm.timeperframe.denominator = drv_ctx.frame_rate.fps_numerator;
Deva Ramasubramaniane47e05b2013-04-24 15:23:29 -07008255
Arun Menon906de572013-06-18 17:01:40 -07008256 struct v4l2_streamparm sparm;
8257 sparm.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
8258 sparm.parm.output = oparm;
8259 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_PARM, &sparm)) {
8260 DEBUG_PRINT_ERROR("Unable to convey fps info to driver, \
8261 performance might be affected");
8262 }
8263
8264 }
Deva Ramasubramaniane47e05b2013-04-24 15:23:29 -07008265 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008266 }
Arun Menon906de572013-06-18 17:01:40 -07008267 prev_ts = act_timestamp;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008268}
8269
8270void omx_vdec::adjust_timestamp(OMX_S64 &act_timestamp)
8271{
Arun Menon906de572013-06-18 17:01:40 -07008272 if (rst_prev_ts && VALID_TS(act_timestamp)) {
8273 prev_ts = act_timestamp;
8274 rst_prev_ts = false;
8275 } else if (VALID_TS(prev_ts)) {
8276 bool codec_cond = (drv_ctx.timestamp_adjust)?
8277 (!VALID_TS(act_timestamp) || (((act_timestamp > prev_ts)?
8278 (act_timestamp - prev_ts):(prev_ts - act_timestamp)) <= 2000)):
8279 (!VALID_TS(act_timestamp) || act_timestamp == prev_ts);
8280 if (frm_int > 0 && codec_cond) {
8281 DEBUG_PRINT_LOW("adjust_timestamp: original ts[%lld]", act_timestamp);
8282 act_timestamp = prev_ts + frm_int;
8283 DEBUG_PRINT_LOW("adjust_timestamp: predicted ts[%lld]", act_timestamp);
8284 prev_ts = act_timestamp;
8285 } else
8286 set_frame_rate(act_timestamp);
8287 } else if (frm_int > 0) // In this case the frame rate was set along
8288 { // with the port definition, start ts with 0
8289 act_timestamp = prev_ts = 0; // and correct if a valid ts is received.
8290 rst_prev_ts = true;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008291 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008292}
8293
8294void omx_vdec::handle_extradata(OMX_BUFFERHEADERTYPE *p_buf_hdr)
8295{
Arun Menon906de572013-06-18 17:01:40 -07008296 OMX_OTHER_EXTRADATATYPE *p_extra = NULL, *p_sei = NULL, *p_vui = NULL;
8297 OMX_U32 num_conceal_MB = 0;
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308298 OMX_TICKS time_stamp = 0;
Arun Menon906de572013-06-18 17:01:40 -07008299 OMX_U32 frame_rate = 0;
8300 int consumed_len = 0;
8301 OMX_U32 num_MB_in_frame;
8302 OMX_U32 recovery_sei_flags = 1;
8303 int enable = 0;
Arun Menon7b6fd642014-02-13 16:48:36 -08008304
Arun Menon906de572013-06-18 17:01:40 -07008305 int buf_index = p_buf_hdr - m_out_mem_ptr;
Praveen Chavan61e5d162013-11-01 02:49:19 -07008306 if (buf_index >= drv_ctx.extradata_info.count) {
8307 DEBUG_PRINT_ERROR("handle_extradata: invalid index(%d) max(%d)",
8308 buf_index, drv_ctx.extradata_info.count);
8309 return;
8310 }
Arun Menon906de572013-06-18 17:01:40 -07008311 struct msm_vidc_panscan_window_payload *panscan_payload = NULL;
8312 OMX_U8 *pBuffer = (OMX_U8 *)(drv_ctx.ptr_outputbuffer[buf_index].bufferaddr) +
8313 p_buf_hdr->nOffset;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308314
Arun Menon906de572013-06-18 17:01:40 -07008315 if (!drv_ctx.extradata_info.uaddr) {
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308316 DEBUG_PRINT_HIGH("NULL drv_ctx.extradata_info.uaddr");
Arun Menon906de572013-06-18 17:01:40 -07008317 return;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008318 }
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05308319 if (!secure_mode)
8320 p_extra = (OMX_OTHER_EXTRADATATYPE *)
Arun Menon906de572013-06-18 17:01:40 -07008321 ((unsigned)(pBuffer + p_buf_hdr->nOffset + p_buf_hdr->nFilledLen + 3)&(~3));
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05308322 else
8323 p_extra = m_other_extradata;
8324
Arun Menon906de572013-06-18 17:01:40 -07008325 char *p_extradata = drv_ctx.extradata_info.uaddr + buf_index * drv_ctx.extradata_info.buffer_size;
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05308326
8327 if (!secure_mode && ((OMX_U8*)p_extra > (pBuffer + p_buf_hdr->nAllocLen))) {
Arun Menon906de572013-06-18 17:01:40 -07008328 p_extra = NULL;
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05308329 return;
8330 }
Arun Menon906de572013-06-18 17:01:40 -07008331 OMX_OTHER_EXTRADATATYPE *data = (struct OMX_OTHER_EXTRADATATYPE *)p_extradata;
8332 if (data) {
8333 while ((consumed_len < drv_ctx.extradata_info.buffer_size)
8334 && (data->eType != (OMX_EXTRADATATYPE)EXTRADATA_NONE)) {
Surajit Podderd2644d52013-08-28 17:59:06 +05308335 if ((consumed_len + data->nSize) > (unsigned)drv_ctx.extradata_info.buffer_size) {
Arun Menon906de572013-06-18 17:01:40 -07008336 DEBUG_PRINT_LOW("Invalid extra data size");
8337 break;
8338 }
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308339 DEBUG_PRINT_LOW("handle_extradata: eType = %d", data->eType);
Arun Menon906de572013-06-18 17:01:40 -07008340 switch ((unsigned long)data->eType) {
8341 case EXTRADATA_INTERLACE_VIDEO:
8342 struct msm_vidc_interlace_payload *payload;
8343 payload = (struct msm_vidc_interlace_payload *)data->data;
Arun Menon7b6fd642014-02-13 16:48:36 -08008344 if (payload) {
Praneeth Paladugudd29c282013-09-12 15:41:47 -07008345 enable = 1;
Arun Menon7b6fd642014-02-13 16:48:36 -08008346 switch (payload->format) {
8347 case INTERLACE_FRAME_PROGRESSIVE:
8348 drv_ctx.interlace = VDEC_InterlaceFrameProgressive;
8349 enable = 0;
8350 break;
8351 case INTERLACE_INTERLEAVE_FRAME_TOPFIELDFIRST:
8352 drv_ctx.interlace = VDEC_InterlaceInterleaveFrameTopFieldFirst;
8353 break;
8354 case INTERLACE_INTERLEAVE_FRAME_BOTTOMFIELDFIRST:
8355 drv_ctx.interlace = VDEC_InterlaceInterleaveFrameBottomFieldFirst;
8356 break;
8357 default:
8358 DEBUG_PRINT_LOW("default case - set interlace to topfield");
8359 drv_ctx.interlace = VDEC_InterlaceInterleaveFrameTopFieldFirst;
8360 }
Arun Menon906de572013-06-18 17:01:40 -07008361 }
8362 if (m_enable_android_native_buffers)
8363 setMetaData((private_handle_t *)native_buffer[buf_index].privatehandle,
8364 PP_PARAM_INTERLACED, (void*)&enable);
Pushkaraj Patil0ddb2e02013-11-12 11:53:58 +05308365 if (client_extradata & OMX_INTERLACE_EXTRADATA) {
Arun Menon7b6fd642014-02-13 16:48:36 -08008366 append_interlace_extradata(p_extra, payload->format,
8367 p_buf_hdr->nFlags & QOMX_VIDEO_BUFFERFLAG_MBAFF);
Arun Menon906de572013-06-18 17:01:40 -07008368 p_extra = (OMX_OTHER_EXTRADATATYPE *) (((OMX_U8 *) p_extra) + p_extra->nSize);
8369 }
8370 break;
8371 case EXTRADATA_FRAME_RATE:
8372 struct msm_vidc_framerate_payload *frame_rate_payload;
8373 frame_rate_payload = (struct msm_vidc_framerate_payload *)data->data;
8374 frame_rate = frame_rate_payload->frame_rate;
8375 break;
8376 case EXTRADATA_TIMESTAMP:
8377 struct msm_vidc_ts_payload *time_stamp_payload;
8378 time_stamp_payload = (struct msm_vidc_ts_payload *)data->data;
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308379 time_stamp = time_stamp_payload->timestamp_lo;
8380 time_stamp |= ((unsigned long long)time_stamp_payload->timestamp_hi << 32);
8381 p_buf_hdr->nTimeStamp = time_stamp;
Arun Menon906de572013-06-18 17:01:40 -07008382 break;
8383 case EXTRADATA_NUM_CONCEALED_MB:
8384 struct msm_vidc_concealmb_payload *conceal_mb_payload;
8385 conceal_mb_payload = (struct msm_vidc_concealmb_payload *)data->data;
8386 num_MB_in_frame = ((drv_ctx.video_resolution.frame_width + 15) *
8387 (drv_ctx.video_resolution.frame_height + 15)) >> 8;
8388 num_conceal_MB = ((num_MB_in_frame > 0)?(conceal_mb_payload->num_mbs * 100 / num_MB_in_frame) : 0);
8389 break;
8390 case EXTRADATA_INDEX:
8391 int *etype;
8392 etype = (int *)(data->data);
8393 if (etype && *etype == EXTRADATA_ASPECT_RATIO) {
8394 struct msm_vidc_aspect_ratio_payload *aspect_ratio_payload;
8395 aspect_ratio_payload = (struct msm_vidc_aspect_ratio_payload *)(++etype);
8396 if (aspect_ratio_payload) {
8397 ((struct vdec_output_frameinfo *)
8398 p_buf_hdr->pOutputPortPrivate)->aspect_ratio_info.par_width = aspect_ratio_payload->aspect_width;
8399 ((struct vdec_output_frameinfo *)
8400 p_buf_hdr->pOutputPortPrivate)->aspect_ratio_info.par_height = aspect_ratio_payload->aspect_height;
8401 }
8402 }
8403 break;
8404 case EXTRADATA_RECOVERY_POINT_SEI:
8405 struct msm_vidc_recoverysei_payload *recovery_sei_payload;
8406 recovery_sei_payload = (struct msm_vidc_recoverysei_payload *)data->data;
8407 recovery_sei_flags = recovery_sei_payload->flags;
8408 if (recovery_sei_flags != FRAME_RECONSTRUCTION_CORRECT) {
8409 p_buf_hdr->nFlags |= OMX_BUFFERFLAG_DATACORRUPT;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008410 DEBUG_PRINT_HIGH("");
8411 DEBUG_PRINT_HIGH("***************************************************");
8412 DEBUG_PRINT_HIGH("FillBufferDone: OMX_BUFFERFLAG_DATACORRUPT Received");
8413 DEBUG_PRINT_HIGH("***************************************************");
Arun Menon906de572013-06-18 17:01:40 -07008414 }
8415 break;
8416 case EXTRADATA_PANSCAN_WINDOW:
8417 panscan_payload = (struct msm_vidc_panscan_window_payload *)data->data;
8418 break;
8419 case EXTRADATA_MPEG2_SEQDISP:
8420 struct msm_vidc_mpeg2_seqdisp_payload *seqdisp_payload;
8421 seqdisp_payload = (struct msm_vidc_mpeg2_seqdisp_payload *)data->data;
8422 if (seqdisp_payload) {
8423 m_disp_hor_size = seqdisp_payload->disp_width;
8424 m_disp_vert_size = seqdisp_payload->disp_height;
8425 }
8426 break;
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308427 case EXTRADATA_S3D_FRAME_PACKING:
8428 struct msm_vidc_s3d_frame_packing_payload *s3d_frame_packing_payload;
8429 s3d_frame_packing_payload = (struct msm_vidc_s3d_frame_packing_payload *)data->data;
Srinu Gorle2eb94e42014-02-14 13:37:40 +05308430 if (client_extradata & OMX_FRAMEPACK_EXTRADATA) {
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308431 append_framepack_extradata(p_extra, s3d_frame_packing_payload);
8432 p_extra = (OMX_OTHER_EXTRADATATYPE *) (((OMX_U8 *) p_extra) + p_extra->nSize);
8433 }
8434 break;
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08008435 case EXTRADATA_FRAME_QP:
8436 struct msm_vidc_frame_qp_payload *qp_payload;
8437 qp_payload = (struct msm_vidc_frame_qp_payload*)data->data;
Srinu Gorle2eb94e42014-02-14 13:37:40 +05308438 if (client_extradata & OMX_QP_EXTRADATA) {
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08008439 append_qp_extradata(p_extra, qp_payload);
8440 p_extra = (OMX_OTHER_EXTRADATATYPE *) (((OMX_U8 *) p_extra) + p_extra->nSize);
8441 }
8442 break;
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08008443 case EXTRADATA_FRAME_BITS_INFO:
8444 struct msm_vidc_frame_bits_info_payload *bits_info_payload;
8445 bits_info_payload = (struct msm_vidc_frame_bits_info_payload*)data->data;
Srinu Gorle2eb94e42014-02-14 13:37:40 +05308446 if (client_extradata & OMX_BITSINFO_EXTRADATA) {
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08008447 append_bitsinfo_extradata(p_extra, bits_info_payload);
8448 p_extra = (OMX_OTHER_EXTRADATATYPE *) (((OMX_U8 *) p_extra) + p_extra->nSize);
8449 }
8450 break;
Arun Menon906de572013-06-18 17:01:40 -07008451 default:
8452 goto unrecognized_extradata;
8453 }
8454 consumed_len += data->nSize;
8455 data = (OMX_OTHER_EXTRADATATYPE *)((char *)data + data->nSize);
8456 }
Srinu Gorle2eb94e42014-02-14 13:37:40 +05308457 if (client_extradata & OMX_FRAMEINFO_EXTRADATA) {
Arun Menon906de572013-06-18 17:01:40 -07008458 p_buf_hdr->nFlags |= OMX_BUFFERFLAG_EXTRADATA;
8459 append_frame_info_extradata(p_extra,
8460 num_conceal_MB, ((struct vdec_output_frameinfo *)p_buf_hdr->pOutputPortPrivate)->pic_type, frame_rate,
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308461 time_stamp, panscan_payload,&((struct vdec_output_frameinfo *)
Arun Menon906de572013-06-18 17:01:40 -07008462 p_buf_hdr->pOutputPortPrivate)->aspect_ratio_info);
Praneeth Paladugudd29c282013-09-12 15:41:47 -07008463 p_extra = (OMX_OTHER_EXTRADATATYPE *) (((OMX_U8 *) p_extra) + p_extra->nSize);
Arun Menon906de572013-06-18 17:01:40 -07008464 }
8465 }
Vinay Kalia0e75e9a2012-09-27 15:41:53 -07008466unrecognized_extradata:
Srinu Gorle2eb94e42014-02-14 13:37:40 +05308467 if (client_extradata)
Arun Menon906de572013-06-18 17:01:40 -07008468 append_terminator_extradata(p_extra);
Srinu Gorle2eb94e42014-02-14 13:37:40 +05308469 if (secure_mode) {
8470 struct vdec_output_frameinfo *ptr_extradatabuff = NULL;
8471 memcpy(p_extradata, m_other_extradata, drv_ctx.extradata_info.buffer_size);
8472 ptr_extradatabuff = (struct vdec_output_frameinfo *)p_buf_hdr->pOutputPortPrivate;
8473 ptr_extradatabuff->metadata_info.metabufaddr = (void *)p_extradata;
8474 ptr_extradatabuff->metadata_info.size = drv_ctx.extradata_info.buffer_size;
8475 }
Arun Menon906de572013-06-18 17:01:40 -07008476 return;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008477}
8478
Vinay Kalia9c00cae2012-12-06 16:08:20 -08008479OMX_ERRORTYPE omx_vdec::enable_extradata(OMX_U32 requested_extradata,
Arun Menon906de572013-06-18 17:01:40 -07008480 bool is_internal, bool enable)
Shalaj Jain273b3e02012-06-22 19:08:03 -07008481{
Arun Menon906de572013-06-18 17:01:40 -07008482 OMX_ERRORTYPE ret = OMX_ErrorNone;
8483 struct v4l2_control control;
8484 if (m_state != OMX_StateLoaded) {
8485 DEBUG_PRINT_ERROR("ERROR: enable extradata allowed in Loaded state only");
8486 return OMX_ErrorIncorrectStateOperation;
Vinay Kaliadb90f8c2012-11-19 18:57:56 -08008487 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008488 DEBUG_PRINT_HIGH("NOTE: enable_extradata: actual[%lu] requested[%lu] enable[%d], is_internal: %d",
Arun Menon906de572013-06-18 17:01:40 -07008489 client_extradata, requested_extradata, enable, is_internal);
8490
8491 if (!is_internal) {
8492 if (enable)
8493 client_extradata |= requested_extradata;
8494 else
8495 client_extradata = client_extradata & ~requested_extradata;
8496 }
8497
8498 if (enable) {
8499 if (requested_extradata & OMX_INTERLACE_EXTRADATA) {
8500 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8501 control.value = V4L2_MPEG_VIDC_EXTRADATA_INTERLACE_VIDEO;
8502 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
8503 DEBUG_PRINT_HIGH("Failed to set interlaced extradata."
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008504 " Quality of interlaced clips might be impacted.");
Arun Menon906de572013-06-18 17:01:40 -07008505 }
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308506 }
8507 if (requested_extradata & OMX_FRAMEINFO_EXTRADATA) {
Arun Menon906de572013-06-18 17:01:40 -07008508 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8509 control.value = V4L2_MPEG_VIDC_EXTRADATA_FRAME_RATE;
8510 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008511 DEBUG_PRINT_HIGH("Failed to set framerate extradata");
Arun Menon906de572013-06-18 17:01:40 -07008512 }
8513 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8514 control.value = V4L2_MPEG_VIDC_EXTRADATA_NUM_CONCEALED_MB;
8515 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008516 DEBUG_PRINT_HIGH("Failed to set concealed MB extradata");
Arun Menon906de572013-06-18 17:01:40 -07008517 }
8518 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8519 control.value = V4L2_MPEG_VIDC_EXTRADATA_RECOVERY_POINT_SEI;
8520 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008521 DEBUG_PRINT_HIGH("Failed to set recovery point SEI extradata");
Arun Menon906de572013-06-18 17:01:40 -07008522 }
8523 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8524 control.value = V4L2_MPEG_VIDC_EXTRADATA_PANSCAN_WINDOW;
8525 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008526 DEBUG_PRINT_HIGH("Failed to set panscan extradata");
Arun Menon906de572013-06-18 17:01:40 -07008527 }
8528 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8529 control.value = V4L2_MPEG_VIDC_INDEX_EXTRADATA_ASPECT_RATIO;
8530 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008531 DEBUG_PRINT_HIGH("Failed to set panscan extradata");
Arun Menon906de572013-06-18 17:01:40 -07008532 }
8533 if (output_capability == V4L2_PIX_FMT_MPEG2) {
8534 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8535 control.value = V4L2_MPEG_VIDC_EXTRADATA_MPEG2_SEQDISP;
8536 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008537 DEBUG_PRINT_HIGH("Failed to set panscan extradata");
Arun Menon906de572013-06-18 17:01:40 -07008538 }
8539 }
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308540 }
8541 if (requested_extradata & OMX_TIMEINFO_EXTRADATA) {
Arun Menon906de572013-06-18 17:01:40 -07008542 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8543 control.value = V4L2_MPEG_VIDC_EXTRADATA_TIMESTAMP;
8544 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008545 DEBUG_PRINT_HIGH("Failed to set timeinfo extradata");
Arun Menon906de572013-06-18 17:01:40 -07008546 }
8547 }
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308548 if (requested_extradata & OMX_FRAMEPACK_EXTRADATA) {
8549 if (output_capability == V4L2_PIX_FMT_H264) {
8550 DEBUG_PRINT_HIGH("enable OMX_FRAMEPACK_EXTRADATA");
8551 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8552 control.value = V4L2_MPEG_VIDC_EXTRADATA_S3D_FRAME_PACKING;
8553 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
8554 DEBUG_PRINT_HIGH("Failed to set S3D_FRAME_PACKING extradata");
8555 }
8556 } else {
8557 DEBUG_PRINT_HIGH("OMX_FRAMEPACK_EXTRADATA supported for H264 only");
8558 }
8559 }
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08008560 if (requested_extradata & OMX_QP_EXTRADATA) {
8561 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8562 control.value = V4L2_MPEG_VIDC_EXTRADATA_FRAME_QP;
8563 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
8564 DEBUG_PRINT_HIGH("Failed to set QP extradata");
8565 }
8566 }
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08008567 if (requested_extradata & OMX_BITSINFO_EXTRADATA) {
8568 control.id = V4L2_CID_MPEG_VIDC_VIDEO_EXTRADATA;
8569 control.value = V4L2_MPEG_VIDC_EXTRADATA_FRAME_BITS_INFO;
8570 if (ioctl(drv_ctx.video_driver_fd, VIDIOC_S_CTRL, &control)) {
8571 DEBUG_PRINT_HIGH("Failed to set frame bits info extradata");
8572 }
8573 }
Arun Menon906de572013-06-18 17:01:40 -07008574 }
8575 ret = get_buffer_req(&drv_ctx.op_buf);
8576 return ret;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008577}
8578
8579OMX_U32 omx_vdec::count_MB_in_extradata(OMX_OTHER_EXTRADATATYPE *extra)
8580{
Arun Menon906de572013-06-18 17:01:40 -07008581 OMX_U32 num_MB = 0, byte_count = 0, num_MB_in_frame = 0;
8582 OMX_U8 *data_ptr = extra->data, data = 0;
8583 while (byte_count < extra->nDataSize) {
8584 data = *data_ptr;
8585 while (data) {
8586 num_MB += (data&0x01);
8587 data >>= 1;
8588 }
8589 data_ptr++;
8590 byte_count++;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008591 }
Arun Menon906de572013-06-18 17:01:40 -07008592 num_MB_in_frame = ((drv_ctx.video_resolution.frame_width + 15) *
8593 (drv_ctx.video_resolution.frame_height + 15)) >> 8;
8594 return ((num_MB_in_frame > 0)?(num_MB * 100 / num_MB_in_frame) : 0);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008595}
8596
8597void omx_vdec::print_debug_extradata(OMX_OTHER_EXTRADATATYPE *extra)
8598{
Arun Menon906de572013-06-18 17:01:40 -07008599 if (!m_debug_extradata)
8600 return;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008601
8602 DEBUG_PRINT_HIGH(
Deepak Verma867d5132013-12-05 12:23:20 +05308603 "============== Extra Data ==============\n"
8604 " Size: %lu\n"
8605 " Version: %lu\n"
8606 " PortIndex: %lu\n"
8607 " Type: %x\n"
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008608 " DataSize: %lu",
Arun Menon906de572013-06-18 17:01:40 -07008609 extra->nSize, extra->nVersion.nVersion,
8610 extra->nPortIndex, extra->eType, extra->nDataSize);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008611
Arun Menon906de572013-06-18 17:01:40 -07008612 if (extra->eType == (OMX_EXTRADATATYPE)OMX_ExtraDataInterlaceFormat) {
8613 OMX_STREAMINTERLACEFORMAT *intfmt = (OMX_STREAMINTERLACEFORMAT *)extra->data;
8614 DEBUG_PRINT_HIGH(
Deepak Verma867d5132013-12-05 12:23:20 +05308615 "------ Interlace Format ------\n"
8616 " Size: %lu\n"
8617 " Version: %lu\n"
8618 " PortIndex: %lu\n"
8619 " Is Interlace Format: %d\n"
8620 " Interlace Formats: %lu\n"
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008621 "=========== End of Interlace ===========",
Arun Menon906de572013-06-18 17:01:40 -07008622 intfmt->nSize, intfmt->nVersion.nVersion, intfmt->nPortIndex,
8623 intfmt->bInterlaceFormat, intfmt->nInterlaceFormats);
8624 } else if (extra->eType == (OMX_EXTRADATATYPE)OMX_ExtraDataFrameInfo) {
8625 OMX_QCOM_EXTRADATA_FRAMEINFO *fminfo = (OMX_QCOM_EXTRADATA_FRAMEINFO *)extra->data;
8626
8627 DEBUG_PRINT_HIGH(
Deepak Verma867d5132013-12-05 12:23:20 +05308628 "-------- Frame Format --------\n"
8629 " Picture Type: %d\n"
8630 " Interlace Type: %d\n"
8631 " Pan Scan Total Frame Num: %lu\n"
8632 " Concealed Macro Blocks: %lu\n"
8633 " frame rate: %lu\n"
8634 " Time Stamp: %llu\n"
8635 " Aspect Ratio X: %lu\n"
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008636 " Aspect Ratio Y: %lu",
Arun Menon906de572013-06-18 17:01:40 -07008637 fminfo->ePicType,
8638 fminfo->interlaceType,
8639 fminfo->panScan.numWindows,
8640 fminfo->nConcealedMacroblocks,
8641 fminfo->nFrameRate,
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308642 fminfo->nTimeStamp,
Arun Menon906de572013-06-18 17:01:40 -07008643 fminfo->aspectRatio.aspectRatioX,
8644 fminfo->aspectRatio.aspectRatioY);
8645
8646 for (OMX_U32 i = 0; i < fminfo->panScan.numWindows; i++) {
8647 DEBUG_PRINT_HIGH(
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008648 "------------------------------"
Deepak Verma867d5132013-12-05 12:23:20 +05308649 " Pan Scan Frame Num: %lu\n"
8650 " Rectangle x: %ld\n"
8651 " Rectangle y: %ld\n"
8652 " Rectangle dx: %ld\n"
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008653 " Rectangle dy: %ld",
Arun Menon906de572013-06-18 17:01:40 -07008654 i, fminfo->panScan.window[i].x, fminfo->panScan.window[i].y,
8655 fminfo->panScan.window[i].dx, fminfo->panScan.window[i].dy);
8656 }
8657
8658 DEBUG_PRINT_HIGH("========= End of Frame Format ==========");
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308659 } else if (extra->eType == (OMX_EXTRADATATYPE)OMX_ExtraDataFramePackingArrangement) {
8660 OMX_QCOM_FRAME_PACK_ARRANGEMENT *framepack = (OMX_QCOM_FRAME_PACK_ARRANGEMENT *)extra->data;
8661 DEBUG_PRINT_HIGH(
8662 "------------------ Framepack Format ----------\n"
8663 " id: %lu \n"
8664 " cancel_flag: %lu \n"
8665 " type: %lu \n"
8666 " quincunx_sampling_flagFormat: %lu \n"
8667 " content_interpretation_type: %lu \n"
8668 " content_interpretation_type: %lu \n"
8669 " spatial_flipping_flag: %lu \n"
8670 " frame0_flipped_flag: %lu \n"
8671 " field_views_flag: %lu \n"
8672 " current_frame_is_frame0_flag: %lu \n"
8673 " frame0_self_contained_flag: %lu \n"
8674 " frame1_self_contained_flag: %lu \n"
8675 " frame0_grid_position_x: %lu \n"
8676 " frame0_grid_position_y: %lu \n"
8677 " frame1_grid_position_x: %lu \n"
8678 " frame1_grid_position_y: %lu \n"
8679 " reserved_byte: %lu \n"
8680 " repetition_period: %lu \n"
8681 " extension_flag: %lu \n"
8682 "================== End of Framepack ===========",
8683 framepack->id,
8684 framepack->cancel_flag,
8685 framepack->type,
8686 framepack->quincunx_sampling_flag,
8687 framepack->content_interpretation_type,
8688 framepack->spatial_flipping_flag,
8689 framepack->frame0_flipped_flag,
8690 framepack->field_views_flag,
8691 framepack->current_frame_is_frame0_flag,
8692 framepack->frame0_self_contained_flag,
8693 framepack->frame1_self_contained_flag,
8694 framepack->frame0_grid_position_x,
8695 framepack->frame0_grid_position_y,
8696 framepack->frame1_grid_position_x,
8697 framepack->frame1_grid_position_y,
8698 framepack->reserved_byte,
8699 framepack->repetition_period,
8700 framepack->extension_flag);
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08008701 } else if (extra->eType == (OMX_EXTRADATATYPE)OMX_ExtraDataQP) {
8702 OMX_QCOM_EXTRADATA_QP * qp = (OMX_QCOM_EXTRADATA_QP *)extra->data;
8703 DEBUG_PRINT_HIGH(
8704 "---- QP (Frame quantization parameter) ----\n"
8705 " Frame QP: %lu \n"
8706 "================ End of QP ================\n",
8707 qp->nQP);
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08008708 } else if (extra->eType == (OMX_EXTRADATATYPE)OMX_ExtraDataInputBitsInfo) {
8709 OMX_QCOM_EXTRADATA_BITS_INFO * bits = (OMX_QCOM_EXTRADATA_BITS_INFO *)extra->data;
8710 DEBUG_PRINT_HIGH(
8711 "--------- Input bits information --------\n"
8712 " Header bits: %lu \n"
8713 " Frame bits: %lu \n"
8714 "===== End of Input bits information =====\n",
8715 bits->header_bits, bits->frame_bits);
Arun Menon906de572013-06-18 17:01:40 -07008716 } else if (extra->eType == OMX_ExtraDataNone) {
8717 DEBUG_PRINT_HIGH("========== End of Terminator ===========");
8718 } else {
8719 DEBUG_PRINT_HIGH("======= End of Driver Extradata ========");
Shalaj Jain273b3e02012-06-22 19:08:03 -07008720 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008721}
8722
8723void omx_vdec::append_interlace_extradata(OMX_OTHER_EXTRADATATYPE *extra,
Arun Menon7b6fd642014-02-13 16:48:36 -08008724 OMX_U32 interlaced_format_type, bool is_mbaff)
Shalaj Jain273b3e02012-06-22 19:08:03 -07008725{
Arun Menon906de572013-06-18 17:01:40 -07008726 OMX_STREAMINTERLACEFORMAT *interlace_format;
Arun Menon7b6fd642014-02-13 16:48:36 -08008727
Arun Menon906de572013-06-18 17:01:40 -07008728 if (!(client_extradata & OMX_INTERLACE_EXTRADATA)) {
8729 return;
8730 }
8731 extra->nSize = OMX_INTERLACE_EXTRADATA_SIZE;
8732 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8733 extra->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8734 extra->eType = (OMX_EXTRADATATYPE)OMX_ExtraDataInterlaceFormat;
8735 extra->nDataSize = sizeof(OMX_STREAMINTERLACEFORMAT);
8736 interlace_format = (OMX_STREAMINTERLACEFORMAT *)extra->data;
8737 interlace_format->nSize = sizeof(OMX_STREAMINTERLACEFORMAT);
8738 interlace_format->nVersion.nVersion = OMX_SPEC_VERSION;
8739 interlace_format->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
Arun Menon7b6fd642014-02-13 16:48:36 -08008740
8741 if ((interlaced_format_type == INTERLACE_FRAME_PROGRESSIVE) && !is_mbaff) {
Arun Menon906de572013-06-18 17:01:40 -07008742 interlace_format->bInterlaceFormat = OMX_FALSE;
8743 interlace_format->nInterlaceFormats = OMX_InterlaceFrameProgressive;
8744 drv_ctx.interlace = VDEC_InterlaceFrameProgressive;
Arun Menon7b6fd642014-02-13 16:48:36 -08008745 } else if ((interlaced_format_type == INTERLACE_INTERLEAVE_FRAME_TOPFIELDFIRST) && !is_mbaff) {
Praneeth Paladugudd29c282013-09-12 15:41:47 -07008746 interlace_format->bInterlaceFormat = OMX_TRUE;
Arun Menon7b6fd642014-02-13 16:48:36 -08008747 interlace_format->nInterlaceFormats = OMX_InterlaceInterleaveFrameTopFieldFirst;
Praneeth Paladugudd29c282013-09-12 15:41:47 -07008748 drv_ctx.interlace = VDEC_InterlaceFrameProgressive;
Arun Menon7b6fd642014-02-13 16:48:36 -08008749 } else if ((interlaced_format_type == INTERLACE_INTERLEAVE_FRAME_BOTTOMFIELDFIRST) && !is_mbaff) {
Praneeth Paladugudd29c282013-09-12 15:41:47 -07008750 interlace_format->bInterlaceFormat = OMX_TRUE;
Arun Menon7b6fd642014-02-13 16:48:36 -08008751 interlace_format->nInterlaceFormats = OMX_InterlaceInterleaveFrameBottomFieldFirst;
Praneeth Paladugudd29c282013-09-12 15:41:47 -07008752 drv_ctx.interlace = VDEC_InterlaceFrameProgressive;
Arun Menon906de572013-06-18 17:01:40 -07008753 } else {
8754 interlace_format->bInterlaceFormat = OMX_TRUE;
8755 interlace_format->nInterlaceFormats = OMX_InterlaceInterleaveFrameTopFieldFirst;
8756 drv_ctx.interlace = VDEC_InterlaceInterleaveFrameTopFieldFirst;
8757 }
8758 print_debug_extradata(extra);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008759}
8760
Praneeth Paladuguf3a492b2013-01-03 17:35:34 -08008761void omx_vdec::fill_aspect_ratio_info(
Arun Menon906de572013-06-18 17:01:40 -07008762 struct vdec_aspectratioinfo *aspect_ratio_info,
8763 OMX_QCOM_EXTRADATA_FRAMEINFO *frame_info)
Praneeth Paladuguf3a492b2013-01-03 17:35:34 -08008764{
Arun Menon906de572013-06-18 17:01:40 -07008765 m_extradata = frame_info;
8766 m_extradata->aspectRatio.aspectRatioX = aspect_ratio_info->par_width;
8767 m_extradata->aspectRatio.aspectRatioY = aspect_ratio_info->par_height;
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308768 DEBUG_PRINT_LOW("aspectRatioX %lu aspectRatioY %lu", m_extradata->aspectRatio.aspectRatioX,
Arun Menon906de572013-06-18 17:01:40 -07008769 m_extradata->aspectRatio.aspectRatioY);
Praneeth Paladuguf3a492b2013-01-03 17:35:34 -08008770}
Shalaj Jain273b3e02012-06-22 19:08:03 -07008771
8772void omx_vdec::append_frame_info_extradata(OMX_OTHER_EXTRADATATYPE *extra,
Arun Menon906de572013-06-18 17:01:40 -07008773 OMX_U32 num_conceal_mb, OMX_U32 picture_type, OMX_U32 frame_rate,
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308774 OMX_TICKS time_stamp, struct msm_vidc_panscan_window_payload *panscan_payload,
Praneeth Paladuguf3a492b2013-01-03 17:35:34 -08008775 struct vdec_aspectratioinfo *aspect_ratio_info)
Shalaj Jain273b3e02012-06-22 19:08:03 -07008776{
Arun Menon906de572013-06-18 17:01:40 -07008777 OMX_QCOM_EXTRADATA_FRAMEINFO *frame_info = NULL;
8778 struct msm_vidc_panscan_window *panscan_window;
8779 if (!(client_extradata & OMX_FRAMEINFO_EXTRADATA)) {
Praneeth Paladugu48a9a8a2012-12-06 12:12:19 -08008780 return;
Praneeth Paladugud0881ef2013-04-23 23:02:55 -07008781 }
Arun Menon906de572013-06-18 17:01:40 -07008782 extra->nSize = OMX_FRAMEINFO_EXTRADATA_SIZE;
8783 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8784 extra->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8785 extra->eType = (OMX_EXTRADATATYPE)OMX_ExtraDataFrameInfo;
8786 extra->nDataSize = sizeof(OMX_QCOM_EXTRADATA_FRAMEINFO);
8787 frame_info = (OMX_QCOM_EXTRADATA_FRAMEINFO *)extra->data;
8788 switch (picture_type) {
8789 case PICTURE_TYPE_I:
8790 frame_info->ePicType = OMX_VIDEO_PictureTypeI;
8791 break;
8792 case PICTURE_TYPE_P:
8793 frame_info->ePicType = OMX_VIDEO_PictureTypeP;
8794 break;
8795 case PICTURE_TYPE_B:
8796 frame_info->ePicType = OMX_VIDEO_PictureTypeB;
8797 break;
8798 default:
8799 frame_info->ePicType = (OMX_VIDEO_PICTURETYPE)0;
8800 }
8801 if (drv_ctx.interlace == VDEC_InterlaceInterleaveFrameTopFieldFirst)
8802 frame_info->interlaceType = OMX_QCOM_InterlaceInterleaveFrameTopFieldFirst;
8803 else if (drv_ctx.interlace == VDEC_InterlaceInterleaveFrameBottomFieldFirst)
8804 frame_info->interlaceType = OMX_QCOM_InterlaceInterleaveFrameBottomFieldFirst;
8805 else
8806 frame_info->interlaceType = OMX_QCOM_InterlaceFrameProgressive;
8807 memset(&frame_info->aspectRatio, 0, sizeof(frame_info->aspectRatio));
8808 frame_info->nConcealedMacroblocks = num_conceal_mb;
8809 frame_info->nFrameRate = frame_rate;
Rajeshwar Kurapaty90a98112013-09-17 16:07:14 +05308810 frame_info->nTimeStamp = time_stamp;
Arun Menon906de572013-06-18 17:01:40 -07008811 frame_info->panScan.numWindows = 0;
8812 if (output_capability == V4L2_PIX_FMT_MPEG2) {
8813 if (m_disp_hor_size && m_disp_vert_size) {
8814 frame_info->displayAspectRatio.displayHorizontalSize = m_disp_hor_size;
8815 frame_info->displayAspectRatio.displayVerticalSize = m_disp_vert_size;
Pushkaraj Patil5e6ebd92014-03-10 10:29:14 +05308816 } else {
8817 frame_info->displayAspectRatio.displayHorizontalSize = 0;
8818 frame_info->displayAspectRatio.displayVerticalSize = 0;
Arun Menon906de572013-06-18 17:01:40 -07008819 }
8820 }
Praneeth Paladugud0881ef2013-04-23 23:02:55 -07008821
Arun Menon906de572013-06-18 17:01:40 -07008822 if (panscan_payload) {
8823 frame_info->panScan.numWindows = panscan_payload->num_panscan_windows;
8824 panscan_window = &panscan_payload->wnd[0];
8825 for (OMX_U32 i = 0; i < frame_info->panScan.numWindows; i++) {
8826 frame_info->panScan.window[i].x = panscan_window->panscan_window_width;
8827 frame_info->panScan.window[i].y = panscan_window->panscan_window_height;
8828 frame_info->panScan.window[i].dx = panscan_window->panscan_width_offset;
8829 frame_info->panScan.window[i].dy = panscan_window->panscan_height_offset;
8830 panscan_window++;
8831 }
Praneeth Paladugu48a9a8a2012-12-06 12:12:19 -08008832 }
Arun Menon906de572013-06-18 17:01:40 -07008833 fill_aspect_ratio_info(aspect_ratio_info, frame_info);
8834 print_debug_extradata(extra);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008835}
8836
8837void omx_vdec::append_portdef_extradata(OMX_OTHER_EXTRADATATYPE *extra)
8838{
Arun Menon906de572013-06-18 17:01:40 -07008839 OMX_PARAM_PORTDEFINITIONTYPE *portDefn = NULL;
8840 extra->nSize = OMX_PORTDEF_EXTRADATA_SIZE;
8841 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8842 extra->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8843 extra->eType = (OMX_EXTRADATATYPE)OMX_ExtraDataPortDef;
8844 extra->nDataSize = sizeof(OMX_PARAM_PORTDEFINITIONTYPE);
8845 portDefn = (OMX_PARAM_PORTDEFINITIONTYPE *)extra->data;
8846 *portDefn = m_port_def;
8847 DEBUG_PRINT_LOW("append_portdef_extradata height = %lu width = %lu "
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008848 "stride = %lu sliceheight = %lu",portDefn->format.video.nFrameHeight,
Arun Menon906de572013-06-18 17:01:40 -07008849 portDefn->format.video.nFrameWidth,
8850 portDefn->format.video.nStride,
8851 portDefn->format.video.nSliceHeight);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008852}
8853
Maheshwar Ajjad2df2182013-10-24 19:20:34 +05308854void omx_vdec::append_framepack_extradata(OMX_OTHER_EXTRADATATYPE *extra,
8855 struct msm_vidc_s3d_frame_packing_payload *s3d_frame_packing_payload)
8856{
8857 OMX_QCOM_FRAME_PACK_ARRANGEMENT *framepack;
8858 if (FRAME_PACK_SIZE*sizeof(OMX_U32) != sizeof(struct msm_vidc_s3d_frame_packing_payload)) {
8859 DEBUG_PRINT_ERROR("frame packing size mismatch");
8860 return;
8861 }
8862 extra->nSize = OMX_FRAMEPACK_EXTRADATA_SIZE;
8863 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8864 extra->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8865 extra->eType = (OMX_EXTRADATATYPE)OMX_ExtraDataFramePackingArrangement;
8866 extra->nDataSize = sizeof(OMX_QCOM_FRAME_PACK_ARRANGEMENT);
8867 framepack = (OMX_QCOM_FRAME_PACK_ARRANGEMENT *)extra->data;
8868 framepack->nSize = sizeof(OMX_QCOM_FRAME_PACK_ARRANGEMENT);
8869 framepack->nVersion.nVersion = OMX_SPEC_VERSION;
8870 framepack->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8871 memcpy(&framepack->id, s3d_frame_packing_payload,
8872 sizeof(struct msm_vidc_s3d_frame_packing_payload));
8873 memcpy(&m_frame_pack_arrangement, framepack,
8874 sizeof(OMX_QCOM_FRAME_PACK_ARRANGEMENT));
8875 print_debug_extradata(extra);
8876}
8877
Jorge Solano Altamiranob10850d2014-01-08 11:17:58 -08008878void omx_vdec::append_qp_extradata(OMX_OTHER_EXTRADATATYPE *extra,
8879 struct msm_vidc_frame_qp_payload *qp_payload)
8880{
8881 OMX_QCOM_EXTRADATA_QP * qp = NULL;
8882 if (!qp_payload) {
8883 DEBUG_PRINT_ERROR("QP payload is NULL");
8884 return;
8885 }
8886 extra->nSize = OMX_QP_EXTRADATA_SIZE;
8887 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8888 extra->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8889 extra->eType = (OMX_EXTRADATATYPE)OMX_ExtraDataQP;
8890 extra->nDataSize = sizeof(OMX_QCOM_EXTRADATA_QP);
8891 qp = (OMX_QCOM_EXTRADATA_QP *)extra->data;
8892 qp->nQP = qp_payload->frame_qp;
8893 print_debug_extradata(extra);
8894}
8895
Jorge Solano Altamirano54338452014-01-08 11:04:57 -08008896void omx_vdec::append_bitsinfo_extradata(OMX_OTHER_EXTRADATATYPE *extra,
8897 struct msm_vidc_frame_bits_info_payload *bits_payload)
8898{
8899 OMX_QCOM_EXTRADATA_BITS_INFO * bits = NULL;
8900 if (!bits_payload) {
8901 DEBUG_PRINT_ERROR("bits info payload is NULL");
8902 return;
8903 }
8904 extra->nSize = OMX_BITSINFO_EXTRADATA_SIZE;
8905 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8906 extra->nPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
8907 extra->eType = (OMX_EXTRADATATYPE)OMX_ExtraDataInputBitsInfo;
8908 extra->nDataSize = sizeof(OMX_QCOM_EXTRADATA_BITS_INFO);
8909 bits = (OMX_QCOM_EXTRADATA_BITS_INFO*)extra->data;
8910 bits->frame_bits = bits_payload->frame_bits;
8911 bits->header_bits = bits_payload->header_bits;
8912 print_debug_extradata(extra);
8913}
8914
Shalaj Jain273b3e02012-06-22 19:08:03 -07008915void omx_vdec::append_terminator_extradata(OMX_OTHER_EXTRADATATYPE *extra)
8916{
Arun Menon906de572013-06-18 17:01:40 -07008917 if (!client_extradata) {
8918 return;
8919 }
8920 extra->nSize = sizeof(OMX_OTHER_EXTRADATATYPE);
8921 extra->nVersion.nVersion = OMX_SPEC_VERSION;
8922 extra->eType = OMX_ExtraDataNone;
8923 extra->nDataSize = 0;
8924 extra->data[0] = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008925
Arun Menon906de572013-06-18 17:01:40 -07008926 print_debug_extradata(extra);
Shalaj Jain273b3e02012-06-22 19:08:03 -07008927}
8928
8929OMX_ERRORTYPE omx_vdec::allocate_desc_buffer(OMX_U32 index)
8930{
Arun Menon906de572013-06-18 17:01:40 -07008931 OMX_ERRORTYPE eRet = OMX_ErrorNone;
8932 if (index >= drv_ctx.ip_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008933 DEBUG_PRINT_ERROR("ERROR:Desc Buffer Index not found");
Arun Menon906de572013-06-18 17:01:40 -07008934 return OMX_ErrorInsufficientResources;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008935 }
Arun Menon906de572013-06-18 17:01:40 -07008936 if (m_desc_buffer_ptr == NULL) {
8937 m_desc_buffer_ptr = (desc_buffer_hdr*) \
8938 calloc( (sizeof(desc_buffer_hdr)),
8939 drv_ctx.ip_buf.actualcount);
8940 if (m_desc_buffer_ptr == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008941 DEBUG_PRINT_ERROR("m_desc_buffer_ptr Allocation failed ");
Arun Menon906de572013-06-18 17:01:40 -07008942 return OMX_ErrorInsufficientResources;
8943 }
8944 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008945
Arun Menon906de572013-06-18 17:01:40 -07008946 m_desc_buffer_ptr[index].buf_addr = (unsigned char *)malloc (DESC_BUFFER_SIZE * sizeof(OMX_U8));
8947 if (m_desc_buffer_ptr[index].buf_addr == NULL) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07008948 DEBUG_PRINT_ERROR("desc buffer Allocation failed ");
Arun Menon906de572013-06-18 17:01:40 -07008949 return OMX_ErrorInsufficientResources;
8950 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07008951
Arun Menon906de572013-06-18 17:01:40 -07008952 return eRet;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008953}
8954
8955void omx_vdec::insert_demux_addr_offset(OMX_U32 address_offset)
8956{
Arun Menon906de572013-06-18 17:01:40 -07008957 DEBUG_PRINT_LOW("Inserting address offset (%lu) at idx (%lu)", address_offset,m_demux_entries);
8958 if (m_demux_entries < 8192) {
8959 m_demux_offsets[m_demux_entries++] = address_offset;
8960 }
8961 return;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008962}
8963
8964void omx_vdec::extract_demux_addr_offsets(OMX_BUFFERHEADERTYPE *buf_hdr)
8965{
Arun Menon906de572013-06-18 17:01:40 -07008966 OMX_U32 bytes_to_parse = buf_hdr->nFilledLen;
8967 OMX_U8 *buf = buf_hdr->pBuffer + buf_hdr->nOffset;
8968 OMX_U32 index = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008969
Arun Menon906de572013-06-18 17:01:40 -07008970 m_demux_entries = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008971
Arun Menon906de572013-06-18 17:01:40 -07008972 while (index < bytes_to_parse) {
8973 if ( ((buf[index] == 0x00) && (buf[index+1] == 0x00) &&
8974 (buf[index+2] == 0x00) && (buf[index+3] == 0x01)) ||
8975 ((buf[index] == 0x00) && (buf[index+1] == 0x00) &&
8976 (buf[index+2] == 0x01)) ) {
8977 //Found start code, insert address offset
8978 insert_demux_addr_offset(index);
8979 if (buf[index+2] == 0x01) // 3 byte start code
8980 index += 3;
8981 else //4 byte start code
8982 index += 4;
8983 } else
8984 index++;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008985 }
Arun Menon906de572013-06-18 17:01:40 -07008986 DEBUG_PRINT_LOW("Extracted (%lu) demux entry offsets",m_demux_entries);
8987 return;
Shalaj Jain273b3e02012-06-22 19:08:03 -07008988}
8989
8990OMX_ERRORTYPE omx_vdec::handle_demux_data(OMX_BUFFERHEADERTYPE *p_buf_hdr)
8991{
Arun Menon906de572013-06-18 17:01:40 -07008992 //fix this, handle 3 byte start code, vc1 terminator entry
8993 OMX_U8 *p_demux_data = NULL;
8994 OMX_U32 desc_data = 0;
8995 OMX_U32 start_addr = 0;
8996 OMX_U32 nal_size = 0;
8997 OMX_U32 suffix_byte = 0;
8998 OMX_U32 demux_index = 0;
8999 OMX_U32 buffer_index = 0;
Shalaj Jain273b3e02012-06-22 19:08:03 -07009000
Arun Menon906de572013-06-18 17:01:40 -07009001 if (m_desc_buffer_ptr == NULL) {
9002 DEBUG_PRINT_ERROR("m_desc_buffer_ptr is NULL. Cannot append demux entries.");
9003 return OMX_ErrorBadParameter;
Shalaj Jain273b3e02012-06-22 19:08:03 -07009004 }
Shalaj Jain273b3e02012-06-22 19:08:03 -07009005
Arun Menon906de572013-06-18 17:01:40 -07009006 buffer_index = p_buf_hdr - ((OMX_BUFFERHEADERTYPE *)m_inp_mem_ptr);
9007 if (buffer_index > drv_ctx.ip_buf.actualcount) {
9008 DEBUG_PRINT_ERROR("handle_demux_data:Buffer index is incorrect (%lu)", buffer_index);
9009 return OMX_ErrorBadParameter;
9010 }
9011
9012 p_demux_data = (OMX_U8 *) m_desc_buffer_ptr[buffer_index].buf_addr;
9013
9014 if ( ((OMX_U8*)p_demux_data == NULL) ||
9015 ((m_demux_entries * 16) + 1) > DESC_BUFFER_SIZE) {
9016 DEBUG_PRINT_ERROR("Insufficient buffer. Cannot append demux entries.");
9017 return OMX_ErrorBadParameter;
9018 } else {
9019 for (; demux_index < m_demux_entries; demux_index++) {
9020 desc_data = 0;
9021 start_addr = m_demux_offsets[demux_index];
9022 if (p_buf_hdr->pBuffer[m_demux_offsets[demux_index] + 2] == 0x01) {
9023 suffix_byte = p_buf_hdr->pBuffer[m_demux_offsets[demux_index] + 3];
9024 } else {
9025 suffix_byte = p_buf_hdr->pBuffer[m_demux_offsets[demux_index] + 4];
9026 }
9027 if (demux_index < (m_demux_entries - 1)) {
9028 nal_size = m_demux_offsets[demux_index + 1] - m_demux_offsets[demux_index] - 2;
9029 } else {
9030 nal_size = p_buf_hdr->nFilledLen - m_demux_offsets[demux_index] - 2;
9031 }
9032 DEBUG_PRINT_LOW("Start_addr(%p), suffix_byte(0x%lx),nal_size(%lu),demux_index(%lu)",
9033 (void *)start_addr,
9034 suffix_byte,
9035 nal_size,
9036 demux_index);
9037 desc_data = (start_addr >> 3) << 1;
9038 desc_data |= (start_addr & 7) << 21;
9039 desc_data |= suffix_byte << 24;
9040
9041 memcpy(p_demux_data, &desc_data, sizeof(OMX_U32));
9042 memcpy(p_demux_data + 4, &nal_size, sizeof(OMX_U32));
9043 memset(p_demux_data + 8, 0, sizeof(OMX_U32));
9044 memset(p_demux_data + 12, 0, sizeof(OMX_U32));
9045
9046 p_demux_data += 16;
9047 }
9048 if (codec_type_parse == CODEC_TYPE_VC1) {
9049 DEBUG_PRINT_LOW("VC1 terminator entry");
9050 desc_data = 0;
9051 desc_data = 0x82 << 24;
9052 memcpy(p_demux_data, &desc_data, sizeof(OMX_U32));
9053 memset(p_demux_data + 4, 0, sizeof(OMX_U32));
9054 memset(p_demux_data + 8, 0, sizeof(OMX_U32));
9055 memset(p_demux_data + 12, 0, sizeof(OMX_U32));
9056 p_demux_data += 16;
9057 m_demux_entries++;
9058 }
9059 //Add zero word to indicate end of descriptors
9060 memset(p_demux_data, 0, sizeof(OMX_U32));
9061
9062 m_desc_buffer_ptr[buffer_index].desc_data_size = (m_demux_entries * 16) + sizeof(OMX_U32);
9063 DEBUG_PRINT_LOW("desc table data size=%lu", m_desc_buffer_ptr[buffer_index].desc_data_size);
9064 }
9065 memset(m_demux_offsets, 0, ( sizeof(OMX_U32) * 8192) );
9066 m_demux_entries = 0;
9067 DEBUG_PRINT_LOW("Demux table complete!");
9068 return OMX_ErrorNone;
Shalaj Jain273b3e02012-06-22 19:08:03 -07009069}
9070
Deva Ramasubramanian9403f022012-11-28 18:27:53 -08009071OMX_ERRORTYPE omx_vdec::createDivxDrmContext()
Shalaj Jain273b3e02012-06-22 19:08:03 -07009072{
Arun Menon906de572013-06-18 17:01:40 -07009073 OMX_ERRORTYPE err = OMX_ErrorNone;
9074 iDivXDrmDecrypt = DivXDrmDecrypt::Create();
9075 if (iDivXDrmDecrypt) {
9076 OMX_ERRORTYPE err = iDivXDrmDecrypt->Init();
9077 if (err!=OMX_ErrorNone) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009078 DEBUG_PRINT_ERROR("ERROR :iDivXDrmDecrypt->Init %d", err);
Shalaj Jain273b3e02012-06-22 19:08:03 -07009079 delete iDivXDrmDecrypt;
9080 iDivXDrmDecrypt = NULL;
Arun Menon906de572013-06-18 17:01:40 -07009081 }
9082 } else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009083 DEBUG_PRINT_ERROR("Unable to Create DIVX DRM");
Arun Menon906de572013-06-18 17:01:40 -07009084 err = OMX_ErrorUndefined;
9085 }
9086 return err;
Shalaj Jain273b3e02012-06-22 19:08:03 -07009087}
Shalaj Jain273b3e02012-06-22 19:08:03 -07009088
Vinay Kaliada4f4422013-01-09 10:45:03 -08009089omx_vdec::allocate_color_convert_buf::allocate_color_convert_buf()
9090{
Arun Menon906de572013-06-18 17:01:40 -07009091 enabled = false;
9092 omx = NULL;
9093 init_members();
9094 ColorFormat = OMX_COLOR_FormatMax;
Praveen Chavandb7776f2014-02-06 18:17:25 -08009095 dest_format = YCbCr420P;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009096}
9097
9098void omx_vdec::allocate_color_convert_buf::set_vdec_client(void *client)
9099{
Arun Menon906de572013-06-18 17:01:40 -07009100 omx = reinterpret_cast<omx_vdec*>(client);
Vinay Kaliada4f4422013-01-09 10:45:03 -08009101}
9102
Arun Menon906de572013-06-18 17:01:40 -07009103void omx_vdec::allocate_color_convert_buf::init_members()
9104{
9105 allocated_count = 0;
9106 buffer_size_req = 0;
9107 buffer_alignment_req = 0;
9108 memset(m_platform_list_client,0,sizeof(m_platform_list_client));
9109 memset(m_platform_entry_client,0,sizeof(m_platform_entry_client));
9110 memset(m_pmem_info_client,0,sizeof(m_pmem_info_client));
9111 memset(m_out_mem_ptr_client,0,sizeof(m_out_mem_ptr_client));
Vinay Kaliada4f4422013-01-09 10:45:03 -08009112#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07009113 memset(op_buf_ion_info,0,sizeof(m_platform_entry_client));
Vinay Kaliada4f4422013-01-09 10:45:03 -08009114#endif
Arun Menon906de572013-06-18 17:01:40 -07009115 for (int i = 0; i < MAX_COUNT; i++)
9116 pmem_fd[i] = -1;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009117}
9118
Arun Menon906de572013-06-18 17:01:40 -07009119omx_vdec::allocate_color_convert_buf::~allocate_color_convert_buf()
9120{
9121 c2d.destroy();
Vinay Kaliada4f4422013-01-09 10:45:03 -08009122}
9123
9124bool omx_vdec::allocate_color_convert_buf::update_buffer_req()
9125{
Arun Menon906de572013-06-18 17:01:40 -07009126 bool status = true;
9127 unsigned int src_size = 0, destination_size = 0;
9128 OMX_COLOR_FORMATTYPE drv_color_format;
9129 if (!omx) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009130 DEBUG_PRINT_ERROR("Invalid client in color convert");
Arun Menon906de572013-06-18 17:01:40 -07009131 return false;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009132 }
Arun Menon906de572013-06-18 17:01:40 -07009133 if (!enabled) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009134 DEBUG_PRINT_HIGH("No color conversion required");
Arun Menon906de572013-06-18 17:01:40 -07009135 return status;
9136 }
9137 pthread_mutex_lock(&omx->c_lock);
9138 if (omx->drv_ctx.output_format != VDEC_YUV_FORMAT_NV12 &&
9139 ColorFormat != OMX_COLOR_FormatYUV420Planar) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009140 DEBUG_PRINT_ERROR("update_buffer_req: Unsupported color conversion");
Arun Menon906de572013-06-18 17:01:40 -07009141 status = false;
9142 goto fail_update_buf_req;
9143 }
9144 c2d.close();
9145 status = c2d.open(omx->drv_ctx.video_resolution.frame_height,
9146 omx->drv_ctx.video_resolution.frame_width,
Praveen Chavandb7776f2014-02-06 18:17:25 -08009147 NV12_128m,dest_format);
Arun Menon906de572013-06-18 17:01:40 -07009148 if (status) {
9149 status = c2d.get_buffer_size(C2D_INPUT,src_size);
9150 if (status)
9151 status = c2d.get_buffer_size(C2D_OUTPUT,destination_size);
9152 }
9153 if (status) {
9154 if (!src_size || src_size > omx->drv_ctx.op_buf.buffer_size ||
9155 !destination_size) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009156 DEBUG_PRINT_ERROR("ERROR: Size mismatch in C2D src_size %d"
Arun Menon906de572013-06-18 17:01:40 -07009157 "driver size %d destination size %d",
9158 src_size,omx->drv_ctx.op_buf.buffer_size,destination_size);
9159 status = false;
9160 c2d.close();
9161 buffer_size_req = 0;
9162 } else {
9163 buffer_size_req = destination_size;
9164 if (buffer_size_req < omx->drv_ctx.op_buf.buffer_size)
9165 buffer_size_req = omx->drv_ctx.op_buf.buffer_size;
9166 if (buffer_alignment_req < omx->drv_ctx.op_buf.alignment)
9167 buffer_alignment_req = omx->drv_ctx.op_buf.alignment;
9168 }
9169 }
Praneeth Paladuguf6995272013-02-04 14:03:56 -08009170fail_update_buf_req:
Arun Menon906de572013-06-18 17:01:40 -07009171 pthread_mutex_unlock(&omx->c_lock);
9172 return status;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009173}
9174
9175bool omx_vdec::allocate_color_convert_buf::set_color_format(
Arun Menon906de572013-06-18 17:01:40 -07009176 OMX_COLOR_FORMATTYPE dest_color_format)
Vinay Kaliada4f4422013-01-09 10:45:03 -08009177{
Arun Menon906de572013-06-18 17:01:40 -07009178 bool status = true;
9179 OMX_COLOR_FORMATTYPE drv_color_format;
9180 if (!omx) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009181 DEBUG_PRINT_ERROR("Invalid client in color convert");
Arun Menon906de572013-06-18 17:01:40 -07009182 return false;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009183 }
Arun Menon906de572013-06-18 17:01:40 -07009184 pthread_mutex_lock(&omx->c_lock);
9185 if (omx->drv_ctx.output_format == VDEC_YUV_FORMAT_NV12)
9186 drv_color_format = (OMX_COLOR_FORMATTYPE)
9187 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
9188 else {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009189 DEBUG_PRINT_ERROR("Incorrect color format");
Arun Menon906de572013-06-18 17:01:40 -07009190 status = false;
9191 }
9192 if (status && (drv_color_format != dest_color_format)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009193 DEBUG_PRINT_LOW("Enabling C2D");
Praveen Chavandb7776f2014-02-06 18:17:25 -08009194 if ((dest_color_format != OMX_COLOR_FormatYUV420Planar) &&
9195 (dest_color_format != OMX_COLOR_FormatYUV420SemiPlanar)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009196 DEBUG_PRINT_ERROR("Unsupported color format for c2d");
Arun Menon906de572013-06-18 17:01:40 -07009197 status = false;
9198 } else {
Praveen Chavandb7776f2014-02-06 18:17:25 -08009199 ColorFormat = dest_color_format;
9200 dest_format = (dest_color_format == OMX_COLOR_FormatYUV420Planar) ?
9201 YCbCr420P : YCbCr420SP;
Arun Menon906de572013-06-18 17:01:40 -07009202 if (enabled)
9203 c2d.destroy();
9204 enabled = false;
9205 if (!c2d.init()) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009206 DEBUG_PRINT_ERROR("open failed for c2d");
Arun Menon906de572013-06-18 17:01:40 -07009207 status = false;
9208 } else
9209 enabled = true;
9210 }
9211 } else {
9212 if (enabled)
9213 c2d.destroy();
9214 enabled = false;
9215 }
9216 pthread_mutex_unlock(&omx->c_lock);
9217 return status;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009218}
9219
9220OMX_BUFFERHEADERTYPE* omx_vdec::allocate_color_convert_buf::get_il_buf_hdr()
9221{
Arun Menon906de572013-06-18 17:01:40 -07009222 if (!omx) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009223 DEBUG_PRINT_ERROR("Invalid param get_buf_hdr");
Arun Menon906de572013-06-18 17:01:40 -07009224 return NULL;
Praneeth Paladuguf6995272013-02-04 14:03:56 -08009225 }
Arun Menon906de572013-06-18 17:01:40 -07009226 if (!enabled)
9227 return omx->m_out_mem_ptr;
9228 return m_out_mem_ptr_client;
9229}
9230
9231 OMX_BUFFERHEADERTYPE* omx_vdec::allocate_color_convert_buf::get_il_buf_hdr
9232(OMX_BUFFERHEADERTYPE *bufadd)
9233{
9234 if (!omx) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009235 DEBUG_PRINT_ERROR("Invalid param get_buf_hdr");
Arun Menon906de572013-06-18 17:01:40 -07009236 return NULL;
9237 }
9238 if (!enabled)
9239 return bufadd;
9240
9241 unsigned index = 0;
9242 index = bufadd - omx->m_out_mem_ptr;
9243 if (index < omx->drv_ctx.op_buf.actualcount) {
9244 m_out_mem_ptr_client[index].nFlags = (bufadd->nFlags & OMX_BUFFERFLAG_EOS);
9245 m_out_mem_ptr_client[index].nTimeStamp = bufadd->nTimeStamp;
9246 bool status;
9247 if (!omx->in_reconfig && !omx->output_flush_progress && bufadd->nFilledLen) {
9248 pthread_mutex_lock(&omx->c_lock);
9249 status = c2d.convert(omx->drv_ctx.ptr_outputbuffer[index].pmem_fd,
9250 omx->m_out_mem_ptr->pBuffer, bufadd->pBuffer, pmem_fd[index],
9251 pmem_baseaddress[index], pmem_baseaddress[index]);
9252 pthread_mutex_unlock(&omx->c_lock);
9253 m_out_mem_ptr_client[index].nFilledLen = buffer_size_req;
9254 if (!status) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009255 DEBUG_PRINT_ERROR("Failed color conversion %d", status);
Arun Menon906de572013-06-18 17:01:40 -07009256 m_out_mem_ptr_client[index].nFilledLen = 0;
9257 return &m_out_mem_ptr_client[index];
9258 }
9259 } else
9260 m_out_mem_ptr_client[index].nFilledLen = 0;
9261 return &m_out_mem_ptr_client[index];
9262 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009263 DEBUG_PRINT_ERROR("Index messed up in the get_il_buf_hdr");
Arun Menon906de572013-06-18 17:01:40 -07009264 return NULL;
9265}
9266
9267 OMX_BUFFERHEADERTYPE* omx_vdec::allocate_color_convert_buf::get_dr_buf_hdr
9268(OMX_BUFFERHEADERTYPE *bufadd)
9269{
9270 if (!omx) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009271 DEBUG_PRINT_ERROR("Invalid param get_buf_hdr");
Arun Menon906de572013-06-18 17:01:40 -07009272 return NULL;
9273 }
9274 if (!enabled)
9275 return bufadd;
9276 unsigned index = 0;
9277 index = bufadd - m_out_mem_ptr_client;
9278 if (index < omx->drv_ctx.op_buf.actualcount) {
9279 return &omx->m_out_mem_ptr[index];
9280 }
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009281 DEBUG_PRINT_ERROR("Index messed up in the get_dr_buf_hdr");
Arun Menon906de572013-06-18 17:01:40 -07009282 return NULL;
9283}
9284 bool omx_vdec::allocate_color_convert_buf::get_buffer_req
9285(unsigned int &buffer_size)
9286{
9287 bool status = true;
9288 pthread_mutex_lock(&omx->c_lock);
9289 if (!enabled)
Vinay Kaliada4f4422013-01-09 10:45:03 -08009290 buffer_size = omx->drv_ctx.op_buf.buffer_size;
Arun Menon906de572013-06-18 17:01:40 -07009291 else {
9292 if (!c2d.get_buffer_size(C2D_OUTPUT,buffer_size)) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009293 DEBUG_PRINT_ERROR("Get buffer size failed");
Arun Menon906de572013-06-18 17:01:40 -07009294 status = false;
9295 goto fail_get_buffer_size;
9296 }
9297 }
9298 if (buffer_size < omx->drv_ctx.op_buf.buffer_size)
9299 buffer_size = omx->drv_ctx.op_buf.buffer_size;
9300 if (buffer_alignment_req < omx->drv_ctx.op_buf.alignment)
9301 buffer_alignment_req = omx->drv_ctx.op_buf.alignment;
Praneeth Paladuguf6995272013-02-04 14:03:56 -08009302fail_get_buffer_size:
Arun Menon906de572013-06-18 17:01:40 -07009303 pthread_mutex_unlock(&omx->c_lock);
9304 return status;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009305}
9306OMX_ERRORTYPE omx_vdec::allocate_color_convert_buf::free_output_buffer(
Arun Menon906de572013-06-18 17:01:40 -07009307 OMX_BUFFERHEADERTYPE *bufhdr)
9308{
9309 unsigned int index = 0;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009310
Arun Menon906de572013-06-18 17:01:40 -07009311 if (!enabled)
9312 return omx->free_output_buffer(bufhdr);
9313 if (enabled && omx->is_component_secure())
9314 return OMX_ErrorNone;
9315 if (!allocated_count || !bufhdr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009316 DEBUG_PRINT_ERROR("Color convert no buffer to be freed %p",bufhdr);
Arun Menon906de572013-06-18 17:01:40 -07009317 return OMX_ErrorBadParameter;
9318 }
9319 index = bufhdr - m_out_mem_ptr_client;
9320 if (index >= omx->drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009321 DEBUG_PRINT_ERROR("Incorrect index color convert free_output_buffer");
Arun Menon906de572013-06-18 17:01:40 -07009322 return OMX_ErrorBadParameter;
9323 }
9324 if (pmem_fd[index] > 0) {
9325 munmap(pmem_baseaddress[index], buffer_size_req);
9326 close(pmem_fd[index]);
9327 }
9328 pmem_fd[index] = -1;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009329#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07009330 omx->free_ion_memory(&op_buf_ion_info[index]);
Vinay Kaliada4f4422013-01-09 10:45:03 -08009331#endif
Arun Menon906de572013-06-18 17:01:40 -07009332 m_heap_ptr[index].video_heap_ptr = NULL;
9333 if (allocated_count > 0)
9334 allocated_count--;
9335 else
9336 allocated_count = 0;
9337 if (!allocated_count) {
9338 pthread_mutex_lock(&omx->c_lock);
9339 c2d.close();
9340 init_members();
9341 pthread_mutex_unlock(&omx->c_lock);
9342 }
9343 return omx->free_output_buffer(&omx->m_out_mem_ptr[index]);
Vinay Kaliada4f4422013-01-09 10:45:03 -08009344}
9345
9346OMX_ERRORTYPE omx_vdec::allocate_color_convert_buf::allocate_buffers_color_convert(OMX_HANDLETYPE hComp,
Arun Menon906de572013-06-18 17:01:40 -07009347 OMX_BUFFERHEADERTYPE **bufferHdr,OMX_U32 port,OMX_PTR appData,OMX_U32 bytes)
Vinay Kaliada4f4422013-01-09 10:45:03 -08009348{
Arun Menon906de572013-06-18 17:01:40 -07009349 OMX_ERRORTYPE eRet = OMX_ErrorNone;
9350 if (!enabled) {
9351 eRet = omx->allocate_output_buffer(hComp,bufferHdr,port,appData,bytes);
9352 return eRet;
9353 }
9354 if (enabled && omx->is_component_secure()) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009355 DEBUG_PRINT_ERROR("Notin color convert mode secure_mode %d",
Arun Menon906de572013-06-18 17:01:40 -07009356 omx->is_component_secure());
9357 return OMX_ErrorUnsupportedSetting;
9358 }
9359 if (!bufferHdr || bytes > buffer_size_req) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009360 DEBUG_PRINT_ERROR("Invalid params allocate_buffers_color_convert %p", bufferHdr);
9361 DEBUG_PRINT_ERROR("color_convert buffer_size_req %d bytes %lu",
Arun Menon906de572013-06-18 17:01:40 -07009362 buffer_size_req,bytes);
9363 return OMX_ErrorBadParameter;
9364 }
9365 if (allocated_count >= omx->drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009366 DEBUG_PRINT_ERROR("Actual count err in allocate_buffers_color_convert");
Arun Menon906de572013-06-18 17:01:40 -07009367 return OMX_ErrorInsufficientResources;
9368 }
9369 OMX_BUFFERHEADERTYPE *temp_bufferHdr = NULL;
9370 eRet = omx->allocate_output_buffer(hComp,&temp_bufferHdr,
9371 port,appData,omx->drv_ctx.op_buf.buffer_size);
9372 if (eRet != OMX_ErrorNone || !temp_bufferHdr) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009373 DEBUG_PRINT_ERROR("Buffer allocation failed color_convert");
Arun Menon906de572013-06-18 17:01:40 -07009374 return eRet;
9375 }
9376 if ((temp_bufferHdr - omx->m_out_mem_ptr) >=
Surajit Podderd2644d52013-08-28 17:59:06 +05309377 (int)omx->drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009378 DEBUG_PRINT_ERROR("Invalid header index %d",
Arun Menon906de572013-06-18 17:01:40 -07009379 (temp_bufferHdr - omx->m_out_mem_ptr));
9380 return OMX_ErrorUndefined;
9381 }
9382 unsigned int i = allocated_count;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009383#ifdef USE_ION
Arun Menon906de572013-06-18 17:01:40 -07009384 op_buf_ion_info[i].ion_device_fd = omx->alloc_map_ion_memory(
9385 buffer_size_req,buffer_alignment_req,
9386 &op_buf_ion_info[i].ion_alloc_data,&op_buf_ion_info[i].fd_ion_data,
9387 0);
9388 pmem_fd[i] = op_buf_ion_info[i].fd_ion_data.fd;
9389 if (op_buf_ion_info[i].ion_device_fd < 0) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009390 DEBUG_PRINT_ERROR("alloc_map_ion failed in color_convert");
Arun Menon906de572013-06-18 17:01:40 -07009391 return OMX_ErrorInsufficientResources;
9392 }
9393 pmem_baseaddress[i] = (unsigned char *)mmap(NULL,buffer_size_req,
9394 PROT_READ|PROT_WRITE,MAP_SHARED,pmem_fd[i],0);
Vinay Kaliada4f4422013-01-09 10:45:03 -08009395
Arun Menon906de572013-06-18 17:01:40 -07009396 if (pmem_baseaddress[i] == MAP_FAILED) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009397 DEBUG_PRINT_ERROR("MMAP failed for Size %d",buffer_size_req);
Arun Menon906de572013-06-18 17:01:40 -07009398 close(pmem_fd[i]);
9399 omx->free_ion_memory(&op_buf_ion_info[i]);
9400 return OMX_ErrorInsufficientResources;
9401 }
9402 m_heap_ptr[i].video_heap_ptr = new VideoHeap (
9403 op_buf_ion_info[i].ion_device_fd,buffer_size_req,
9404 pmem_baseaddress[i],op_buf_ion_info[i].ion_alloc_data.handle,pmem_fd[i]);
Vinay Kaliada4f4422013-01-09 10:45:03 -08009405#endif
Arun Menon906de572013-06-18 17:01:40 -07009406 m_pmem_info_client[i].pmem_fd = (OMX_U32)m_heap_ptr[i].video_heap_ptr.get();
9407 m_pmem_info_client[i].offset = 0;
9408 m_platform_entry_client[i].entry = (void *)&m_pmem_info_client[i];
9409 m_platform_entry_client[i].type = OMX_QCOM_PLATFORM_PRIVATE_PMEM;
9410 m_platform_list_client[i].nEntries = 1;
9411 m_platform_list_client[i].entryList = &m_platform_entry_client[i];
9412 m_out_mem_ptr_client[i].pOutputPortPrivate = NULL;
9413 m_out_mem_ptr_client[i].nAllocLen = buffer_size_req;
9414 m_out_mem_ptr_client[i].nFilledLen = 0;
9415 m_out_mem_ptr_client[i].nFlags = 0;
9416 m_out_mem_ptr_client[i].nOutputPortIndex = OMX_CORE_OUTPUT_PORT_INDEX;
9417 m_out_mem_ptr_client[i].nSize = sizeof(OMX_BUFFERHEADERTYPE);
9418 m_out_mem_ptr_client[i].nVersion.nVersion = OMX_SPEC_VERSION;
9419 m_out_mem_ptr_client[i].pPlatformPrivate = &m_platform_list_client[i];
9420 m_out_mem_ptr_client[i].pBuffer = pmem_baseaddress[i];
9421 m_out_mem_ptr_client[i].pAppPrivate = appData;
9422 *bufferHdr = &m_out_mem_ptr_client[i];
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009423 DEBUG_PRINT_ERROR("IL client buffer header %p", *bufferHdr);
Arun Menon906de572013-06-18 17:01:40 -07009424 allocated_count++;
9425 return eRet;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009426}
9427
9428bool omx_vdec::is_component_secure()
9429{
Arun Menon906de572013-06-18 17:01:40 -07009430 return secure_mode;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009431}
9432
9433bool omx_vdec::allocate_color_convert_buf::get_color_format(OMX_COLOR_FORMATTYPE &dest_color_format)
9434{
Arun Menon906de572013-06-18 17:01:40 -07009435 bool status = true;
9436 if (!enabled) {
9437 if (omx->drv_ctx.output_format == VDEC_YUV_FORMAT_NV12)
9438 dest_color_format = (OMX_COLOR_FORMATTYPE)
9439 QOMX_COLOR_FORMATYUV420PackedSemiPlanar32m;
9440 else
9441 status = false;
9442 } else {
Praveen Chavandb7776f2014-02-06 18:17:25 -08009443 if (ColorFormat == OMX_COLOR_FormatYUV420Planar ||
9444 ColorFormat == OMX_COLOR_FormatYUV420SemiPlanar) {
9445 dest_color_format = ColorFormat;
Arun Menon906de572013-06-18 17:01:40 -07009446 } else
Praveen Chavandb7776f2014-02-06 18:17:25 -08009447 status = false;
Arun Menon906de572013-06-18 17:01:40 -07009448 }
9449 return status;
Vinay Kaliada4f4422013-01-09 10:45:03 -08009450}
Arun Menonbdb80b02013-08-12 17:45:54 -07009451
Arun Menonbdb80b02013-08-12 17:45:54 -07009452void omx_vdec::buf_ref_add(OMX_U32 fd, OMX_U32 offset)
9453{
9454 int i = 0;
9455 bool buf_present = false;
9456 pthread_mutex_lock(&m_lock);
9457 for (i = 0; i < drv_ctx.op_buf.actualcount; i++) {
9458 //check the buffer fd, offset, uv addr with list contents
9459 //If present increment reference.
9460 if ((out_dynamic_list[i].fd == fd) &&
9461 (out_dynamic_list[i].offset == offset)) {
9462 out_dynamic_list[i].ref_count++;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009463 DEBUG_PRINT_LOW("buf_ref_add: [ALREADY PRESENT] fd = %d ref_count = %d",
Arun Menonbdb80b02013-08-12 17:45:54 -07009464 out_dynamic_list[i].fd, out_dynamic_list[i].ref_count);
9465 buf_present = true;
9466 break;
9467 }
9468 }
9469 if (!buf_present) {
9470 for (i = 0; i < drv_ctx.op_buf.actualcount; i++) {
9471 //search for a entry to insert details of the new buffer
9472 if (out_dynamic_list[i].dup_fd == 0) {
9473 out_dynamic_list[i].fd = fd;
9474 out_dynamic_list[i].offset = offset;
9475 out_dynamic_list[i].dup_fd = dup(fd);
9476 out_dynamic_list[i].ref_count++;
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009477 DEBUG_PRINT_LOW("buf_ref_add: [ADDED] fd = %d ref_count = %d",
Arun Menonbdb80b02013-08-12 17:45:54 -07009478 out_dynamic_list[i].fd, out_dynamic_list[i].ref_count);
9479 break;
9480 }
9481 }
9482 }
9483 pthread_mutex_unlock(&m_lock);
9484}
9485
9486void omx_vdec::buf_ref_remove(OMX_U32 fd, OMX_U32 offset)
9487{
9488 int i = 0;
9489 pthread_mutex_lock(&m_lock);
9490 for (i = 0; i < drv_ctx.op_buf.actualcount; i++) {
9491 //check the buffer fd, offset, uv addr with list contents
9492 //If present decrement reference.
9493 if ((out_dynamic_list[i].fd == fd) &&
9494 (out_dynamic_list[i].offset == offset)) {
9495 out_dynamic_list[i].ref_count--;
9496 if (out_dynamic_list[i].ref_count == 0) {
9497 close(out_dynamic_list[i].dup_fd);
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009498 DEBUG_PRINT_LOW("buf_ref_remove: [REMOVED] fd = %d ref_count = %d",
Arun Menonbdb80b02013-08-12 17:45:54 -07009499 out_dynamic_list[i].fd, out_dynamic_list[i].ref_count);
9500 out_dynamic_list[i].dup_fd = 0;
9501 out_dynamic_list[i].fd = 0;
9502 out_dynamic_list[i].offset = 0;
9503 }
9504 break;
9505 }
9506 }
9507 if (i >= drv_ctx.op_buf.actualcount) {
Deva Ramasubramanian43918e22013-10-21 20:04:23 -07009508 DEBUG_PRINT_ERROR("Error - could not remove ref, no match with any entry in list");
Arun Menonbdb80b02013-08-12 17:45:54 -07009509 }
9510 pthread_mutex_unlock(&m_lock);
9511}
Leena Winterrowd974fd1f2013-10-30 10:58:02 -07009512
9513#ifdef _MSM8974_
9514void omx_vdec::send_codec_config() {
9515 if (codec_config_flag) {
9516 unsigned p1 = 0; // Parameter - 1
9517 unsigned p2 = 0; // Parameter - 2
9518 unsigned ident = 0;
9519 pthread_mutex_lock(&m_lock);
9520 DEBUG_PRINT_LOW("\n Check Queue for codec_config buffer \n");
9521 while (m_etb_q.m_size) {
9522 m_etb_q.pop_entry(&p1,&p2,&ident);
9523 if (ident == OMX_COMPONENT_GENERATE_ETB_ARBITRARY) {
9524 if (((OMX_BUFFERHEADERTYPE *)p2)->nFlags & OMX_BUFFERFLAG_CODECCONFIG) {
9525 if (empty_this_buffer_proxy_arbitrary((OMX_HANDLETYPE)p1,\
9526 (OMX_BUFFERHEADERTYPE *)p2) != OMX_ErrorNone) {
9527 DEBUG_PRINT_ERROR("\n empty_this_buffer_proxy_arbitrary failure");
9528 omx_report_error();
9529 }
9530 } else {
9531 DEBUG_PRINT_LOW("\n Flush Input Heap Buffer %p",(OMX_BUFFERHEADERTYPE *)p2);
9532 m_cb.EmptyBufferDone(&m_cmp ,m_app_data, (OMX_BUFFERHEADERTYPE *)p2);
9533 }
9534 } else if (ident == OMX_COMPONENT_GENERATE_ETB) {
9535 if (((OMX_BUFFERHEADERTYPE *)p2)->nFlags & OMX_BUFFERFLAG_CODECCONFIG) {
9536 if (empty_this_buffer_proxy((OMX_HANDLETYPE)p1,\
9537 (OMX_BUFFERHEADERTYPE *)p2) != OMX_ErrorNone) {
9538 DEBUG_PRINT_ERROR("\n empty_this_buffer_proxy failure");
9539 omx_report_error ();
9540 }
9541 } else {
9542 pending_input_buffers++;
9543 DEBUG_PRINT_LOW("\n Flush Input OMX_COMPONENT_GENERATE_ETB %p, pending_input_buffers %d",
9544 (OMX_BUFFERHEADERTYPE *)p2, pending_input_buffers);
9545 empty_buffer_done(&m_cmp,(OMX_BUFFERHEADERTYPE *)p2);
9546 }
9547 } else if (ident == OMX_COMPONENT_GENERATE_EBD) {
9548 DEBUG_PRINT_LOW("\n Flush Input OMX_COMPONENT_GENERATE_EBD %p",
9549 (OMX_BUFFERHEADERTYPE *)p1);
9550 empty_buffer_done(&m_cmp,(OMX_BUFFERHEADERTYPE *)p1);
9551 }
9552 }
9553 pthread_mutex_unlock(&m_lock);
9554 }
9555}
9556#endif