1 /******************************************************************************
2 *
3 * Copyright (C) 2015 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 *****************************************************************************
18 * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20
21 /*****************************************************************************/
22 /* */
23 /* File Name : ih264d_api.c */
24 /* */
25 /* Description : Has all API related functions */
26 /* */
27 /* */
28 /* List of Functions : api_check_struct_sanity */
29 /* ih264d_set_processor */
30 /* ih264d_create */
31 /* ih264d_delete */
32 /* ih264d_init */
33 /* ih264d_map_error */
34 /* ih264d_video_decode */
35 /* ih264d_get_version */
36 /* ih264d_get_display_frame */
37 /* ih264d_set_display_frame */
38 /* ih264d_set_flush_mode */
39 /* ih264d_get_status */
40 /* ih264d_get_buf_info */
41 /* ih264d_set_params */
42 /* ih264d_set_default_params */
43 /* ih264d_reset */
44 /* ih264d_ctl */
45 /* ih264d_rel_display_frame */
46 /* ih264d_set_degrade */
47 /* ih264d_get_frame_dimensions */
48 /* ih264d_set_num_cores */
49 /* ih264d_fill_output_struct_from_context */
50 /* ih264d_api_function */
51 /* */
52 /* Issues / Problems : None */
53 /* */
54 /* Revision History : */
55 /* */
56 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
57 /* 14 10 2008 100356(SKV) Draft */
58 /* */
59 /*****************************************************************************/
60 #include "ih264_typedefs.h"
61 #include "ih264_macros.h"
62 #include "ih264_platform_macros.h"
63 #include "ih264d_tables.h"
64 #include "iv.h"
65 #include "ivd.h"
66 #include "ih264d.h"
67 #include "ih264d_defs.h"
68
69 #include <string.h>
70 #include <limits.h>
71 #include <stddef.h>
72
73 #include "ih264d_inter_pred.h"
74
75 #include "ih264d_structs.h"
76 #include "ih264d_nal.h"
77 #include "ih264d_error_handler.h"
78
79 #include "ih264d_defs.h"
80
81 #include "ithread.h"
82 #include "ih264d_parse_slice.h"
83 #include "ih264d_function_selector.h"
84 #include "ih264_error.h"
85 #include "ih264_disp_mgr.h"
86 #include "ih264_buf_mgr.h"
87 #include "ih264d_deblocking.h"
88 #include "ih264d_parse_cavlc.h"
89 #include "ih264d_parse_cabac.h"
90 #include "ih264d_utils.h"
91 #include "ih264d_format_conv.h"
92 #include "ih264d_parse_headers.h"
93 #include "ih264d_thread_compute_bs.h"
94 #include <assert.h>
95
96
97 /*********************/
98 /* Codec Versioning */
99 /*********************/
100 //Move this to where it is used
101 #define CODEC_NAME "H264VDEC"
102 #define CODEC_RELEASE_TYPE "production"
103 #define CODEC_RELEASE_VER "05.00"
104 #define CODEC_VENDOR "ITTIAM"
105 #define MAXVERSION_STRLEN 511
106 #ifdef __ANDROID__
107 #define VERSION(version_string, codec_name, codec_release_type, codec_release_ver, codec_vendor) \
108 snprintf(version_string, MAXVERSION_STRLEN, \
109 "@(#)Id:%s_%s Ver:%s Released by %s", \
110 codec_name, codec_release_type, codec_release_ver, codec_vendor)
111 #else
112 #define VERSION(version_string, codec_name, codec_release_type, codec_release_ver, codec_vendor) \
113 snprintf(version_string, MAXVERSION_STRLEN, \
114 "@(#)Id:%s_%s Ver:%s Released by %s Build: %s @ %s", \
115 codec_name, codec_release_type, codec_release_ver, codec_vendor, __DATE__, __TIME__)
116 #endif
117
118
119 #define MIN_IN_BUFS 1
120 #define MIN_OUT_BUFS_420 3
121 #define MIN_OUT_BUFS_422ILE 1
122 #define MIN_OUT_BUFS_RGB565 1
123 #define MIN_OUT_BUFS_420SP 2
124
125 #define NUM_FRAMES_LIMIT_ENABLED 0
126
127 #if NUM_FRAMES_LIMIT_ENABLED
128 #define NUM_FRAMES_LIMIT 10000
129 #else
130 #define NUM_FRAMES_LIMIT 0x7FFFFFFF
131 #endif
132
133
134 UWORD32 ih264d_get_extra_mem_external(UWORD32 width, UWORD32 height);
135 WORD32 ih264d_get_frame_dimensions(iv_obj_t *dec_hdl,
136 void *pv_api_ip,
137 void *pv_api_op);
138 WORD32 ih264d_set_num_cores(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op);
139
140 WORD32 ih264d_deblock_display(dec_struct_t *ps_dec);
141
142 void ih264d_signal_decode_thread(dec_struct_t *ps_dec);
143
144 void ih264d_signal_bs_deblk_thread(dec_struct_t *ps_dec);
145 void ih264d_decode_picture_thread(dec_struct_t *ps_dec);
146
147 WORD32 ih264d_set_degrade(iv_obj_t *ps_codec_obj,
148 void *pv_api_ip,
149 void *pv_api_op);
150
151 void ih264d_fill_output_struct_from_context(dec_struct_t *ps_dec,
152 ivd_video_decode_op_t *ps_dec_op);
153
api_check_struct_sanity(iv_obj_t * ps_handle,void * pv_api_ip,void * pv_api_op)154 static IV_API_CALL_STATUS_T api_check_struct_sanity(iv_obj_t *ps_handle,
155 void *pv_api_ip,
156 void *pv_api_op)
157 {
158 IVD_API_COMMAND_TYPE_T e_cmd;
159 UWORD32 *pu4_api_ip;
160 UWORD32 *pu4_api_op;
161 UWORD32 i, j;
162
163 if(NULL == pv_api_op)
164 return (IV_FAIL);
165
166 if(NULL == pv_api_ip)
167 return (IV_FAIL);
168
169 pu4_api_ip = (UWORD32 *)pv_api_ip;
170 pu4_api_op = (UWORD32 *)pv_api_op;
171 e_cmd = *(pu4_api_ip + 1);
172
173 /* error checks on handle */
174 switch((WORD32)e_cmd)
175 {
176 case IVD_CMD_CREATE:
177 break;
178
179 case IVD_CMD_REL_DISPLAY_FRAME:
180 case IVD_CMD_SET_DISPLAY_FRAME:
181 case IVD_CMD_GET_DISPLAY_FRAME:
182 case IVD_CMD_VIDEO_DECODE:
183 case IVD_CMD_DELETE:
184 case IVD_CMD_VIDEO_CTL:
185 if(ps_handle == NULL)
186 {
187 *(pu4_api_op + 1) |= 1 << IVD_UNSUPPORTEDPARAM;
188 *(pu4_api_op + 1) |= IVD_HANDLE_NULL;
189 return IV_FAIL;
190 }
191
192 if(ps_handle->u4_size != sizeof(iv_obj_t))
193 {
194 *(pu4_api_op + 1) |= 1 << IVD_UNSUPPORTEDPARAM;
195 *(pu4_api_op + 1) |= IVD_HANDLE_STRUCT_SIZE_INCORRECT;
196 return IV_FAIL;
197 }
198
199 if(ps_handle->pv_fxns != ih264d_api_function)
200 {
201 *(pu4_api_op + 1) |= 1 << IVD_UNSUPPORTEDPARAM;
202 *(pu4_api_op + 1) |= IVD_INVALID_HANDLE_NULL;
203 return IV_FAIL;
204 }
205
206 if(ps_handle->pv_codec_handle == NULL)
207 {
208 *(pu4_api_op + 1) |= 1 << IVD_UNSUPPORTEDPARAM;
209 *(pu4_api_op + 1) |= IVD_INVALID_HANDLE_NULL;
210 return IV_FAIL;
211 }
212 break;
213 default:
214 *(pu4_api_op + 1) |= 1 << IVD_UNSUPPORTEDPARAM;
215 *(pu4_api_op + 1) |= IVD_INVALID_API_CMD;
216 return IV_FAIL;
217 }
218
219 switch((WORD32)e_cmd)
220 {
221 case IVD_CMD_CREATE:
222 {
223 ih264d_create_ip_t *ps_ip = (ih264d_create_ip_t *)pv_api_ip;
224 ih264d_create_op_t *ps_op = (ih264d_create_op_t *)pv_api_op;
225
226
227 ps_op->s_ivd_create_op_t.u4_error_code = 0;
228
229 if((ps_ip->s_ivd_create_ip_t.u4_size > sizeof(ih264d_create_ip_t))
230 || (ps_ip->s_ivd_create_ip_t.u4_size
231 < sizeof(ivd_create_ip_t)))
232 {
233 ps_op->s_ivd_create_op_t.u4_error_code |= 1
234 << IVD_UNSUPPORTEDPARAM;
235 ps_op->s_ivd_create_op_t.u4_error_code |=
236 IVD_IP_API_STRUCT_SIZE_INCORRECT;
237 H264_DEC_DEBUG_PRINT("\n");
238 return (IV_FAIL);
239 }
240
241 if((ps_op->s_ivd_create_op_t.u4_size != sizeof(ih264d_create_op_t))
242 && (ps_op->s_ivd_create_op_t.u4_size
243 != sizeof(ivd_create_op_t)))
244 {
245 ps_op->s_ivd_create_op_t.u4_error_code |= 1
246 << IVD_UNSUPPORTEDPARAM;
247 ps_op->s_ivd_create_op_t.u4_error_code |=
248 IVD_OP_API_STRUCT_SIZE_INCORRECT;
249 H264_DEC_DEBUG_PRINT("\n");
250 return (IV_FAIL);
251 }
252
253
254 if((ps_ip->s_ivd_create_ip_t.e_output_format != IV_YUV_420P)
255 && (ps_ip->s_ivd_create_ip_t.e_output_format
256 != IV_YUV_422ILE)
257 && (ps_ip->s_ivd_create_ip_t.e_output_format
258 != IV_RGB_565)
259 && (ps_ip->s_ivd_create_ip_t.e_output_format
260 != IV_YUV_420SP_UV)
261 && (ps_ip->s_ivd_create_ip_t.e_output_format
262 != IV_YUV_420SP_VU))
263 {
264 ps_op->s_ivd_create_op_t.u4_error_code |= 1
265 << IVD_UNSUPPORTEDPARAM;
266 ps_op->s_ivd_create_op_t.u4_error_code |=
267 IVD_INIT_DEC_COL_FMT_NOT_SUPPORTED;
268 H264_DEC_DEBUG_PRINT("\n");
269 return (IV_FAIL);
270 }
271
272 }
273 break;
274
275 case IVD_CMD_GET_DISPLAY_FRAME:
276 {
277 ih264d_get_display_frame_ip_t *ps_ip =
278 (ih264d_get_display_frame_ip_t *)pv_api_ip;
279 ih264d_get_display_frame_op_t *ps_op =
280 (ih264d_get_display_frame_op_t *)pv_api_op;
281
282 ps_op->s_ivd_get_display_frame_op_t.u4_error_code = 0;
283
284 if((ps_ip->s_ivd_get_display_frame_ip_t.u4_size
285 != sizeof(ih264d_get_display_frame_ip_t))
286 && (ps_ip->s_ivd_get_display_frame_ip_t.u4_size
287 != sizeof(ivd_get_display_frame_ip_t)))
288 {
289 ps_op->s_ivd_get_display_frame_op_t.u4_error_code |= 1
290 << IVD_UNSUPPORTEDPARAM;
291 ps_op->s_ivd_get_display_frame_op_t.u4_error_code |=
292 IVD_IP_API_STRUCT_SIZE_INCORRECT;
293 return (IV_FAIL);
294 }
295
296 if((ps_op->s_ivd_get_display_frame_op_t.u4_size
297 != sizeof(ih264d_get_display_frame_op_t))
298 && (ps_op->s_ivd_get_display_frame_op_t.u4_size
299 != sizeof(ivd_get_display_frame_op_t)))
300 {
301 ps_op->s_ivd_get_display_frame_op_t.u4_error_code |= 1
302 << IVD_UNSUPPORTEDPARAM;
303 ps_op->s_ivd_get_display_frame_op_t.u4_error_code |=
304 IVD_OP_API_STRUCT_SIZE_INCORRECT;
305 return (IV_FAIL);
306 }
307 }
308 break;
309
310 case IVD_CMD_REL_DISPLAY_FRAME:
311 {
312 ih264d_rel_display_frame_ip_t *ps_ip =
313 (ih264d_rel_display_frame_ip_t *)pv_api_ip;
314 ih264d_rel_display_frame_op_t *ps_op =
315 (ih264d_rel_display_frame_op_t *)pv_api_op;
316
317 ps_op->s_ivd_rel_display_frame_op_t.u4_error_code = 0;
318
319 if((ps_ip->s_ivd_rel_display_frame_ip_t.u4_size
320 != sizeof(ih264d_rel_display_frame_ip_t))
321 && (ps_ip->s_ivd_rel_display_frame_ip_t.u4_size
322 != sizeof(ivd_rel_display_frame_ip_t)))
323 {
324 ps_op->s_ivd_rel_display_frame_op_t.u4_error_code |= 1
325 << IVD_UNSUPPORTEDPARAM;
326 ps_op->s_ivd_rel_display_frame_op_t.u4_error_code |=
327 IVD_IP_API_STRUCT_SIZE_INCORRECT;
328 return (IV_FAIL);
329 }
330
331 if((ps_op->s_ivd_rel_display_frame_op_t.u4_size
332 != sizeof(ih264d_rel_display_frame_op_t))
333 && (ps_op->s_ivd_rel_display_frame_op_t.u4_size
334 != sizeof(ivd_rel_display_frame_op_t)))
335 {
336 ps_op->s_ivd_rel_display_frame_op_t.u4_error_code |= 1
337 << IVD_UNSUPPORTEDPARAM;
338 ps_op->s_ivd_rel_display_frame_op_t.u4_error_code |=
339 IVD_OP_API_STRUCT_SIZE_INCORRECT;
340 return (IV_FAIL);
341 }
342
343 }
344 break;
345
346 case IVD_CMD_SET_DISPLAY_FRAME:
347 {
348 ih264d_set_display_frame_ip_t *ps_ip =
349 (ih264d_set_display_frame_ip_t *)pv_api_ip;
350 ih264d_set_display_frame_op_t *ps_op =
351 (ih264d_set_display_frame_op_t *)pv_api_op;
352 UWORD32 j;
353
354 ps_op->s_ivd_set_display_frame_op_t.u4_error_code = 0;
355
356 if((ps_ip->s_ivd_set_display_frame_ip_t.u4_size
357 != sizeof(ih264d_set_display_frame_ip_t))
358 && (ps_ip->s_ivd_set_display_frame_ip_t.u4_size
359 != sizeof(ivd_set_display_frame_ip_t)))
360 {
361 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |= 1
362 << IVD_UNSUPPORTEDPARAM;
363 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |=
364 IVD_IP_API_STRUCT_SIZE_INCORRECT;
365 return (IV_FAIL);
366 }
367
368 if((ps_op->s_ivd_set_display_frame_op_t.u4_size
369 != sizeof(ih264d_set_display_frame_op_t))
370 && (ps_op->s_ivd_set_display_frame_op_t.u4_size
371 != sizeof(ivd_set_display_frame_op_t)))
372 {
373 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |= 1
374 << IVD_UNSUPPORTEDPARAM;
375 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |=
376 IVD_OP_API_STRUCT_SIZE_INCORRECT;
377 return (IV_FAIL);
378 }
379
380 if(ps_ip->s_ivd_set_display_frame_ip_t.num_disp_bufs == 0)
381 {
382 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |= 1
383 << IVD_UNSUPPORTEDPARAM;
384 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |=
385 IVD_DISP_FRM_ZERO_OP_BUFS;
386 return IV_FAIL;
387 }
388
389 for(j = 0; j < ps_ip->s_ivd_set_display_frame_ip_t.num_disp_bufs;
390 j++)
391 {
392 if(ps_ip->s_ivd_set_display_frame_ip_t.s_disp_buffer[j].u4_num_bufs
393 == 0)
394 {
395 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |= 1
396 << IVD_UNSUPPORTEDPARAM;
397 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |=
398 IVD_DISP_FRM_ZERO_OP_BUFS;
399 return IV_FAIL;
400 }
401
402 for(i = 0;
403 i
404 < ps_ip->s_ivd_set_display_frame_ip_t.s_disp_buffer[j].u4_num_bufs;
405 i++)
406 {
407 if(ps_ip->s_ivd_set_display_frame_ip_t.s_disp_buffer[j].pu1_bufs[i]
408 == NULL)
409 {
410 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |= 1
411 << IVD_UNSUPPORTEDPARAM;
412 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |=
413 IVD_DISP_FRM_OP_BUF_NULL;
414 return IV_FAIL;
415 }
416
417 if(ps_ip->s_ivd_set_display_frame_ip_t.s_disp_buffer[j].u4_min_out_buf_size[i]
418 == 0)
419 {
420 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |= 1
421 << IVD_UNSUPPORTEDPARAM;
422 ps_op->s_ivd_set_display_frame_op_t.u4_error_code |=
423 IVD_DISP_FRM_ZERO_OP_BUF_SIZE;
424 return IV_FAIL;
425 }
426 }
427 }
428 }
429 break;
430
431 case IVD_CMD_VIDEO_DECODE:
432 {
433 ih264d_video_decode_ip_t *ps_ip =
434 (ih264d_video_decode_ip_t *)pv_api_ip;
435 ih264d_video_decode_op_t *ps_op =
436 (ih264d_video_decode_op_t *)pv_api_op;
437
438 H264_DEC_DEBUG_PRINT("The input bytes is: %d",
439 ps_ip->s_ivd_video_decode_ip_t.u4_num_Bytes);
440 ps_op->s_ivd_video_decode_op_t.u4_error_code = 0;
441
442 if(ps_ip->s_ivd_video_decode_ip_t.u4_size
443 != sizeof(ih264d_video_decode_ip_t)&&
444 ps_ip->s_ivd_video_decode_ip_t.u4_size != offsetof(ivd_video_decode_ip_t, s_out_buffer))
445 {
446 ps_op->s_ivd_video_decode_op_t.u4_error_code |= 1
447 << IVD_UNSUPPORTEDPARAM;
448 ps_op->s_ivd_video_decode_op_t.u4_error_code |=
449 IVD_IP_API_STRUCT_SIZE_INCORRECT;
450 return (IV_FAIL);
451 }
452
453 if(ps_op->s_ivd_video_decode_op_t.u4_size
454 != sizeof(ih264d_video_decode_op_t)&&
455 ps_op->s_ivd_video_decode_op_t.u4_size != offsetof(ivd_video_decode_op_t, u4_output_present))
456 {
457 ps_op->s_ivd_video_decode_op_t.u4_error_code |= 1
458 << IVD_UNSUPPORTEDPARAM;
459 ps_op->s_ivd_video_decode_op_t.u4_error_code |=
460 IVD_OP_API_STRUCT_SIZE_INCORRECT;
461 return (IV_FAIL);
462 }
463
464 }
465 break;
466
467 case IVD_CMD_DELETE:
468 {
469 ih264d_delete_ip_t *ps_ip =
470 (ih264d_delete_ip_t *)pv_api_ip;
471 ih264d_delete_op_t *ps_op =
472 (ih264d_delete_op_t *)pv_api_op;
473
474 ps_op->s_ivd_delete_op_t.u4_error_code = 0;
475
476 if(ps_ip->s_ivd_delete_ip_t.u4_size
477 != sizeof(ih264d_delete_ip_t))
478 {
479 ps_op->s_ivd_delete_op_t.u4_error_code |= 1
480 << IVD_UNSUPPORTEDPARAM;
481 ps_op->s_ivd_delete_op_t.u4_error_code |=
482 IVD_IP_API_STRUCT_SIZE_INCORRECT;
483 return (IV_FAIL);
484 }
485
486 if(ps_op->s_ivd_delete_op_t.u4_size
487 != sizeof(ih264d_delete_op_t))
488 {
489 ps_op->s_ivd_delete_op_t.u4_error_code |= 1
490 << IVD_UNSUPPORTEDPARAM;
491 ps_op->s_ivd_delete_op_t.u4_error_code |=
492 IVD_OP_API_STRUCT_SIZE_INCORRECT;
493 return (IV_FAIL);
494 }
495
496 }
497 break;
498
499 case IVD_CMD_VIDEO_CTL:
500 {
501 UWORD32 *pu4_ptr_cmd;
502 UWORD32 sub_command;
503
504 pu4_ptr_cmd = (UWORD32 *)pv_api_ip;
505 pu4_ptr_cmd += 2;
506 sub_command = *pu4_ptr_cmd;
507
508 switch(sub_command)
509 {
510 case IVD_CMD_CTL_SETPARAMS:
511 {
512 ih264d_ctl_set_config_ip_t *ps_ip;
513 ih264d_ctl_set_config_op_t *ps_op;
514 ps_ip = (ih264d_ctl_set_config_ip_t *)pv_api_ip;
515 ps_op = (ih264d_ctl_set_config_op_t *)pv_api_op;
516
517 if(ps_ip->s_ivd_ctl_set_config_ip_t.u4_size
518 != sizeof(ih264d_ctl_set_config_ip_t))
519 {
520 ps_op->s_ivd_ctl_set_config_op_t.u4_error_code |= 1
521 << IVD_UNSUPPORTEDPARAM;
522 ps_op->s_ivd_ctl_set_config_op_t.u4_error_code |=
523 IVD_IP_API_STRUCT_SIZE_INCORRECT;
524 return IV_FAIL;
525 }
526 }
527 //no break; is needed here
528 case IVD_CMD_CTL_SETDEFAULT:
529 {
530 ih264d_ctl_set_config_op_t *ps_op;
531 ps_op = (ih264d_ctl_set_config_op_t *)pv_api_op;
532 if(ps_op->s_ivd_ctl_set_config_op_t.u4_size
533 != sizeof(ih264d_ctl_set_config_op_t))
534 {
535 ps_op->s_ivd_ctl_set_config_op_t.u4_error_code |= 1
536 << IVD_UNSUPPORTEDPARAM;
537 ps_op->s_ivd_ctl_set_config_op_t.u4_error_code |=
538 IVD_OP_API_STRUCT_SIZE_INCORRECT;
539 return IV_FAIL;
540 }
541 }
542 break;
543
544 case IVD_CMD_CTL_GETPARAMS:
545 {
546 ih264d_ctl_getstatus_ip_t *ps_ip;
547 ih264d_ctl_getstatus_op_t *ps_op;
548
549 ps_ip = (ih264d_ctl_getstatus_ip_t *)pv_api_ip;
550 ps_op = (ih264d_ctl_getstatus_op_t *)pv_api_op;
551 if(ps_ip->s_ivd_ctl_getstatus_ip_t.u4_size
552 != sizeof(ih264d_ctl_getstatus_ip_t))
553 {
554 ps_op->s_ivd_ctl_getstatus_op_t.u4_error_code |= 1
555 << IVD_UNSUPPORTEDPARAM;
556 ps_op->s_ivd_ctl_getstatus_op_t.u4_error_code |=
557 IVD_IP_API_STRUCT_SIZE_INCORRECT;
558 return IV_FAIL;
559 }
560 if(ps_op->s_ivd_ctl_getstatus_op_t.u4_size
561 != sizeof(ih264d_ctl_getstatus_op_t))
562 {
563 ps_op->s_ivd_ctl_getstatus_op_t.u4_error_code |= 1
564 << IVD_UNSUPPORTEDPARAM;
565 ps_op->s_ivd_ctl_getstatus_op_t.u4_error_code |=
566 IVD_OP_API_STRUCT_SIZE_INCORRECT;
567 return IV_FAIL;
568 }
569 }
570 break;
571
572 case IVD_CMD_CTL_GETBUFINFO:
573 {
574 ih264d_ctl_getbufinfo_ip_t *ps_ip;
575 ih264d_ctl_getbufinfo_op_t *ps_op;
576 ps_ip = (ih264d_ctl_getbufinfo_ip_t *)pv_api_ip;
577 ps_op = (ih264d_ctl_getbufinfo_op_t *)pv_api_op;
578
579 if(ps_ip->s_ivd_ctl_getbufinfo_ip_t.u4_size
580 != sizeof(ih264d_ctl_getbufinfo_ip_t))
581 {
582 ps_op->s_ivd_ctl_getbufinfo_op_t.u4_error_code |= 1
583 << IVD_UNSUPPORTEDPARAM;
584 ps_op->s_ivd_ctl_getbufinfo_op_t.u4_error_code |=
585 IVD_IP_API_STRUCT_SIZE_INCORRECT;
586 return IV_FAIL;
587 }
588 if(ps_op->s_ivd_ctl_getbufinfo_op_t.u4_size
589 != sizeof(ih264d_ctl_getbufinfo_op_t))
590 {
591 ps_op->s_ivd_ctl_getbufinfo_op_t.u4_error_code |= 1
592 << IVD_UNSUPPORTEDPARAM;
593 ps_op->s_ivd_ctl_getbufinfo_op_t.u4_error_code |=
594 IVD_OP_API_STRUCT_SIZE_INCORRECT;
595 return IV_FAIL;
596 }
597 }
598 break;
599
600 case IVD_CMD_CTL_GETVERSION:
601 {
602 ih264d_ctl_getversioninfo_ip_t *ps_ip;
603 ih264d_ctl_getversioninfo_op_t *ps_op;
604 ps_ip = (ih264d_ctl_getversioninfo_ip_t *)pv_api_ip;
605 ps_op = (ih264d_ctl_getversioninfo_op_t *)pv_api_op;
606 if(ps_ip->s_ivd_ctl_getversioninfo_ip_t.u4_size
607 != sizeof(ih264d_ctl_getversioninfo_ip_t))
608 {
609 ps_op->s_ivd_ctl_getversioninfo_op_t.u4_error_code |= 1
610 << IVD_UNSUPPORTEDPARAM;
611 ps_op->s_ivd_ctl_getversioninfo_op_t.u4_error_code |=
612 IVD_IP_API_STRUCT_SIZE_INCORRECT;
613 return IV_FAIL;
614 }
615 if(ps_op->s_ivd_ctl_getversioninfo_op_t.u4_size
616 != sizeof(ih264d_ctl_getversioninfo_op_t))
617 {
618 ps_op->s_ivd_ctl_getversioninfo_op_t.u4_error_code |= 1
619 << IVD_UNSUPPORTEDPARAM;
620 ps_op->s_ivd_ctl_getversioninfo_op_t.u4_error_code |=
621 IVD_OP_API_STRUCT_SIZE_INCORRECT;
622 return IV_FAIL;
623 }
624 }
625 break;
626
627 case IVD_CMD_CTL_FLUSH:
628 {
629 ih264d_ctl_flush_ip_t *ps_ip;
630 ih264d_ctl_flush_op_t *ps_op;
631 ps_ip = (ih264d_ctl_flush_ip_t *)pv_api_ip;
632 ps_op = (ih264d_ctl_flush_op_t *)pv_api_op;
633 if(ps_ip->s_ivd_ctl_flush_ip_t.u4_size
634 != sizeof(ih264d_ctl_flush_ip_t))
635 {
636 ps_op->s_ivd_ctl_flush_op_t.u4_error_code |= 1
637 << IVD_UNSUPPORTEDPARAM;
638 ps_op->s_ivd_ctl_flush_op_t.u4_error_code |=
639 IVD_IP_API_STRUCT_SIZE_INCORRECT;
640 return IV_FAIL;
641 }
642 if(ps_op->s_ivd_ctl_flush_op_t.u4_size
643 != sizeof(ih264d_ctl_flush_op_t))
644 {
645 ps_op->s_ivd_ctl_flush_op_t.u4_error_code |= 1
646 << IVD_UNSUPPORTEDPARAM;
647 ps_op->s_ivd_ctl_flush_op_t.u4_error_code |=
648 IVD_OP_API_STRUCT_SIZE_INCORRECT;
649 return IV_FAIL;
650 }
651 }
652 break;
653
654 case IVD_CMD_CTL_RESET:
655 {
656 ih264d_ctl_reset_ip_t *ps_ip;
657 ih264d_ctl_reset_op_t *ps_op;
658 ps_ip = (ih264d_ctl_reset_ip_t *)pv_api_ip;
659 ps_op = (ih264d_ctl_reset_op_t *)pv_api_op;
660 if(ps_ip->s_ivd_ctl_reset_ip_t.u4_size
661 != sizeof(ih264d_ctl_reset_ip_t))
662 {
663 ps_op->s_ivd_ctl_reset_op_t.u4_error_code |= 1
664 << IVD_UNSUPPORTEDPARAM;
665 ps_op->s_ivd_ctl_reset_op_t.u4_error_code |=
666 IVD_IP_API_STRUCT_SIZE_INCORRECT;
667 return IV_FAIL;
668 }
669 if(ps_op->s_ivd_ctl_reset_op_t.u4_size
670 != sizeof(ih264d_ctl_reset_op_t))
671 {
672 ps_op->s_ivd_ctl_reset_op_t.u4_error_code |= 1
673 << IVD_UNSUPPORTEDPARAM;
674 ps_op->s_ivd_ctl_reset_op_t.u4_error_code |=
675 IVD_OP_API_STRUCT_SIZE_INCORRECT;
676 return IV_FAIL;
677 }
678 }
679 break;
680
681 case IH264D_CMD_CTL_DEGRADE:
682 {
683 ih264d_ctl_degrade_ip_t *ps_ip;
684 ih264d_ctl_degrade_op_t *ps_op;
685
686 ps_ip = (ih264d_ctl_degrade_ip_t *)pv_api_ip;
687 ps_op = (ih264d_ctl_degrade_op_t *)pv_api_op;
688
689 if(ps_ip->u4_size != sizeof(ih264d_ctl_degrade_ip_t))
690 {
691 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
692 ps_op->u4_error_code |=
693 IVD_IP_API_STRUCT_SIZE_INCORRECT;
694 return IV_FAIL;
695 }
696
697 if(ps_op->u4_size != sizeof(ih264d_ctl_degrade_op_t))
698 {
699 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
700 ps_op->u4_error_code |=
701 IVD_OP_API_STRUCT_SIZE_INCORRECT;
702 return IV_FAIL;
703 }
704
705 if((ps_ip->i4_degrade_pics < 0)
706 || (ps_ip->i4_degrade_pics > 4)
707 || (ps_ip->i4_nondegrade_interval < 0)
708 || (ps_ip->i4_degrade_type < 0)
709 || (ps_ip->i4_degrade_type > 15))
710 {
711 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
712 return IV_FAIL;
713 }
714
715 break;
716 }
717
718 case IH264D_CMD_CTL_GET_BUFFER_DIMENSIONS:
719 {
720 ih264d_ctl_get_frame_dimensions_ip_t *ps_ip;
721 ih264d_ctl_get_frame_dimensions_op_t *ps_op;
722
723 ps_ip = (ih264d_ctl_get_frame_dimensions_ip_t *)pv_api_ip;
724 ps_op = (ih264d_ctl_get_frame_dimensions_op_t *)pv_api_op;
725
726 if(ps_ip->u4_size
727 != sizeof(ih264d_ctl_get_frame_dimensions_ip_t))
728 {
729 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
730 ps_op->u4_error_code |=
731 IVD_IP_API_STRUCT_SIZE_INCORRECT;
732 return IV_FAIL;
733 }
734
735 if(ps_op->u4_size
736 != sizeof(ih264d_ctl_get_frame_dimensions_op_t))
737 {
738 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
739 ps_op->u4_error_code |=
740 IVD_OP_API_STRUCT_SIZE_INCORRECT;
741 return IV_FAIL;
742 }
743
744 break;
745 }
746
747 case IH264D_CMD_CTL_SET_NUM_CORES:
748 {
749 ih264d_ctl_set_num_cores_ip_t *ps_ip;
750 ih264d_ctl_set_num_cores_op_t *ps_op;
751
752 ps_ip = (ih264d_ctl_set_num_cores_ip_t *)pv_api_ip;
753 ps_op = (ih264d_ctl_set_num_cores_op_t *)pv_api_op;
754
755 if(ps_ip->u4_size != sizeof(ih264d_ctl_set_num_cores_ip_t))
756 {
757 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
758 ps_op->u4_error_code |=
759 IVD_IP_API_STRUCT_SIZE_INCORRECT;
760 return IV_FAIL;
761 }
762
763 if(ps_op->u4_size != sizeof(ih264d_ctl_set_num_cores_op_t))
764 {
765 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
766 ps_op->u4_error_code |=
767 IVD_OP_API_STRUCT_SIZE_INCORRECT;
768 return IV_FAIL;
769 }
770
771 if((ps_ip->u4_num_cores != 1) && (ps_ip->u4_num_cores != 2)
772 && (ps_ip->u4_num_cores != 3)
773 && (ps_ip->u4_num_cores != 4))
774 {
775 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
776 return IV_FAIL;
777 }
778 break;
779 }
780 case IH264D_CMD_CTL_SET_PROCESSOR:
781 {
782 ih264d_ctl_set_processor_ip_t *ps_ip;
783 ih264d_ctl_set_processor_op_t *ps_op;
784
785 ps_ip = (ih264d_ctl_set_processor_ip_t *)pv_api_ip;
786 ps_op = (ih264d_ctl_set_processor_op_t *)pv_api_op;
787
788 if(ps_ip->u4_size != sizeof(ih264d_ctl_set_processor_ip_t))
789 {
790 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
791 ps_op->u4_error_code |=
792 IVD_IP_API_STRUCT_SIZE_INCORRECT;
793 return IV_FAIL;
794 }
795
796 if(ps_op->u4_size != sizeof(ih264d_ctl_set_processor_op_t))
797 {
798 ps_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
799 ps_op->u4_error_code |=
800 IVD_OP_API_STRUCT_SIZE_INCORRECT;
801 return IV_FAIL;
802 }
803
804 break;
805 }
806 default:
807 *(pu4_api_op + 1) |= 1 << IVD_UNSUPPORTEDPARAM;
808 *(pu4_api_op + 1) |= IVD_UNSUPPORTED_API_CMD;
809 return IV_FAIL;
810 break;
811 }
812 }
813 break;
814 }
815
816 return IV_SUCCESS;
817 }
818
819
820 /**
821 *******************************************************************************
822 *
823 * @brief
824 * Sets Processor type
825 *
826 * @par Description:
827 * Sets Processor type
828 *
829 * @param[in] ps_codec_obj
830 * Pointer to codec object at API level
831 *
832 * @param[in] pv_api_ip
833 * Pointer to input argument structure
834 *
835 * @param[out] pv_api_op
836 * Pointer to output argument structure
837 *
838 * @returns Status
839 *
840 * @remarks
841 *
842 *
843 *******************************************************************************
844 */
845
ih264d_set_processor(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)846 WORD32 ih264d_set_processor(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
847 {
848 ih264d_ctl_set_processor_ip_t *ps_ip;
849 ih264d_ctl_set_processor_op_t *ps_op;
850 dec_struct_t *ps_codec = (dec_struct_t *)dec_hdl->pv_codec_handle;
851
852 ps_ip = (ih264d_ctl_set_processor_ip_t *)pv_api_ip;
853 ps_op = (ih264d_ctl_set_processor_op_t *)pv_api_op;
854
855 ps_codec->e_processor_arch = (IVD_ARCH_T)ps_ip->u4_arch;
856 ps_codec->e_processor_soc = (IVD_SOC_T)ps_ip->u4_soc;
857
858 ih264d_init_function_ptr(ps_codec);
859
860 ps_op->u4_error_code = 0;
861 return IV_SUCCESS;
862 }
863
864
865 /**************************************************************************
866 * \if Function name : ih264d_init_decoder \endif
867 *
868 *
869 * \brief
870 * Initializes the decoder
871 *
872 * \param apiVersion : Version of the api being used.
873 * \param errorHandlingMechanism : Mechanism to be used for errror handling.
874 * \param postFilteringType: Type of post filtering operation to be used.
875 * \param uc_outputFormat: Format of the decoded picture [default 4:2:0].
876 * \param uc_dispBufs: Number of Display Buffers.
877 * \param p_NALBufAPI: Pointer to NAL Buffer API.
878 * \param p_DispBufAPI: Pointer to Display Buffer API.
879 * \param ih264d_dec_mem_manager :Pointer to the function that will be called by decoder
880 * for memory allocation and freeing.
881 *
882 * \return
883 * 0 on Success and -1 on error
884 *
885 **************************************************************************
886 */
ih264d_init_decoder(void * ps_dec_params)887 void ih264d_init_decoder(void * ps_dec_params)
888 {
889 dec_struct_t * ps_dec = (dec_struct_t *)ps_dec_params;
890 dec_slice_params_t *ps_cur_slice;
891 pocstruct_t *ps_prev_poc, *ps_cur_poc;
892 WORD32 size;
893
894 size = sizeof(pred_info_t) * 2 * 32;
895 memset(ps_dec->ps_pred, 0 , size);
896
897 size = sizeof(disp_mgr_t);
898 memset(ps_dec->pv_disp_buf_mgr, 0 , size);
899
900 size = sizeof(buf_mgr_t) + ithread_get_mutex_lock_size();
901 memset(ps_dec->pv_pic_buf_mgr, 0, size);
902
903 size = sizeof(dec_err_status_t);
904 memset(ps_dec->ps_dec_err_status, 0, size);
905
906 size = sizeof(sei);
907 memset(ps_dec->ps_sei, 0, size);
908
909 size = sizeof(dpb_commands_t);
910 memset(ps_dec->ps_dpb_cmds, 0, size);
911
912 size = sizeof(dec_bit_stream_t);
913 memset(ps_dec->ps_bitstrm, 0, size);
914
915 size = sizeof(dec_slice_params_t);
916 memset(ps_dec->ps_cur_slice, 0, size);
917
918 size = MAX(sizeof(dec_seq_params_t), sizeof(dec_pic_params_t));
919 memset(ps_dec->pv_scratch_sps_pps, 0, size);
920
921 size = sizeof(ctxt_inc_mb_info_t);
922 memset(ps_dec->ps_left_mb_ctxt_info, 0, size);
923
924 size = (sizeof(neighbouradd_t) << 2);
925 memset(ps_dec->ps_left_mvpred_addr, 0 ,size);
926
927 size = sizeof(buf_mgr_t) + ithread_get_mutex_lock_size();
928 memset(ps_dec->pv_mv_buf_mgr, 0, size);
929
930 /* Free any dynamic buffers that are allocated */
931 ih264d_free_dynamic_bufs(ps_dec);
932
933 ps_cur_slice = ps_dec->ps_cur_slice;
934 ps_dec->init_done = 0;
935
936 ps_dec->u4_num_cores = 1;
937
938 ps_dec->u2_pic_ht = ps_dec->u2_pic_wd = 0;
939
940 ps_dec->u1_separate_parse = DEFAULT_SEPARATE_PARSE;
941 ps_dec->u4_app_disable_deblk_frm = 0;
942 ps_dec->i4_degrade_type = 0;
943 ps_dec->i4_degrade_pics = 0;
944
945 ps_dec->i4_app_skip_mode = IVD_SKIP_NONE;
946 ps_dec->i4_dec_skip_mode = IVD_SKIP_NONE;
947
948 memset(ps_dec->ps_pps, 0,
949 ((sizeof(dec_pic_params_t)) * MAX_NUM_PIC_PARAMS));
950 memset(ps_dec->ps_sps, 0,
951 ((sizeof(dec_seq_params_t)) * MAX_NUM_SEQ_PARAMS));
952
953 /* Initialization of function pointers ih264d_deblock_picture function*/
954
955 ps_dec->p_DeblockPicture[0] = ih264d_deblock_picture_non_mbaff;
956 ps_dec->p_DeblockPicture[1] = ih264d_deblock_picture_mbaff;
957
958 ps_dec->s_cab_dec_env.pv_codec_handle = ps_dec;
959
960 ps_dec->u4_num_fld_in_frm = 0;
961
962 ps_dec->ps_dpb_mgr->pv_codec_handle = ps_dec;
963
964 /* Initialize the sei validity u4_flag with zero indiacting sei is not valid*/
965 ps_dec->ps_sei->u1_is_valid = 0;
966
967 /* decParams Initializations */
968 ps_dec->ps_cur_pps = NULL;
969 ps_dec->ps_cur_sps = NULL;
970 ps_dec->u1_init_dec_flag = 0;
971 ps_dec->u1_first_slice_in_stream = 1;
972 ps_dec->u1_first_pb_nal_in_pic = 1;
973 ps_dec->u1_last_pic_not_decoded = 0;
974 ps_dec->u4_app_disp_width = 0;
975 ps_dec->i4_header_decoded = 0;
976 ps_dec->u4_total_frames_decoded = 0;
977
978 ps_dec->i4_error_code = 0;
979 ps_dec->i4_content_type = -1;
980 ps_dec->ps_cur_slice->u1_mbaff_frame_flag = 0;
981
982 ps_dec->ps_dec_err_status->u1_err_flag = ACCEPT_ALL_PICS; //REJECT_PB_PICS;
983 ps_dec->ps_dec_err_status->u1_cur_pic_type = PIC_TYPE_UNKNOWN;
984 ps_dec->ps_dec_err_status->u4_frm_sei_sync = SYNC_FRM_DEFAULT;
985 ps_dec->ps_dec_err_status->u4_cur_frm = INIT_FRAME;
986 ps_dec->ps_dec_err_status->u1_pic_aud_i = PIC_TYPE_UNKNOWN;
987
988 ps_dec->u1_pr_sl_type = 0xFF;
989 ps_dec->u2_mbx = 0xffff;
990 ps_dec->u2_mby = 0;
991 ps_dec->u2_total_mbs_coded = 0;
992
993 /* POC initializations */
994 ps_prev_poc = &ps_dec->s_prev_pic_poc;
995 ps_cur_poc = &ps_dec->s_cur_pic_poc;
996 ps_prev_poc->i4_pic_order_cnt_lsb = ps_cur_poc->i4_pic_order_cnt_lsb = 0;
997 ps_prev_poc->i4_pic_order_cnt_msb = ps_cur_poc->i4_pic_order_cnt_msb = 0;
998 ps_prev_poc->i4_delta_pic_order_cnt_bottom =
999 ps_cur_poc->i4_delta_pic_order_cnt_bottom = 0;
1000 ps_prev_poc->i4_delta_pic_order_cnt[0] =
1001 ps_cur_poc->i4_delta_pic_order_cnt[0] = 0;
1002 ps_prev_poc->i4_delta_pic_order_cnt[1] =
1003 ps_cur_poc->i4_delta_pic_order_cnt[1] = 0;
1004 ps_prev_poc->u1_mmco_equalto5 = ps_cur_poc->u1_mmco_equalto5 = 0;
1005 ps_prev_poc->i4_top_field_order_count = ps_cur_poc->i4_top_field_order_count =
1006 0;
1007 ps_prev_poc->i4_bottom_field_order_count =
1008 ps_cur_poc->i4_bottom_field_order_count = 0;
1009 ps_prev_poc->u1_bot_field = ps_cur_poc->u1_bot_field = 0;
1010 ps_prev_poc->u1_mmco_equalto5 = ps_cur_poc->u1_mmco_equalto5 = 0;
1011 ps_prev_poc->i4_prev_frame_num_ofst = ps_cur_poc->i4_prev_frame_num_ofst = 0;
1012 ps_cur_slice->u1_mmco_equalto5 = 0;
1013 ps_cur_slice->u2_frame_num = 0;
1014
1015 ps_dec->i4_max_poc = 0;
1016 ps_dec->i4_prev_max_display_seq = 0;
1017 ps_dec->u1_recon_mb_grp = 4;
1018
1019 /* Field PIC initializations */
1020 ps_dec->u1_second_field = 0;
1021 ps_dec->s_prev_seq_params.u1_eoseq_pending = 0;
1022
1023 /* Set the cropping parameters as zero */
1024 ps_dec->u2_crop_offset_y = 0;
1025 ps_dec->u2_crop_offset_uv = 0;
1026
1027 /* The Initial Frame Rate Info is not Present */
1028 ps_dec->i4_vui_frame_rate = -1;
1029 ps_dec->i4_pic_type = -1;
1030 ps_dec->i4_frametype = -1;
1031 ps_dec->i4_content_type = -1;
1032
1033 ps_dec->u1_res_changed = 0;
1034
1035
1036 ps_dec->u1_frame_decoded_flag = 0;
1037
1038 /* Set the default frame seek mask mode */
1039 ps_dec->u4_skip_frm_mask = SKIP_NONE;
1040
1041 /********************************************************/
1042 /* Initialize CAVLC residual decoding function pointers */
1043 /********************************************************/
1044 ps_dec->pf_cavlc_4x4res_block[0] = ih264d_cavlc_4x4res_block_totalcoeff_1;
1045 ps_dec->pf_cavlc_4x4res_block[1] =
1046 ih264d_cavlc_4x4res_block_totalcoeff_2to10;
1047 ps_dec->pf_cavlc_4x4res_block[2] =
1048 ih264d_cavlc_4x4res_block_totalcoeff_11to16;
1049
1050 ps_dec->pf_cavlc_parse4x4coeff[0] = ih264d_cavlc_parse4x4coeff_n0to7;
1051 ps_dec->pf_cavlc_parse4x4coeff[1] = ih264d_cavlc_parse4x4coeff_n8;
1052
1053 ps_dec->pf_cavlc_parse_8x8block[0] =
1054 ih264d_cavlc_parse_8x8block_none_available;
1055 ps_dec->pf_cavlc_parse_8x8block[1] =
1056 ih264d_cavlc_parse_8x8block_left_available;
1057 ps_dec->pf_cavlc_parse_8x8block[2] =
1058 ih264d_cavlc_parse_8x8block_top_available;
1059 ps_dec->pf_cavlc_parse_8x8block[3] =
1060 ih264d_cavlc_parse_8x8block_both_available;
1061
1062 /***************************************************************************/
1063 /* Initialize Bs calculation function pointers for P and B, 16x16/non16x16 */
1064 /***************************************************************************/
1065 ps_dec->pf_fill_bs1[0][0] = ih264d_fill_bs1_16x16mb_pslice;
1066 ps_dec->pf_fill_bs1[0][1] = ih264d_fill_bs1_non16x16mb_pslice;
1067
1068 ps_dec->pf_fill_bs1[1][0] = ih264d_fill_bs1_16x16mb_bslice;
1069 ps_dec->pf_fill_bs1[1][1] = ih264d_fill_bs1_non16x16mb_bslice;
1070
1071 ps_dec->pf_fill_bs_xtra_left_edge[0] =
1072 ih264d_fill_bs_xtra_left_edge_cur_frm;
1073 ps_dec->pf_fill_bs_xtra_left_edge[1] =
1074 ih264d_fill_bs_xtra_left_edge_cur_fld;
1075
1076 /* Initialize Reference Pic Buffers */
1077 ih264d_init_ref_bufs(ps_dec->ps_dpb_mgr);
1078
1079 ps_dec->u2_prv_frame_num = 0;
1080 ps_dec->u1_top_bottom_decoded = 0;
1081 ps_dec->u1_dangling_field = 0;
1082
1083 ps_dec->s_cab_dec_env.cabac_table = gau4_ih264d_cabac_table;
1084
1085 ps_dec->pu1_left_mv_ctxt_inc = ps_dec->u1_left_mv_ctxt_inc_arr[0];
1086 ps_dec->pi1_left_ref_idx_ctxt_inc =
1087 &ps_dec->i1_left_ref_idx_ctx_inc_arr[0][0];
1088 ps_dec->pu1_left_yuv_dc_csbp = &ps_dec->u1_yuv_dc_csbp_topmb;
1089
1090 /* ! */
1091 /* Initializing flush frame u4_flag */
1092 ps_dec->u1_flushfrm = 0;
1093
1094 {
1095 ps_dec->s_cab_dec_env.pv_codec_handle = (void*)ps_dec;
1096 ps_dec->ps_bitstrm->pv_codec_handle = (void*)ps_dec;
1097 ps_dec->ps_cur_slice->pv_codec_handle = (void*)ps_dec;
1098 ps_dec->ps_dpb_mgr->pv_codec_handle = (void*)ps_dec;
1099 }
1100
1101 memset(ps_dec->disp_bufs, 0, (MAX_DISP_BUFS_NEW) * sizeof(disp_buf_t));
1102 memset(ps_dec->u4_disp_buf_mapping, 0,
1103 (MAX_DISP_BUFS_NEW) * sizeof(UWORD32));
1104 memset(ps_dec->u4_disp_buf_to_be_freed, 0,
1105 (MAX_DISP_BUFS_NEW) * sizeof(UWORD32));
1106 memset(ps_dec->ps_cur_slice, 0, sizeof(dec_slice_params_t));
1107
1108 ih264d_init_arch(ps_dec);
1109 ih264d_init_function_ptr(ps_dec);
1110 ps_dec->e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
1111 ps_dec->init_done = 1;
1112
1113 }
ih264d_free_static_bufs(iv_obj_t * dec_hdl)1114 WORD32 ih264d_free_static_bufs(iv_obj_t *dec_hdl)
1115 {
1116 dec_struct_t *ps_dec;
1117
1118 void (*pf_aligned_free)(void *pv_mem_ctxt, void *pv_buf);
1119 void *pv_mem_ctxt;
1120
1121 ps_dec = (dec_struct_t *)dec_hdl->pv_codec_handle;
1122 pf_aligned_free = ps_dec->pf_aligned_free;
1123 pv_mem_ctxt = ps_dec->pv_mem_ctxt;
1124
1125 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_sps);
1126 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_pps);
1127 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pv_dec_thread_handle);
1128 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pv_bs_deblk_thread_handle);
1129 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_dpb_mgr);
1130 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_pred);
1131 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pv_disp_buf_mgr);
1132 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pv_pic_buf_mgr);
1133 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_pic_buf_base);
1134 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_dec_err_status);
1135 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_sei);
1136 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_dpb_cmds);
1137 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_bitstrm);
1138 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_cur_slice);
1139 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pv_scratch_sps_pps);
1140 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pu1_bits_buf_static);
1141 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ppv_map_ref_idx_to_poc_base);
1142 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->p_cabac_ctxt_table_t);
1143 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_left_mb_ctxt_info);
1144 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pu1_ref_buff_base);
1145 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pi2_pred1);
1146 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pu1_temp_mc_buffer);
1147 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pu1_init_dpb_base);
1148 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pu4_mbaff_wt_mat);
1149 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pu4_wts_ofsts_mat);
1150 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_left_mvpred_addr);
1151 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->pv_mv_buf_mgr);
1152 PS_DEC_ALIGNED_FREE(ps_dec, ps_dec->ps_col_mv_base);
1153 PS_DEC_ALIGNED_FREE(ps_dec, dec_hdl->pv_codec_handle);
1154
1155 if(dec_hdl)
1156 {
1157 pf_aligned_free(pv_mem_ctxt, dec_hdl);
1158 }
1159 return IV_SUCCESS;
1160 }
1161 /*****************************************************************************/
1162 /* */
1163 /* Function Name : ih264d_create */
1164 /* */
1165 /* Description : creates decoder */
1166 /* */
1167 /* Inputs :iv_obj_t decoder handle */
1168 /* :pv_api_ip pointer to input structure */
1169 /* :pv_api_op pointer to output structure */
1170 /* Outputs : */
1171 /* Returns : void */
1172 /* */
1173 /* Issues : none */
1174 /* */
1175 /* Revision History: */
1176 /* */
1177 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
1178 /* 22 10 2008 100356 Draft */
1179 /* */
1180 /*****************************************************************************/
ih264d_allocate_static_bufs(iv_obj_t ** dec_hdl,void * pv_api_ip,void * pv_api_op)1181 WORD32 ih264d_allocate_static_bufs(iv_obj_t **dec_hdl, void *pv_api_ip, void *pv_api_op)
1182 {
1183 ih264d_create_ip_t *ps_create_ip;
1184 ih264d_create_op_t *ps_create_op;
1185 void *pv_buf;
1186 UWORD8 *pu1_buf;
1187 dec_struct_t *ps_dec;
1188 void *(*pf_aligned_alloc)(void *pv_mem_ctxt, WORD32 alignment, WORD32 size);
1189 void (*pf_aligned_free)(void *pv_mem_ctxt, void *pv_buf);
1190 void *pv_mem_ctxt;
1191 WORD32 size;
1192
1193 ps_create_ip = (ih264d_create_ip_t *)pv_api_ip;
1194 ps_create_op = (ih264d_create_op_t *)pv_api_op;
1195
1196 ps_create_op->s_ivd_create_op_t.u4_error_code = 0;
1197
1198 pf_aligned_alloc = ps_create_ip->s_ivd_create_ip_t.pf_aligned_alloc;
1199 pf_aligned_free = ps_create_ip->s_ivd_create_ip_t.pf_aligned_free;
1200 pv_mem_ctxt = ps_create_ip->s_ivd_create_ip_t.pv_mem_ctxt;
1201
1202 /* Initialize return handle to NULL */
1203 ps_create_op->s_ivd_create_op_t.pv_handle = NULL;
1204 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, sizeof(iv_obj_t));
1205 RETURN_IF((NULL == pv_buf), IV_FAIL);
1206 *dec_hdl = (iv_obj_t *)pv_buf;
1207 ps_create_op->s_ivd_create_op_t.pv_handle = *dec_hdl;
1208
1209 (*dec_hdl)->pv_codec_handle = NULL;
1210 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, sizeof(dec_struct_t));
1211 RETURN_IF((NULL == pv_buf), IV_FAIL);
1212 (*dec_hdl)->pv_codec_handle = (dec_struct_t *)pv_buf;
1213 ps_dec = (dec_struct_t *)pv_buf;
1214
1215 memset(ps_dec, 0, sizeof(dec_struct_t));
1216
1217 #ifndef LOGO_EN
1218 ps_dec->u4_share_disp_buf = ps_create_ip->s_ivd_create_ip_t.u4_share_disp_buf;
1219 #else
1220 ps_dec->u4_share_disp_buf = 0;
1221 #endif
1222
1223 ps_dec->u1_chroma_format =
1224 (UWORD8)(ps_create_ip->s_ivd_create_ip_t.e_output_format);
1225
1226 if((ps_dec->u1_chroma_format != IV_YUV_420P)
1227 && (ps_dec->u1_chroma_format
1228 != IV_YUV_420SP_UV)
1229 && (ps_dec->u1_chroma_format
1230 != IV_YUV_420SP_VU))
1231 {
1232 ps_dec->u4_share_disp_buf = 0;
1233 }
1234
1235 ps_dec->pf_aligned_alloc = pf_aligned_alloc;
1236 ps_dec->pf_aligned_free = pf_aligned_free;
1237 ps_dec->pv_mem_ctxt = pv_mem_ctxt;
1238
1239
1240 size = ((sizeof(dec_seq_params_t)) * MAX_NUM_SEQ_PARAMS);
1241 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1242 RETURN_IF((NULL == pv_buf), IV_FAIL);
1243 ps_dec->ps_sps = pv_buf;
1244
1245 size = (sizeof(dec_pic_params_t)) * MAX_NUM_PIC_PARAMS;
1246 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1247 RETURN_IF((NULL == pv_buf), IV_FAIL);
1248 ps_dec->ps_pps = pv_buf;
1249
1250 size = ithread_get_handle_size();
1251 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1252 RETURN_IF((NULL == pv_buf), IV_FAIL);
1253 ps_dec->pv_dec_thread_handle = pv_buf;
1254
1255 size = ithread_get_handle_size();
1256 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1257 RETURN_IF((NULL == pv_buf), IV_FAIL);
1258 ps_dec->pv_bs_deblk_thread_handle = pv_buf;
1259
1260 size = sizeof(dpb_manager_t);
1261 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1262 RETURN_IF((NULL == pv_buf), IV_FAIL);
1263 ps_dec->ps_dpb_mgr = pv_buf;
1264
1265 size = sizeof(pred_info_t) * 2 * 32;
1266 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1267 RETURN_IF((NULL == pv_buf), IV_FAIL);
1268 ps_dec->ps_pred = pv_buf;
1269
1270 size = sizeof(disp_mgr_t);
1271 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1272 RETURN_IF((NULL == pv_buf), IV_FAIL);
1273 ps_dec->pv_disp_buf_mgr = pv_buf;
1274
1275 size = sizeof(buf_mgr_t) + ithread_get_mutex_lock_size();
1276 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1277 RETURN_IF((NULL == pv_buf), IV_FAIL);
1278 ps_dec->pv_pic_buf_mgr = pv_buf;
1279
1280 size = sizeof(struct pic_buffer_t) * (H264_MAX_REF_PICS * 2);
1281 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1282 RETURN_IF((NULL == pv_buf), IV_FAIL);
1283 ps_dec->ps_pic_buf_base = pv_buf;
1284
1285 size = sizeof(dec_err_status_t);
1286 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1287 RETURN_IF((NULL == pv_buf), IV_FAIL);
1288 ps_dec->ps_dec_err_status = (dec_err_status_t *)pv_buf;
1289
1290 size = sizeof(sei);
1291 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1292 RETURN_IF((NULL == pv_buf), IV_FAIL);
1293 ps_dec->ps_sei = (sei *)pv_buf;
1294
1295 size = sizeof(dpb_commands_t);
1296 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1297 RETURN_IF((NULL == pv_buf), IV_FAIL);
1298 ps_dec->ps_dpb_cmds = (dpb_commands_t *)pv_buf;
1299
1300 size = sizeof(dec_bit_stream_t);
1301 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1302 RETURN_IF((NULL == pv_buf), IV_FAIL);
1303 ps_dec->ps_bitstrm = (dec_bit_stream_t *)pv_buf;
1304
1305 size = sizeof(dec_slice_params_t);
1306 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1307 RETURN_IF((NULL == pv_buf), IV_FAIL);
1308 ps_dec->ps_cur_slice = (dec_slice_params_t *)pv_buf;
1309
1310 size = MAX(sizeof(dec_seq_params_t), sizeof(dec_pic_params_t));
1311 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1312 RETURN_IF((NULL == pv_buf), IV_FAIL);
1313 ps_dec->pv_scratch_sps_pps = pv_buf;
1314
1315
1316 ps_dec->u4_static_bits_buf_size = 256000;
1317 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, ps_dec->u4_static_bits_buf_size);
1318 RETURN_IF((NULL == pv_buf), IV_FAIL);
1319 ps_dec->pu1_bits_buf_static = pv_buf;
1320
1321
1322 size = ((TOTAL_LIST_ENTRIES + PAD_MAP_IDX_POC)
1323 * sizeof(void *));
1324 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1325 RETURN_IF((NULL == pv_buf), IV_FAIL);
1326 ps_dec->ppv_map_ref_idx_to_poc_base = pv_buf;
1327 memset(ps_dec->ppv_map_ref_idx_to_poc_base, 0, size);
1328
1329 ps_dec->ppv_map_ref_idx_to_poc = ps_dec->ppv_map_ref_idx_to_poc_base + OFFSET_MAP_IDX_POC;
1330
1331
1332 size = (sizeof(bin_ctxt_model_t) * NUM_CABAC_CTXTS);
1333 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1334 RETURN_IF((NULL == pv_buf), IV_FAIL);
1335 ps_dec->p_cabac_ctxt_table_t = pv_buf;
1336
1337
1338
1339 size = sizeof(ctxt_inc_mb_info_t);
1340 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1341 RETURN_IF((NULL == pv_buf), IV_FAIL);
1342 ps_dec->ps_left_mb_ctxt_info = pv_buf;
1343
1344
1345
1346 size = MAX_REF_BUF_SIZE * 2;
1347 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1348 RETURN_IF((NULL == pv_buf), IV_FAIL);
1349 ps_dec->pu1_ref_buff_base = pv_buf;
1350 ps_dec->pu1_ref_buff = ps_dec->pu1_ref_buff_base + MAX_REF_BUF_SIZE;
1351
1352
1353 size = ((sizeof(WORD16)) * PRED_BUFFER_WIDTH
1354 * PRED_BUFFER_HEIGHT * 2);
1355 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1356 RETURN_IF((NULL == pv_buf), IV_FAIL);
1357 ps_dec->pi2_pred1 = pv_buf;
1358
1359
1360 size = sizeof(UWORD8) * (MB_LUM_SIZE);
1361 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1362 RETURN_IF((NULL == pv_buf), IV_FAIL);
1363 ps_dec->pu1_temp_mc_buffer = pv_buf;
1364
1365
1366
1367
1368 size = 8 * MAX_REF_BUFS * sizeof(struct pic_buffer_t);
1369 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1370 RETURN_IF((NULL == pv_buf), IV_FAIL);
1371
1372 ps_dec->pu1_init_dpb_base = pv_buf;
1373 pu1_buf = pv_buf;
1374 ps_dec->ps_dpb_mgr->ps_init_dpb[0][0] = (struct pic_buffer_t *)pu1_buf;
1375
1376 pu1_buf += size / 2;
1377 ps_dec->ps_dpb_mgr->ps_init_dpb[1][0] = (struct pic_buffer_t *)pu1_buf;
1378
1379 size = (sizeof(UWORD32) * 3
1380 * (MAX_FRAMES * MAX_FRAMES))
1381 << 3;
1382 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1383 RETURN_IF((NULL == pv_buf), IV_FAIL);
1384 ps_dec->pu4_mbaff_wt_mat = pv_buf;
1385
1386 size = sizeof(UWORD32) * 2 * 3
1387 * (MAX_FRAMES * MAX_FRAMES);
1388 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1389 RETURN_IF((NULL == pv_buf), IV_FAIL);
1390 ps_dec->pu4_wts_ofsts_mat = pv_buf;
1391
1392
1393 size = (sizeof(neighbouradd_t) << 2);
1394 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1395 RETURN_IF((NULL == pv_buf), IV_FAIL);
1396 ps_dec->ps_left_mvpred_addr = pv_buf;
1397
1398
1399 size = sizeof(buf_mgr_t) + ithread_get_mutex_lock_size();
1400 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1401 RETURN_IF((NULL == pv_buf), IV_FAIL);
1402 ps_dec->pv_mv_buf_mgr = pv_buf;
1403
1404
1405 size = sizeof(col_mv_buf_t) * (H264_MAX_REF_PICS * 2);
1406 pv_buf = pf_aligned_alloc(pv_mem_ctxt, 128, size);
1407 RETURN_IF((NULL == pv_buf), IV_FAIL);
1408 ps_dec->ps_col_mv_base = pv_buf;
1409 memset(ps_dec->ps_col_mv_base, 0, size);
1410
1411 {
1412 UWORD8 i;
1413 struct pic_buffer_t *ps_init_dpb;
1414 ps_init_dpb = ps_dec->ps_dpb_mgr->ps_init_dpb[0][0];
1415 for(i = 0; i < 2 * MAX_REF_BUFS; i++)
1416 {
1417 ps_init_dpb->pu1_buf1 = NULL;
1418 ps_init_dpb->u1_long_term_frm_idx = MAX_REF_BUFS + 1;
1419 ps_dec->ps_dpb_mgr->ps_init_dpb[0][i] = ps_init_dpb;
1420 ps_dec->ps_dpb_mgr->ps_mod_dpb[0][i] = ps_init_dpb;
1421 ps_init_dpb++;
1422 }
1423
1424 ps_init_dpb = ps_dec->ps_dpb_mgr->ps_init_dpb[1][0];
1425 for(i = 0; i < 2 * MAX_REF_BUFS; i++)
1426 {
1427 ps_init_dpb->pu1_buf1 = NULL;
1428 ps_init_dpb->u1_long_term_frm_idx = MAX_REF_BUFS + 1;
1429 ps_dec->ps_dpb_mgr->ps_init_dpb[1][i] = ps_init_dpb;
1430 ps_dec->ps_dpb_mgr->ps_mod_dpb[1][i] = ps_init_dpb;
1431 ps_init_dpb++;
1432 }
1433 }
1434 ih264d_init_decoder(ps_dec);
1435
1436 return IV_SUCCESS;
1437 }
1438
1439
1440 /*****************************************************************************/
1441 /* */
1442 /* Function Name : ih264d_create */
1443 /* */
1444 /* Description : creates decoder */
1445 /* */
1446 /* Inputs :iv_obj_t decoder handle */
1447 /* :pv_api_ip pointer to input structure */
1448 /* :pv_api_op pointer to output structure */
1449 /* Outputs : */
1450 /* Returns : void */
1451 /* */
1452 /* Issues : none */
1453 /* */
1454 /* Revision History: */
1455 /* */
1456 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
1457 /* 22 10 2008 100356 Draft */
1458 /* */
1459 /*****************************************************************************/
ih264d_create(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)1460 WORD32 ih264d_create(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
1461 {
1462 ih264d_create_op_t *ps_create_op;
1463
1464 WORD32 ret;
1465
1466 ps_create_op = (ih264d_create_op_t *)pv_api_op;
1467
1468 ps_create_op->s_ivd_create_op_t.u4_error_code = 0;
1469
1470 ret = ih264d_allocate_static_bufs(&dec_hdl, pv_api_ip, pv_api_op);
1471
1472 /* If allocation of some buffer fails, then free buffers allocated till then */
1473 if((IV_FAIL == ret) && (NULL != dec_hdl))
1474 {
1475 ih264d_free_static_bufs(dec_hdl);
1476 ps_create_op->s_ivd_create_op_t.u4_error_code = IVD_MEM_ALLOC_FAILED;
1477 ps_create_op->s_ivd_create_op_t.u4_error_code = 1 << IVD_FATALERROR;
1478
1479 return IV_FAIL;
1480 }
1481
1482 return IV_SUCCESS;
1483 }
1484
1485 /*****************************************************************************/
1486 /* */
1487 /* Function Name : ih264d_map_error */
1488 /* */
1489 /* Description : Maps error codes to IVD error groups */
1490 /* */
1491 /* Inputs : */
1492 /* Globals : <Does it use any global variables?> */
1493 /* Outputs : */
1494 /* Returns : void */
1495 /* */
1496 /* Issues : none */
1497 /* */
1498 /* Revision History: */
1499 /* */
1500 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
1501 /* 22 10 2008 100356 Draft */
1502 /* */
1503 /*****************************************************************************/
ih264d_map_error(UWORD32 i4_err_status)1504 UWORD32 ih264d_map_error(UWORD32 i4_err_status)
1505 {
1506 UWORD32 temp = 0;
1507
1508 switch(i4_err_status)
1509 {
1510 case ERROR_MEM_ALLOC_ISRAM_T:
1511 case ERROR_MEM_ALLOC_SDRAM_T:
1512 case ERROR_BUF_MGR:
1513 case ERROR_MB_GROUP_ASSGN_T:
1514 case ERROR_FRAME_LIMIT_OVER:
1515 case ERROR_ACTUAL_RESOLUTION_GREATER_THAN_INIT:
1516 case ERROR_PROFILE_NOT_SUPPORTED:
1517 case ERROR_INIT_NOT_DONE:
1518 case IVD_MEM_ALLOC_FAILED:
1519 temp = 1 << IVD_FATALERROR;
1520 H264_DEC_DEBUG_PRINT("\nFatal Error\n");
1521 break;
1522
1523 case ERROR_DBP_MANAGER_T:
1524 case ERROR_GAPS_IN_FRM_NUM:
1525 case ERROR_UNKNOWN_NAL:
1526 case ERROR_INV_MB_SLC_GRP_T:
1527 case ERROR_MULTIPLE_SLC_GRP_T:
1528 case ERROR_UNKNOWN_LEVEL:
1529 case ERROR_UNAVAIL_PICBUF_T:
1530 case ERROR_UNAVAIL_MVBUF_T:
1531 case ERROR_UNAVAIL_DISPBUF_T:
1532 case ERROR_NUM_REF:
1533 case ERROR_REFIDX_ORDER_T:
1534 case ERROR_PIC0_NOT_FOUND_T:
1535 case ERROR_MB_TYPE:
1536 case ERROR_SUB_MB_TYPE:
1537 case ERROR_CBP:
1538 case ERROR_REF_IDX:
1539 case ERROR_NUM_MV:
1540 case ERROR_CHROMA_PRED_MODE:
1541 case ERROR_INTRAPRED:
1542 case ERROR_NEXT_MB_ADDRESS_T:
1543 case ERROR_MB_ADDRESS_T:
1544 case ERROR_PIC1_NOT_FOUND_T:
1545 case ERROR_CAVLC_NUM_COEFF_T:
1546 case ERROR_CAVLC_SCAN_POS_T:
1547 case ERROR_PRED_WEIGHT_TABLE_T:
1548 case ERROR_CORRUPTED_SLICE:
1549 temp = 1 << IVD_CORRUPTEDDATA;
1550 break;
1551
1552 case ERROR_NOT_SUPP_RESOLUTION:
1553 case ERROR_FEATURE_UNAVAIL:
1554 case ERROR_ACTUAL_LEVEL_GREATER_THAN_INIT:
1555 temp = 1 << IVD_UNSUPPORTEDINPUT;
1556 break;
1557
1558 case ERROR_INVALID_PIC_PARAM:
1559 case ERROR_INVALID_SEQ_PARAM:
1560 case ERROR_EGC_EXCEED_32_1_T:
1561 case ERROR_EGC_EXCEED_32_2_T:
1562 case ERROR_INV_RANGE_TEV_T:
1563 case ERROR_INV_SLC_TYPE_T:
1564 case ERROR_INV_POC_TYPE_T:
1565 case ERROR_INV_RANGE_QP_T:
1566 case ERROR_INV_SPS_PPS_T:
1567 case ERROR_INV_SLICE_HDR_T:
1568 temp = 1 << IVD_CORRUPTEDHEADER;
1569 break;
1570
1571 case ERROR_EOB_FLUSHBITS_T:
1572 case ERROR_EOB_GETBITS_T:
1573 case ERROR_EOB_GETBIT_T:
1574 case ERROR_EOB_BYPASS_T:
1575 case ERROR_EOB_DECISION_T:
1576 case ERROR_EOB_TERMINATE_T:
1577 case ERROR_EOB_READCOEFF4X4CAB_T:
1578 temp = 1 << IVD_INSUFFICIENTDATA;
1579 break;
1580 case ERROR_DYNAMIC_RESOLUTION_NOT_SUPPORTED:
1581 case ERROR_DISP_WIDTH_RESET_TO_PIC_WIDTH:
1582 temp = 1 << IVD_UNSUPPORTEDPARAM | 1 << IVD_FATALERROR;
1583 break;
1584
1585 case ERROR_DANGLING_FIELD_IN_PIC:
1586 temp = 1 << IVD_APPLIEDCONCEALMENT;
1587 break;
1588
1589 }
1590
1591 return temp;
1592
1593 }
1594
1595 /*****************************************************************************/
1596 /* */
1597 /* Function Name : ih264d_video_decode */
1598 /* */
1599 /* Description : handle video decode API command */
1600 /* */
1601 /* Inputs :iv_obj_t decoder handle */
1602 /* :pv_api_ip pointer to input structure */
1603 /* :pv_api_op pointer to output structure */
1604 /* Outputs : */
1605 /* Returns : void */
1606 /* */
1607 /* Issues : none */
1608 /* */
1609 /* Revision History: */
1610 /* */
1611 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
1612 /* 22 10 2008 100356 Draft */
1613 /* */
1614 /*****************************************************************************/
1615
ih264d_video_decode(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)1616 WORD32 ih264d_video_decode(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
1617 {
1618 /* ! */
1619
1620 dec_struct_t * ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
1621
1622 WORD32 i4_err_status = 0;
1623 UWORD8 *pu1_buf = NULL;
1624 WORD32 buflen;
1625 UWORD32 u4_max_ofst, u4_length_of_start_code = 0;
1626
1627 UWORD32 bytes_consumed = 0;
1628 UWORD32 cur_slice_is_nonref = 0;
1629 UWORD32 u4_next_is_aud;
1630 UWORD32 u4_first_start_code_found = 0;
1631 WORD32 ret = 0,api_ret_value = IV_SUCCESS;
1632 WORD32 header_data_left = 0,frame_data_left = 0;
1633 UWORD8 *pu1_bitstrm_buf;
1634 ivd_video_decode_ip_t *ps_dec_ip;
1635 ivd_video_decode_op_t *ps_dec_op;
1636
1637 ithread_set_name((void*)"Parse_thread");
1638
1639 ps_dec_ip = (ivd_video_decode_ip_t *)pv_api_ip;
1640 ps_dec_op = (ivd_video_decode_op_t *)pv_api_op;
1641
1642 {
1643 UWORD32 u4_size;
1644 u4_size = ps_dec_op->u4_size;
1645 memset(ps_dec_op, 0, sizeof(ivd_video_decode_op_t));
1646 ps_dec_op->u4_size = u4_size;
1647 }
1648
1649 ps_dec->pv_dec_out = ps_dec_op;
1650 if(ps_dec->init_done != 1)
1651 {
1652 return IV_FAIL;
1653 }
1654
1655 /*Data memory barries instruction,so that bitstream write by the application is complete*/
1656 DATA_SYNC();
1657
1658 if(0 == ps_dec->u1_flushfrm)
1659 {
1660 if(ps_dec_ip->pv_stream_buffer == NULL)
1661 {
1662 ps_dec_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
1663 ps_dec_op->u4_error_code |= IVD_DEC_FRM_BS_BUF_NULL;
1664 return IV_FAIL;
1665 }
1666 if(ps_dec_ip->u4_num_Bytes <= 0)
1667 {
1668 ps_dec_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
1669 ps_dec_op->u4_error_code |= IVD_DEC_NUMBYTES_INV;
1670 return IV_FAIL;
1671
1672 }
1673 }
1674 ps_dec->u1_pic_decode_done = 0;
1675
1676 ps_dec_op->u4_num_bytes_consumed = 0;
1677
1678 ps_dec->ps_out_buffer = NULL;
1679
1680 if(ps_dec_ip->u4_size
1681 >= offsetof(ivd_video_decode_ip_t, s_out_buffer))
1682 ps_dec->ps_out_buffer = &ps_dec_ip->s_out_buffer;
1683
1684 ps_dec->u4_fmt_conv_cur_row = 0;
1685
1686 ps_dec->u4_output_present = 0;
1687 ps_dec->s_disp_op.u4_error_code = 1;
1688 ps_dec->u4_fmt_conv_num_rows = FMT_CONV_NUM_ROWS;
1689 if(0 == ps_dec->u4_share_disp_buf
1690 && ps_dec->i4_decode_header == 0)
1691 {
1692 UWORD32 i;
1693 if(ps_dec->ps_out_buffer->u4_num_bufs == 0)
1694 {
1695 ps_dec_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
1696 ps_dec_op->u4_error_code |= IVD_DISP_FRM_ZERO_OP_BUFS;
1697 return IV_FAIL;
1698 }
1699
1700 for(i = 0; i < ps_dec->ps_out_buffer->u4_num_bufs; i++)
1701 {
1702 if(ps_dec->ps_out_buffer->pu1_bufs[i] == NULL)
1703 {
1704 ps_dec_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
1705 ps_dec_op->u4_error_code |= IVD_DISP_FRM_OP_BUF_NULL;
1706 return IV_FAIL;
1707 }
1708
1709 if(ps_dec->ps_out_buffer->u4_min_out_buf_size[i] == 0)
1710 {
1711 ps_dec_op->u4_error_code |= 1 << IVD_UNSUPPORTEDPARAM;
1712 ps_dec_op->u4_error_code |=
1713 IVD_DISP_FRM_ZERO_OP_BUF_SIZE;
1714 return IV_FAIL;
1715 }
1716 }
1717 }
1718
1719 if(ps_dec->u4_total_frames_decoded >= NUM_FRAMES_LIMIT)
1720 {
1721 ps_dec_op->u4_error_code = ERROR_FRAME_LIMIT_OVER;
1722 return IV_FAIL;
1723 }
1724
1725 /* ! */
1726 ps_dec->u4_ts = ps_dec_ip->u4_ts;
1727
1728 ps_dec_op->u4_error_code = 0;
1729 ps_dec_op->e_pic_type = -1;
1730 ps_dec_op->u4_output_present = 0;
1731 ps_dec_op->u4_frame_decoded_flag = 0;
1732
1733 ps_dec->i4_frametype = -1;
1734 ps_dec->i4_content_type = -1;
1735 /*
1736 * For field pictures, set the bottom and top picture decoded u4_flag correctly.
1737 */
1738 {
1739 if((TOP_FIELD_ONLY | BOT_FIELD_ONLY) == ps_dec->u1_top_bottom_decoded)
1740 {
1741 ps_dec->u1_top_bottom_decoded = 0;
1742 }
1743 }
1744 ps_dec->u4_slice_start_code_found = 0;
1745
1746 /* In case the deocder is not in flush mode(in shared mode),
1747 then decoder has to pick up a buffer to write current frame.
1748 Check if a frame is available in such cases */
1749
1750 if(ps_dec->u1_init_dec_flag == 1 && ps_dec->u4_share_disp_buf == 1
1751 && ps_dec->u1_flushfrm == 0)
1752 {
1753 UWORD32 i;
1754
1755 WORD32 disp_avail = 0, free_id;
1756
1757 /* Check if at least one buffer is available with the codec */
1758 /* If not then return to application with error */
1759 for(i = 0; i < ps_dec->u1_pic_bufs; i++)
1760 {
1761 if(0 == ps_dec->u4_disp_buf_mapping[i]
1762 || 1 == ps_dec->u4_disp_buf_to_be_freed[i])
1763 {
1764 disp_avail = 1;
1765 break;
1766 }
1767
1768 }
1769
1770 if(0 == disp_avail)
1771 {
1772 /* If something is queued for display wait for that buffer to be returned */
1773
1774 ps_dec_op->u4_error_code = IVD_DEC_REF_BUF_NULL;
1775 ps_dec_op->u4_error_code |= (1 << IVD_UNSUPPORTEDPARAM);
1776 return (IV_FAIL);
1777 }
1778
1779 while(1)
1780 {
1781 pic_buffer_t *ps_pic_buf;
1782 ps_pic_buf = (pic_buffer_t *)ih264_buf_mgr_get_next_free(
1783 (buf_mgr_t *)ps_dec->pv_pic_buf_mgr, &free_id);
1784
1785 if(ps_pic_buf == NULL)
1786 {
1787 UWORD32 i, display_queued = 0;
1788
1789 /* check if any buffer was given for display which is not returned yet */
1790 for(i = 0; i < (MAX_DISP_BUFS_NEW); i++)
1791 {
1792 if(0 != ps_dec->u4_disp_buf_mapping[i])
1793 {
1794 display_queued = 1;
1795 break;
1796 }
1797 }
1798 /* If some buffer is queued for display, then codec has to singal an error and wait
1799 for that buffer to be returned.
1800 If nothing is queued for display then codec has ownership of all display buffers
1801 and it can reuse any of the existing buffers and continue decoding */
1802
1803 if(1 == display_queued)
1804 {
1805 /* If something is queued for display wait for that buffer to be returned */
1806 ps_dec_op->u4_error_code = IVD_DEC_REF_BUF_NULL;
1807 ps_dec_op->u4_error_code |= (1
1808 << IVD_UNSUPPORTEDPARAM);
1809 return (IV_FAIL);
1810 }
1811 }
1812 else
1813 {
1814 /* If the buffer is with display, then mark it as in use and then look for a buffer again */
1815 if(1 == ps_dec->u4_disp_buf_mapping[free_id])
1816 {
1817 ih264_buf_mgr_set_status(
1818 (buf_mgr_t *)ps_dec->pv_pic_buf_mgr,
1819 free_id,
1820 BUF_MGR_IO);
1821 }
1822 else
1823 {
1824 /**
1825 * Found a free buffer for present call. Release it now.
1826 * Will be again obtained later.
1827 */
1828 ih264_buf_mgr_release((buf_mgr_t *)ps_dec->pv_pic_buf_mgr,
1829 free_id,
1830 BUF_MGR_IO);
1831 break;
1832 }
1833 }
1834 }
1835
1836 }
1837
1838 if(ps_dec->u1_flushfrm && ps_dec->u1_init_dec_flag)
1839 {
1840
1841 ih264d_get_next_display_field(ps_dec, ps_dec->ps_out_buffer,
1842 &(ps_dec->s_disp_op));
1843 if(0 == ps_dec->s_disp_op.u4_error_code)
1844 {
1845 ps_dec->u4_fmt_conv_cur_row = 0;
1846 ps_dec->u4_fmt_conv_num_rows = ps_dec->s_disp_frame_info.u4_y_ht;
1847 ih264d_format_convert(ps_dec, &(ps_dec->s_disp_op),
1848 ps_dec->u4_fmt_conv_cur_row,
1849 ps_dec->u4_fmt_conv_num_rows);
1850 ps_dec->u4_fmt_conv_cur_row += ps_dec->u4_fmt_conv_num_rows;
1851 ps_dec->u4_output_present = 1;
1852
1853 }
1854 ih264d_release_display_field(ps_dec, &(ps_dec->s_disp_op));
1855
1856 ps_dec_op->u4_pic_wd = (UWORD32)ps_dec->u2_disp_width;
1857 ps_dec_op->u4_pic_ht = (UWORD32)ps_dec->u2_disp_height;
1858
1859 ps_dec_op->u4_new_seq = 0;
1860
1861 ps_dec_op->u4_output_present = ps_dec->u4_output_present;
1862 ps_dec_op->u4_progressive_frame_flag =
1863 ps_dec->s_disp_op.u4_progressive_frame_flag;
1864 ps_dec_op->e_output_format =
1865 ps_dec->s_disp_op.e_output_format;
1866 ps_dec_op->s_disp_frm_buf = ps_dec->s_disp_op.s_disp_frm_buf;
1867 ps_dec_op->e4_fld_type = ps_dec->s_disp_op.e4_fld_type;
1868 ps_dec_op->u4_ts = ps_dec->s_disp_op.u4_ts;
1869 ps_dec_op->u4_disp_buf_id = ps_dec->s_disp_op.u4_disp_buf_id;
1870
1871 /*In the case of flush ,since no frame is decoded set pic type as invalid*/
1872 ps_dec_op->u4_is_ref_flag = -1;
1873 ps_dec_op->e_pic_type = IV_NA_FRAME;
1874 ps_dec_op->u4_frame_decoded_flag = 0;
1875
1876 if(0 == ps_dec->s_disp_op.u4_error_code)
1877 {
1878 return (IV_SUCCESS);
1879 }
1880 else
1881 return (IV_FAIL);
1882
1883 }
1884 if(ps_dec->u1_res_changed == 1)
1885 {
1886 /*if resolution has changed and all buffers have been flushed, reset decoder*/
1887 ih264d_init_decoder(ps_dec);
1888 }
1889
1890 ps_dec->u4_prev_nal_skipped = 0;
1891
1892 ps_dec->u2_cur_mb_addr = 0;
1893 ps_dec->u2_total_mbs_coded = 0;
1894 ps_dec->u2_cur_slice_num = 0;
1895 ps_dec->cur_dec_mb_num = 0;
1896 ps_dec->cur_recon_mb_num = 0;
1897 ps_dec->u4_first_slice_in_pic = 2;
1898 ps_dec->u1_first_pb_nal_in_pic = 1;
1899 ps_dec->u1_slice_header_done = 0;
1900 ps_dec->u1_dangling_field = 0;
1901
1902 ps_dec->u4_dec_thread_created = 0;
1903 ps_dec->u4_bs_deblk_thread_created = 0;
1904 ps_dec->u4_cur_bs_mb_num = 0;
1905 ps_dec->u4_start_recon_deblk = 0;
1906
1907 DEBUG_THREADS_PRINTF(" Starting process call\n");
1908
1909
1910 ps_dec->u4_pic_buf_got = 0;
1911
1912 do
1913 {
1914 WORD32 buf_size;
1915
1916 pu1_buf = (UWORD8*)ps_dec_ip->pv_stream_buffer
1917 + ps_dec_op->u4_num_bytes_consumed;
1918
1919 u4_max_ofst = ps_dec_ip->u4_num_Bytes
1920 - ps_dec_op->u4_num_bytes_consumed;
1921
1922 /* If dynamic bitstream buffer is not allocated and
1923 * header decode is done, then allocate dynamic bitstream buffer
1924 */
1925 if((NULL == ps_dec->pu1_bits_buf_dynamic) &&
1926 (ps_dec->i4_header_decoded & 1))
1927 {
1928 WORD32 size;
1929
1930 void *pv_buf;
1931 void *pv_mem_ctxt = ps_dec->pv_mem_ctxt;
1932 size = MAX(256000, ps_dec->u2_pic_wd * ps_dec->u2_pic_ht * 3 / 2);
1933 pv_buf = ps_dec->pf_aligned_alloc(pv_mem_ctxt, 128, size);
1934 RETURN_IF((NULL == pv_buf), IV_FAIL);
1935 ps_dec->pu1_bits_buf_dynamic = pv_buf;
1936 ps_dec->u4_dynamic_bits_buf_size = size;
1937 }
1938
1939 if(ps_dec->pu1_bits_buf_dynamic)
1940 {
1941 pu1_bitstrm_buf = ps_dec->pu1_bits_buf_dynamic;
1942 buf_size = ps_dec->u4_dynamic_bits_buf_size;
1943 }
1944 else
1945 {
1946 pu1_bitstrm_buf = ps_dec->pu1_bits_buf_static;
1947 buf_size = ps_dec->u4_static_bits_buf_size;
1948 }
1949
1950 u4_next_is_aud = 0;
1951
1952 buflen = ih264d_find_start_code(pu1_buf, 0, u4_max_ofst,
1953 &u4_length_of_start_code,
1954 &u4_next_is_aud);
1955
1956 if(buflen == -1)
1957 buflen = 0;
1958 /* Ignore bytes beyond the allocated size of intermediate buffer */
1959 buflen = MIN(buflen, buf_size);
1960
1961 bytes_consumed = buflen + u4_length_of_start_code;
1962 ps_dec_op->u4_num_bytes_consumed += bytes_consumed;
1963
1964 {
1965 UWORD8 u1_firstbyte, u1_nal_ref_idc;
1966
1967 if(ps_dec->i4_app_skip_mode == IVD_SKIP_B)
1968 {
1969 u1_firstbyte = *(pu1_buf + u4_length_of_start_code);
1970 u1_nal_ref_idc = (UWORD8)(NAL_REF_IDC(u1_firstbyte));
1971 if(u1_nal_ref_idc == 0)
1972 {
1973 /*skip non reference frames*/
1974 cur_slice_is_nonref = 1;
1975 continue;
1976 }
1977 else
1978 {
1979 if(1 == cur_slice_is_nonref)
1980 {
1981 /*We have encountered a referenced frame,return to app*/
1982 ps_dec_op->u4_num_bytes_consumed -=
1983 bytes_consumed;
1984 ps_dec_op->e_pic_type = IV_B_FRAME;
1985 ps_dec_op->u4_error_code =
1986 IVD_DEC_FRM_SKIPPED;
1987 ps_dec_op->u4_error_code |= (1
1988 << IVD_UNSUPPORTEDPARAM);
1989 ps_dec_op->u4_frame_decoded_flag = 0;
1990 ps_dec_op->u4_size =
1991 sizeof(ivd_video_decode_op_t);
1992 /*signal the decode thread*/
1993 ih264d_signal_decode_thread(ps_dec);
1994 /* close deblock thread if it is not closed yet*/
1995 if(ps_dec->u4_num_cores == 3)
1996 {
1997 ih264d_signal_bs_deblk_thread(ps_dec);
1998 }
1999
2000 return (IV_FAIL);
2001 }
2002 }
2003
2004 }
2005
2006 }
2007
2008
2009 if(buflen)
2010 {
2011 memcpy(pu1_bitstrm_buf, pu1_buf + u4_length_of_start_code,
2012 buflen);
2013 /* Decoder may read extra 8 bytes near end of the frame */
2014 if((buflen + 8) < buf_size)
2015 {
2016 memset(pu1_bitstrm_buf + buflen, 0, 8);
2017 }
2018 u4_first_start_code_found = 1;
2019
2020 }
2021 else
2022 {
2023 /*start code not found*/
2024
2025 if(u4_first_start_code_found == 0)
2026 {
2027 /*no start codes found in current process call*/
2028
2029 ps_dec->i4_error_code = ERROR_START_CODE_NOT_FOUND;
2030 ps_dec_op->u4_error_code |= 1 << IVD_INSUFFICIENTDATA;
2031
2032 if(ps_dec->u4_pic_buf_got == 0)
2033 {
2034
2035 ih264d_fill_output_struct_from_context(ps_dec,
2036 ps_dec_op);
2037
2038 ps_dec_op->u4_error_code = ps_dec->i4_error_code;
2039 ps_dec_op->u4_frame_decoded_flag = 0;
2040
2041 return (IV_FAIL);
2042 }
2043 else
2044 {
2045 ps_dec->u1_pic_decode_done = 1;
2046 continue;
2047 }
2048 }
2049 else
2050 {
2051 /* a start code has already been found earlier in the same process call*/
2052 frame_data_left = 0;
2053 continue;
2054 }
2055
2056 }
2057
2058 ps_dec->u4_return_to_app = 0;
2059 ret = ih264d_parse_nal_unit(dec_hdl, ps_dec_op,
2060 pu1_bitstrm_buf, buflen);
2061 if(ret != OK)
2062 {
2063 UWORD32 error = ih264d_map_error(ret);
2064 ps_dec_op->u4_error_code = error | ret;
2065 api_ret_value = IV_FAIL;
2066
2067 if((ret == IVD_RES_CHANGED)
2068 || (ret == IVD_MEM_ALLOC_FAILED)
2069 || (ret == ERROR_UNAVAIL_PICBUF_T)
2070 || (ret == ERROR_UNAVAIL_MVBUF_T)
2071 || (ret == ERROR_INV_SPS_PPS_T))
2072 {
2073 ps_dec->u4_slice_start_code_found = 0;
2074 break;
2075 }
2076
2077 if((ret == ERROR_INCOMPLETE_FRAME) || (ret == ERROR_DANGLING_FIELD_IN_PIC))
2078 {
2079 ps_dec_op->u4_num_bytes_consumed -= bytes_consumed;
2080 api_ret_value = IV_FAIL;
2081 break;
2082 }
2083
2084 if(ret == ERROR_IN_LAST_SLICE_OF_PIC)
2085 {
2086 api_ret_value = IV_FAIL;
2087 break;
2088 }
2089
2090 }
2091
2092 if(ps_dec->u4_return_to_app)
2093 {
2094 /*We have encountered a referenced frame,return to app*/
2095 ps_dec_op->u4_num_bytes_consumed -= bytes_consumed;
2096 ps_dec_op->u4_error_code = IVD_DEC_FRM_SKIPPED;
2097 ps_dec_op->u4_error_code |= (1 << IVD_UNSUPPORTEDPARAM);
2098 ps_dec_op->u4_frame_decoded_flag = 0;
2099 ps_dec_op->u4_size = sizeof(ivd_video_decode_op_t);
2100 /*signal the decode thread*/
2101 ih264d_signal_decode_thread(ps_dec);
2102 /* close deblock thread if it is not closed yet*/
2103 if(ps_dec->u4_num_cores == 3)
2104 {
2105 ih264d_signal_bs_deblk_thread(ps_dec);
2106 }
2107 return (IV_FAIL);
2108
2109 }
2110
2111
2112
2113 header_data_left = ((ps_dec->i4_decode_header == 1)
2114 && (ps_dec->i4_header_decoded != 3)
2115 && (ps_dec_op->u4_num_bytes_consumed
2116 < ps_dec_ip->u4_num_Bytes));
2117 frame_data_left = (((ps_dec->i4_decode_header == 0)
2118 && ((ps_dec->u1_pic_decode_done == 0)
2119 || (u4_next_is_aud == 1)))
2120 && (ps_dec_op->u4_num_bytes_consumed
2121 < ps_dec_ip->u4_num_Bytes));
2122 }
2123 while(( header_data_left == 1)||(frame_data_left == 1));
2124
2125 if((ps_dec->u4_slice_start_code_found == 1)
2126 && (ret != IVD_MEM_ALLOC_FAILED)
2127 && ps_dec->u2_total_mbs_coded < ps_dec->u2_frm_ht_in_mbs * ps_dec->u2_frm_wd_in_mbs)
2128 {
2129 // last slice - missing/corruption
2130 WORD32 num_mb_skipped;
2131 WORD32 prev_slice_err;
2132 pocstruct_t temp_poc;
2133 WORD32 ret1;
2134
2135 num_mb_skipped = (ps_dec->u2_frm_ht_in_mbs * ps_dec->u2_frm_wd_in_mbs)
2136 - ps_dec->u2_total_mbs_coded;
2137
2138 if(ps_dec->u4_first_slice_in_pic && (ps_dec->u4_pic_buf_got == 0))
2139 prev_slice_err = 1;
2140 else
2141 prev_slice_err = 2;
2142
2143 ret1 = ih264d_mark_err_slice_skip(ps_dec, num_mb_skipped, ps_dec->u1_nal_unit_type == IDR_SLICE_NAL, ps_dec->ps_cur_slice->u2_frame_num,
2144 &temp_poc, prev_slice_err);
2145
2146 if((ret1 == ERROR_UNAVAIL_PICBUF_T) || (ret1 == ERROR_UNAVAIL_MVBUF_T))
2147 {
2148 return IV_FAIL;
2149 }
2150 }
2151
2152 if((ret == IVD_RES_CHANGED)
2153 || (ret == IVD_MEM_ALLOC_FAILED)
2154 || (ret == ERROR_UNAVAIL_PICBUF_T)
2155 || (ret == ERROR_UNAVAIL_MVBUF_T)
2156 || (ret == ERROR_INV_SPS_PPS_T))
2157 {
2158
2159 /* signal the decode thread */
2160 ih264d_signal_decode_thread(ps_dec);
2161 /* close deblock thread if it is not closed yet */
2162 if(ps_dec->u4_num_cores == 3)
2163 {
2164 ih264d_signal_bs_deblk_thread(ps_dec);
2165 }
2166 /* dont consume bitstream for change in resolution case */
2167 if(ret == IVD_RES_CHANGED)
2168 {
2169 ps_dec_op->u4_num_bytes_consumed -= bytes_consumed;
2170 }
2171 return IV_FAIL;
2172 }
2173
2174
2175 if(ps_dec->u1_separate_parse)
2176 {
2177 /* If Format conversion is not complete,
2178 complete it here */
2179 if(ps_dec->u4_num_cores == 2)
2180 {
2181
2182 /*do deblocking of all mbs*/
2183 if((ps_dec->u4_nmb_deblk == 0) &&(ps_dec->u4_start_recon_deblk == 1) && (ps_dec->ps_cur_sps->u1_mb_aff_flag == 0))
2184 {
2185 UWORD32 u4_num_mbs,u4_max_addr;
2186 tfr_ctxt_t s_tfr_ctxt;
2187 tfr_ctxt_t *ps_tfr_cxt = &s_tfr_ctxt;
2188 pad_mgr_t *ps_pad_mgr = &ps_dec->s_pad_mgr;
2189
2190 /*BS is done for all mbs while parsing*/
2191 u4_max_addr = (ps_dec->u2_frm_wd_in_mbs * ps_dec->u2_frm_ht_in_mbs) - 1;
2192 ps_dec->u4_cur_bs_mb_num = u4_max_addr + 1;
2193
2194
2195 ih264d_init_deblk_tfr_ctxt(ps_dec, ps_pad_mgr, ps_tfr_cxt,
2196 ps_dec->u2_frm_wd_in_mbs, 0);
2197
2198
2199 u4_num_mbs = u4_max_addr
2200 - ps_dec->u4_cur_deblk_mb_num + 1;
2201
2202 DEBUG_PERF_PRINTF("mbs left for deblocking= %d \n",u4_num_mbs);
2203
2204 if(u4_num_mbs != 0)
2205 ih264d_check_mb_map_deblk(ps_dec, u4_num_mbs,
2206 ps_tfr_cxt,1);
2207
2208 ps_dec->u4_start_recon_deblk = 0;
2209
2210 }
2211
2212 }
2213
2214 /*signal the decode thread*/
2215 ih264d_signal_decode_thread(ps_dec);
2216 /* close deblock thread if it is not closed yet*/
2217 if(ps_dec->u4_num_cores == 3)
2218 {
2219 ih264d_signal_bs_deblk_thread(ps_dec);
2220 }
2221 }
2222
2223
2224 DATA_SYNC();
2225
2226
2227 if((ps_dec_op->u4_error_code & 0xff)
2228 != ERROR_DYNAMIC_RESOLUTION_NOT_SUPPORTED)
2229 {
2230 ps_dec_op->u4_pic_wd = (UWORD32)ps_dec->u2_disp_width;
2231 ps_dec_op->u4_pic_ht = (UWORD32)ps_dec->u2_disp_height;
2232 }
2233
2234 //Report if header (sps and pps) has not been decoded yet
2235 if(ps_dec->i4_header_decoded != 3)
2236 {
2237 ps_dec_op->u4_error_code |= (1 << IVD_INSUFFICIENTDATA);
2238
2239 }
2240
2241 if(ps_dec->i4_decode_header == 1 && ps_dec->i4_header_decoded != 3)
2242 {
2243 ps_dec_op->u4_error_code |= (1 << IVD_INSUFFICIENTDATA);
2244
2245 }
2246 if(ps_dec->u4_prev_nal_skipped)
2247 {
2248 /*We have encountered a referenced frame,return to app*/
2249 ps_dec_op->u4_error_code = IVD_DEC_FRM_SKIPPED;
2250 ps_dec_op->u4_error_code |= (1 << IVD_UNSUPPORTEDPARAM);
2251 ps_dec_op->u4_frame_decoded_flag = 0;
2252 ps_dec_op->u4_size = sizeof(ivd_video_decode_op_t);
2253 /* close deblock thread if it is not closed yet*/
2254 if(ps_dec->u4_num_cores == 3)
2255 {
2256 ih264d_signal_bs_deblk_thread(ps_dec);
2257 }
2258 return (IV_FAIL);
2259
2260 }
2261
2262 if((ps_dec->u4_slice_start_code_found == 1)
2263 && (ERROR_DANGLING_FIELD_IN_PIC != i4_err_status))
2264 {
2265 /*
2266 * For field pictures, set the bottom and top picture decoded u4_flag correctly.
2267 */
2268
2269 if(ps_dec->ps_cur_slice->u1_field_pic_flag)
2270 {
2271 if(1 == ps_dec->ps_cur_slice->u1_bottom_field_flag)
2272 {
2273 ps_dec->u1_top_bottom_decoded |= BOT_FIELD_ONLY;
2274 }
2275 else
2276 {
2277 ps_dec->u1_top_bottom_decoded |= TOP_FIELD_ONLY;
2278 }
2279 }
2280
2281 /* if new frame in not found (if we are still getting slices from previous frame)
2282 * ih264d_deblock_display is not called. Such frames will not be added to reference /display
2283 */
2284 if((ps_dec->ps_dec_err_status->u1_err_flag & REJECT_CUR_PIC) == 0)
2285 {
2286 /* Calling Function to deblock Picture and Display */
2287 ret = ih264d_deblock_display(ps_dec);
2288 if(ret != 0)
2289 {
2290 return IV_FAIL;
2291 }
2292 }
2293
2294
2295 /*set to complete ,as we dont support partial frame decode*/
2296 if(ps_dec->i4_header_decoded == 3)
2297 {
2298 ps_dec->u2_total_mbs_coded = ps_dec->ps_cur_sps->u2_max_mb_addr + 1;
2299 }
2300
2301 /*Update the i4_frametype at the end of picture*/
2302 if(ps_dec->ps_cur_slice->u1_nal_unit_type == IDR_SLICE_NAL)
2303 {
2304 ps_dec->i4_frametype = IV_IDR_FRAME;
2305 }
2306 else if(ps_dec->i4_pic_type == B_SLICE)
2307 {
2308 ps_dec->i4_frametype = IV_B_FRAME;
2309 }
2310 else if(ps_dec->i4_pic_type == P_SLICE)
2311 {
2312 ps_dec->i4_frametype = IV_P_FRAME;
2313 }
2314 else if(ps_dec->i4_pic_type == I_SLICE)
2315 {
2316 ps_dec->i4_frametype = IV_I_FRAME;
2317 }
2318 else
2319 {
2320 H264_DEC_DEBUG_PRINT("Shouldn't come here\n");
2321 }
2322
2323 //Update the content type
2324 ps_dec->i4_content_type = ps_dec->ps_cur_slice->u1_field_pic_flag;
2325
2326 ps_dec->u4_total_frames_decoded = ps_dec->u4_total_frames_decoded + 2;
2327 ps_dec->u4_total_frames_decoded = ps_dec->u4_total_frames_decoded
2328 - ps_dec->ps_cur_slice->u1_field_pic_flag;
2329
2330 }
2331
2332 /* close deblock thread if it is not closed yet*/
2333 if(ps_dec->u4_num_cores == 3)
2334 {
2335 ih264d_signal_bs_deblk_thread(ps_dec);
2336 }
2337
2338
2339 {
2340 /* In case the decoder is configured to run in low delay mode,
2341 * then get display buffer and then format convert.
2342 * Note in this mode, format conversion does not run paralelly in a thread and adds to the codec cycles
2343 */
2344
2345 if((IVD_DECODE_FRAME_OUT == ps_dec->e_frm_out_mode)
2346 && ps_dec->u1_init_dec_flag)
2347 {
2348
2349 ih264d_get_next_display_field(ps_dec, ps_dec->ps_out_buffer,
2350 &(ps_dec->s_disp_op));
2351 if(0 == ps_dec->s_disp_op.u4_error_code)
2352 {
2353 ps_dec->u4_fmt_conv_cur_row = 0;
2354 ps_dec->u4_output_present = 1;
2355 }
2356 }
2357
2358 ih264d_fill_output_struct_from_context(ps_dec, ps_dec_op);
2359
2360 /* If Format conversion is not complete,
2361 complete it here */
2362 if(ps_dec->u4_output_present &&
2363 (ps_dec->u4_fmt_conv_cur_row < ps_dec->s_disp_frame_info.u4_y_ht))
2364 {
2365 ps_dec->u4_fmt_conv_num_rows = ps_dec->s_disp_frame_info.u4_y_ht
2366 - ps_dec->u4_fmt_conv_cur_row;
2367 ih264d_format_convert(ps_dec, &(ps_dec->s_disp_op),
2368 ps_dec->u4_fmt_conv_cur_row,
2369 ps_dec->u4_fmt_conv_num_rows);
2370 ps_dec->u4_fmt_conv_cur_row += ps_dec->u4_fmt_conv_num_rows;
2371 }
2372
2373 ih264d_release_display_field(ps_dec, &(ps_dec->s_disp_op));
2374 }
2375
2376 if(ps_dec->i4_decode_header == 1 && (ps_dec->i4_header_decoded & 1) == 1)
2377 {
2378 ps_dec_op->u4_progressive_frame_flag = 1;
2379 if((NULL != ps_dec->ps_cur_sps) && (1 == (ps_dec->ps_cur_sps->u1_is_valid)))
2380 {
2381 if((0 == ps_dec->ps_sps->u1_frame_mbs_only_flag)
2382 && (0 == ps_dec->ps_sps->u1_mb_aff_flag))
2383 ps_dec_op->u4_progressive_frame_flag = 0;
2384
2385 }
2386 }
2387
2388 /*Data memory barrier instruction,so that yuv write by the library is complete*/
2389 DATA_SYNC();
2390
2391 H264_DEC_DEBUG_PRINT("The num bytes consumed: %d\n",
2392 ps_dec_op->u4_num_bytes_consumed);
2393 return api_ret_value;
2394 }
2395
ih264d_get_version(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2396 WORD32 ih264d_get_version(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
2397 {
2398 char version_string[MAXVERSION_STRLEN + 1];
2399 UWORD32 version_string_len;
2400
2401 ivd_ctl_getversioninfo_ip_t *ps_ip;
2402 ivd_ctl_getversioninfo_op_t *ps_op;
2403
2404 ps_ip = (ivd_ctl_getversioninfo_ip_t *)pv_api_ip;
2405 ps_op = (ivd_ctl_getversioninfo_op_t *)pv_api_op;
2406 UNUSED(dec_hdl);
2407 ps_op->u4_error_code = IV_SUCCESS;
2408
2409 VERSION(version_string, CODEC_NAME, CODEC_RELEASE_TYPE, CODEC_RELEASE_VER,
2410 CODEC_VENDOR);
2411
2412 if((WORD32)ps_ip->u4_version_buffer_size <= 0)
2413 {
2414 ps_op->u4_error_code = IH264D_VERS_BUF_INSUFFICIENT;
2415 return (IV_FAIL);
2416 }
2417
2418 version_string_len = strnlen(version_string, MAXVERSION_STRLEN) + 1;
2419
2420 if(ps_ip->u4_version_buffer_size >= version_string_len) //(WORD32)sizeof(sizeof(version_string)))
2421 {
2422 memcpy(ps_ip->pv_version_buffer, version_string, version_string_len);
2423 ps_op->u4_error_code = IV_SUCCESS;
2424 }
2425 else
2426 {
2427 ps_op->u4_error_code = IH264D_VERS_BUF_INSUFFICIENT;
2428 return IV_FAIL;
2429 }
2430 return (IV_SUCCESS);
2431 }
2432
2433 /*****************************************************************************/
2434 /* */
2435 /* Function Name : ih264d_get_display_frame */
2436 /* */
2437 /* Description : */
2438 /* Inputs :iv_obj_t decoder handle */
2439 /* :pv_api_ip pointer to input structure */
2440 /* :pv_api_op pointer to output structure */
2441 /* Outputs : */
2442 /* Returns : void */
2443 /* */
2444 /* Issues : none */
2445 /* */
2446 /* Revision History: */
2447 /* */
2448 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
2449 /* 22 10 2008 100356 Draft */
2450 /* */
2451 /*****************************************************************************/
ih264d_get_display_frame(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2452 WORD32 ih264d_get_display_frame(iv_obj_t *dec_hdl,
2453 void *pv_api_ip,
2454 void *pv_api_op)
2455 {
2456
2457 UNUSED(dec_hdl);
2458 UNUSED(pv_api_ip);
2459 UNUSED(pv_api_op);
2460 // This function is no longer needed, output is returned in the process()
2461 return IV_FAIL;
2462 }
2463
2464 /*****************************************************************************/
2465 /* */
2466 /* Function Name : ih264d_set_display_frame */
2467 /* */
2468 /* Description : */
2469 /* */
2470 /* Inputs :iv_obj_t decoder handle */
2471 /* :pv_api_ip pointer to input structure */
2472 /* :pv_api_op pointer to output structure */
2473 /* Outputs : */
2474 /* Returns : void */
2475 /* */
2476 /* Issues : none */
2477 /* */
2478 /* Revision History: */
2479 /* */
2480 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
2481 /* 22 10 2008 100356 Draft */
2482 /* */
2483 /*****************************************************************************/
ih264d_set_display_frame(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2484 WORD32 ih264d_set_display_frame(iv_obj_t *dec_hdl,
2485 void *pv_api_ip,
2486 void *pv_api_op)
2487 {
2488
2489 ivd_set_display_frame_ip_t *dec_disp_ip;
2490 ivd_set_display_frame_op_t *dec_disp_op;
2491
2492 UWORD32 i;
2493 dec_struct_t * ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
2494
2495 dec_disp_ip = (ivd_set_display_frame_ip_t *)pv_api_ip;
2496 dec_disp_op = (ivd_set_display_frame_op_t *)pv_api_op;
2497 dec_disp_op->u4_error_code = 0;
2498
2499
2500 ps_dec->u4_num_disp_bufs = 0;
2501 if(ps_dec->u4_share_disp_buf)
2502 {
2503 UWORD32 u4_num_bufs = dec_disp_ip->num_disp_bufs;
2504
2505 u4_num_bufs = MIN(u4_num_bufs, MAX_DISP_BUFS_NEW);
2506
2507 ps_dec->u4_num_disp_bufs = u4_num_bufs;
2508 for(i = 0; i < u4_num_bufs; i++)
2509 {
2510 ps_dec->disp_bufs[i].u4_num_bufs =
2511 dec_disp_ip->s_disp_buffer[i].u4_num_bufs;
2512
2513 ps_dec->disp_bufs[i].buf[0] =
2514 dec_disp_ip->s_disp_buffer[i].pu1_bufs[0];
2515 ps_dec->disp_bufs[i].buf[1] =
2516 dec_disp_ip->s_disp_buffer[i].pu1_bufs[1];
2517 ps_dec->disp_bufs[i].buf[2] =
2518 dec_disp_ip->s_disp_buffer[i].pu1_bufs[2];
2519
2520 ps_dec->disp_bufs[i].u4_bufsize[0] =
2521 dec_disp_ip->s_disp_buffer[i].u4_min_out_buf_size[0];
2522 ps_dec->disp_bufs[i].u4_bufsize[1] =
2523 dec_disp_ip->s_disp_buffer[i].u4_min_out_buf_size[1];
2524 ps_dec->disp_bufs[i].u4_bufsize[2] =
2525 dec_disp_ip->s_disp_buffer[i].u4_min_out_buf_size[2];
2526
2527 }
2528 }
2529 return IV_SUCCESS;
2530
2531 }
2532
2533 /*****************************************************************************/
2534 /* */
2535 /* Function Name : ih264d_set_flush_mode */
2536 /* */
2537 /* Description : */
2538 /* */
2539 /* Inputs :iv_obj_t decoder handle */
2540 /* :pv_api_ip pointer to input structure */
2541 /* :pv_api_op pointer to output structure */
2542 /* Globals : <Does it use any global variables?> */
2543 /* Outputs : */
2544 /* Returns : void */
2545 /* */
2546 /* Issues : none */
2547 /* */
2548 /* Revision History: */
2549 /* */
2550 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
2551 /* 22 10 2008 100356 Draft */
2552 /* */
2553 /*****************************************************************************/
ih264d_set_flush_mode(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2554 WORD32 ih264d_set_flush_mode(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
2555 {
2556 dec_struct_t * ps_dec;
2557 ivd_ctl_flush_op_t *ps_ctl_op = (ivd_ctl_flush_op_t*)pv_api_op;
2558 ps_ctl_op->u4_error_code = 0;
2559
2560 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
2561 UNUSED(pv_api_ip);
2562 /* ! */
2563 /* Signal flush frame control call */
2564 ps_dec->u1_flushfrm = 1;
2565
2566 if(ps_dec->u1_init_dec_flag == 1)
2567 {
2568 ih264d_release_pics_in_dpb((void *)ps_dec, ps_dec->u1_pic_bufs);
2569 ih264d_release_display_bufs(ps_dec);
2570 }
2571
2572 ps_ctl_op->u4_error_code = 0;
2573
2574 return IV_SUCCESS;
2575 }
2576
2577 /*****************************************************************************/
2578 /* */
2579 /* Function Name : ih264d_get_status */
2580 /* */
2581 /* Description : */
2582 /* */
2583 /* Inputs :iv_obj_t decoder handle */
2584 /* :pv_api_ip pointer to input structure */
2585 /* :pv_api_op pointer to output structure */
2586 /* Globals : <Does it use any global variables?> */
2587 /* Outputs : */
2588 /* Returns : void */
2589 /* */
2590 /* Issues : none */
2591 /* */
2592 /* Revision History: */
2593 /* */
2594 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
2595 /* 22 10 2008 100356 Draft */
2596 /* */
2597 /*****************************************************************************/
2598
ih264d_get_status(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2599 WORD32 ih264d_get_status(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
2600 {
2601
2602 UWORD32 i;
2603 dec_struct_t * ps_dec;
2604 UWORD32 pic_wd, pic_ht;
2605 ivd_ctl_getstatus_op_t *ps_ctl_op = (ivd_ctl_getstatus_op_t*)pv_api_op;
2606 UNUSED(pv_api_ip);
2607 ps_ctl_op->u4_error_code = 0;
2608
2609 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
2610
2611
2612 if((NULL != ps_dec->ps_cur_sps) && (1 == (ps_dec->ps_cur_sps->u1_is_valid)))
2613 {
2614 ps_ctl_op->u4_pic_ht = ps_dec->u2_disp_height;
2615 ps_ctl_op->u4_pic_wd = ps_dec->u2_disp_width;
2616
2617 if(0 == ps_dec->u4_share_disp_buf)
2618 {
2619 pic_wd = ps_dec->u2_disp_width;
2620 pic_ht = ps_dec->u2_disp_height;
2621
2622 }
2623 else
2624 {
2625 pic_wd = ps_dec->u2_frm_wd_y;
2626 pic_ht = ps_dec->u2_frm_ht_y;
2627 }
2628 }
2629 else
2630 {
2631 pic_wd = 0;
2632 pic_ht = 0;
2633
2634 ps_ctl_op->u4_pic_ht = pic_wd;
2635 ps_ctl_op->u4_pic_wd = pic_ht;
2636
2637 if(1 == ps_dec->u4_share_disp_buf)
2638 {
2639 pic_wd += (PAD_LEN_Y_H << 1);
2640 pic_ht += (PAD_LEN_Y_V << 2);
2641
2642 }
2643
2644 }
2645
2646 if(ps_dec->u4_app_disp_width > pic_wd)
2647 pic_wd = ps_dec->u4_app_disp_width;
2648 if(0 == ps_dec->u4_share_disp_buf)
2649 ps_ctl_op->u4_num_disp_bufs = 1;
2650 else
2651 {
2652 if((NULL != ps_dec->ps_cur_sps) && (1 == (ps_dec->ps_cur_sps->u1_is_valid)))
2653 {
2654 if((ps_dec->ps_cur_sps->u1_vui_parameters_present_flag == 1) &&
2655 (1 == ps_dec->ps_cur_sps->s_vui.u1_bitstream_restriction_flag))
2656 {
2657 ps_ctl_op->u4_num_disp_bufs =
2658 ps_dec->ps_cur_sps->s_vui.u4_num_reorder_frames + 1;
2659 }
2660 else
2661 {
2662 /*if VUI is not present assume maximum possible refrence frames for the level,
2663 * as max reorder frames*/
2664 ps_ctl_op->u4_num_disp_bufs = ih264d_get_dpb_size(ps_dec->ps_cur_sps);
2665 }
2666
2667 ps_ctl_op->u4_num_disp_bufs +=
2668 ps_dec->ps_cur_sps->u1_num_ref_frames + 1;
2669 }
2670 else
2671 {
2672 ps_ctl_op->u4_num_disp_bufs = 32;
2673 }
2674 ps_ctl_op->u4_num_disp_bufs = MAX(
2675 ps_ctl_op->u4_num_disp_bufs, 6);
2676 ps_ctl_op->u4_num_disp_bufs = MIN(
2677 ps_ctl_op->u4_num_disp_bufs, 32);
2678 }
2679
2680 ps_ctl_op->u4_error_code = ps_dec->i4_error_code;
2681
2682 ps_ctl_op->u4_frame_rate = 0; //make it proper
2683 ps_ctl_op->u4_bit_rate = 0; //make it proper
2684 ps_ctl_op->e_content_type = ps_dec->i4_content_type;
2685 ps_ctl_op->e_output_chroma_format = ps_dec->u1_chroma_format;
2686 ps_ctl_op->u4_min_num_in_bufs = MIN_IN_BUFS;
2687
2688 if(ps_dec->u1_chroma_format == IV_YUV_420P)
2689 {
2690 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_420;
2691 }
2692 else if(ps_dec->u1_chroma_format == IV_YUV_422ILE)
2693 {
2694 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_422ILE;
2695 }
2696 else if(ps_dec->u1_chroma_format == IV_RGB_565)
2697 {
2698 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_RGB565;
2699 }
2700 else if((ps_dec->u1_chroma_format == IV_YUV_420SP_UV)
2701 || (ps_dec->u1_chroma_format == IV_YUV_420SP_VU))
2702 {
2703 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_420SP;
2704 }
2705
2706 else
2707 {
2708 //Invalid chroma format; Error code may be updated, verify in testing if needed
2709 ps_ctl_op->u4_error_code = ERROR_FEATURE_UNAVAIL;
2710 return IV_FAIL;
2711 }
2712
2713 for(i = 0; i < ps_ctl_op->u4_min_num_in_bufs; i++)
2714 {
2715 ps_ctl_op->u4_min_in_buf_size[i] = MAX(256000, pic_wd * pic_ht * 3 / 2);
2716 }
2717
2718 /*!*/
2719 if(ps_dec->u1_chroma_format == IV_YUV_420P)
2720 {
2721 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht);
2722 ps_ctl_op->u4_min_out_buf_size[1] = (pic_wd * pic_ht)
2723 >> 2;
2724 ps_ctl_op->u4_min_out_buf_size[2] = (pic_wd * pic_ht)
2725 >> 2;
2726 }
2727 else if(ps_dec->u1_chroma_format == IV_YUV_422ILE)
2728 {
2729 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht)
2730 * 2;
2731 ps_ctl_op->u4_min_out_buf_size[1] =
2732 ps_ctl_op->u4_min_out_buf_size[2] = 0;
2733 }
2734 else if(ps_dec->u1_chroma_format == IV_RGB_565)
2735 {
2736 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht)
2737 * 2;
2738 ps_ctl_op->u4_min_out_buf_size[1] =
2739 ps_ctl_op->u4_min_out_buf_size[2] = 0;
2740 }
2741 else if((ps_dec->u1_chroma_format == IV_YUV_420SP_UV)
2742 || (ps_dec->u1_chroma_format == IV_YUV_420SP_VU))
2743 {
2744 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht);
2745 ps_ctl_op->u4_min_out_buf_size[1] = (pic_wd * pic_ht)
2746 >> 1;
2747 ps_ctl_op->u4_min_out_buf_size[2] = 0;
2748 }
2749
2750 ps_dec->u4_num_disp_bufs_requested = ps_ctl_op->u4_num_disp_bufs;
2751 return IV_SUCCESS;
2752 }
2753
2754 /*****************************************************************************/
2755 /* */
2756 /* Function Name : ih264d_get_buf_info */
2757 /* */
2758 /* Description : */
2759 /* */
2760 /* Inputs :iv_obj_t decoder handle */
2761 /* :pv_api_ip pointer to input structure */
2762 /* :pv_api_op pointer to output structure */
2763 /* Globals : <Does it use any global variables?> */
2764 /* Outputs : */
2765 /* Returns : void */
2766 /* */
2767 /* Issues : none */
2768 /* */
2769 /* Revision History: */
2770 /* */
2771 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
2772 /* 22 10 2008 100356 Draft */
2773 /* */
2774 /*****************************************************************************/
ih264d_get_buf_info(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2775 WORD32 ih264d_get_buf_info(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
2776 {
2777
2778 dec_struct_t * ps_dec;
2779 UWORD8 i = 0; // Default for 420P format
2780 UWORD16 pic_wd, pic_ht;
2781 ivd_ctl_getbufinfo_op_t *ps_ctl_op =
2782 (ivd_ctl_getbufinfo_op_t*)pv_api_op;
2783 UNUSED(pv_api_ip);
2784 ps_ctl_op->u4_error_code = 0;
2785
2786 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
2787
2788 ps_ctl_op->u4_min_num_in_bufs = MIN_IN_BUFS;
2789 if(ps_dec->u1_chroma_format == IV_YUV_420P)
2790 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_420;
2791 else if(ps_dec->u1_chroma_format == IV_YUV_422ILE)
2792 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_422ILE;
2793 else if(ps_dec->u1_chroma_format == IV_RGB_565)
2794 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_RGB565;
2795 else if((ps_dec->u1_chroma_format == IV_YUV_420SP_UV)
2796 || (ps_dec->u1_chroma_format == IV_YUV_420SP_VU))
2797 ps_ctl_op->u4_min_num_out_bufs = MIN_OUT_BUFS_420SP;
2798
2799 else
2800 {
2801 //Invalid chroma format; Error code may be updated, verify in testing if needed
2802 return IV_FAIL;
2803 }
2804
2805 ps_ctl_op->u4_num_disp_bufs = 1;
2806
2807
2808 pic_wd = 0;
2809 pic_ht = 0;
2810
2811 if(ps_dec->i4_header_decoded == 3)
2812 {
2813
2814 if(0 == ps_dec->u4_share_disp_buf)
2815 {
2816 pic_wd = ps_dec->u2_disp_width;
2817 pic_ht = ps_dec->u2_disp_height;
2818
2819 }
2820 else
2821 {
2822 pic_wd = ps_dec->u2_frm_wd_y;
2823 pic_ht = ps_dec->u2_frm_ht_y;
2824 }
2825
2826 }
2827
2828 for(i = 0; i < ps_ctl_op->u4_min_num_in_bufs; i++)
2829 {
2830 ps_ctl_op->u4_min_in_buf_size[i] = MAX(256000, pic_wd * pic_ht * 3 / 2);
2831 }
2832 if((WORD32)ps_dec->u4_app_disp_width > pic_wd)
2833 pic_wd = ps_dec->u4_app_disp_width;
2834
2835 if(0 == ps_dec->u4_share_disp_buf)
2836 ps_ctl_op->u4_num_disp_bufs = 1;
2837 else
2838 {
2839 if((NULL != ps_dec->ps_cur_sps) && (1 == (ps_dec->ps_cur_sps->u1_is_valid)))
2840 {
2841 if((ps_dec->ps_cur_sps->u1_vui_parameters_present_flag == 1) &&
2842 (1 == ps_dec->ps_cur_sps->s_vui.u1_bitstream_restriction_flag))
2843 {
2844 ps_ctl_op->u4_num_disp_bufs =
2845 ps_dec->ps_cur_sps->s_vui.u4_num_reorder_frames + 1;
2846 }
2847 else
2848 {
2849 /*if VUI is not present assume maximum possible refrence frames for the level,
2850 * as max reorder frames*/
2851 ps_ctl_op->u4_num_disp_bufs = ih264d_get_dpb_size(ps_dec->ps_cur_sps);
2852 }
2853
2854 ps_ctl_op->u4_num_disp_bufs +=
2855 ps_dec->ps_cur_sps->u1_num_ref_frames + 1;
2856
2857 }
2858 else
2859 {
2860 ps_ctl_op->u4_num_disp_bufs = 32;
2861
2862 }
2863
2864 ps_ctl_op->u4_num_disp_bufs = MAX(
2865 ps_ctl_op->u4_num_disp_bufs, 6);
2866 ps_ctl_op->u4_num_disp_bufs = MIN(
2867 ps_ctl_op->u4_num_disp_bufs, 32);
2868 }
2869
2870 /*!*/
2871 if(ps_dec->u1_chroma_format == IV_YUV_420P)
2872 {
2873 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht);
2874 ps_ctl_op->u4_min_out_buf_size[1] = (pic_wd * pic_ht)
2875 >> 2;
2876 ps_ctl_op->u4_min_out_buf_size[2] = (pic_wd * pic_ht)
2877 >> 2;
2878 }
2879 else if(ps_dec->u1_chroma_format == IV_YUV_422ILE)
2880 {
2881 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht)
2882 * 2;
2883 ps_ctl_op->u4_min_out_buf_size[1] =
2884 ps_ctl_op->u4_min_out_buf_size[2] = 0;
2885 }
2886 else if(ps_dec->u1_chroma_format == IV_RGB_565)
2887 {
2888 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht)
2889 * 2;
2890 ps_ctl_op->u4_min_out_buf_size[1] =
2891 ps_ctl_op->u4_min_out_buf_size[2] = 0;
2892 }
2893 else if((ps_dec->u1_chroma_format == IV_YUV_420SP_UV)
2894 || (ps_dec->u1_chroma_format == IV_YUV_420SP_VU))
2895 {
2896 ps_ctl_op->u4_min_out_buf_size[0] = (pic_wd * pic_ht);
2897 ps_ctl_op->u4_min_out_buf_size[1] = (pic_wd * pic_ht)
2898 >> 1;
2899 ps_ctl_op->u4_min_out_buf_size[2] = 0;
2900 }
2901 ps_dec->u4_num_disp_bufs_requested = ps_ctl_op->u4_num_disp_bufs;
2902
2903 return IV_SUCCESS;
2904 }
2905
2906 /*****************************************************************************/
2907 /* */
2908 /* Function Name : ih264d_set_params */
2909 /* */
2910 /* Description : */
2911 /* */
2912 /* Inputs :iv_obj_t decoder handle */
2913 /* :pv_api_ip pointer to input structure */
2914 /* :pv_api_op pointer to output structure */
2915 /* Outputs : */
2916 /* Returns : void */
2917 /* */
2918 /* Issues : none */
2919 /* */
2920 /* Revision History: */
2921 /* */
2922 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
2923 /* 22 10 2008 100356 Draft */
2924 /* */
2925 /*****************************************************************************/
ih264d_set_params(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)2926 WORD32 ih264d_set_params(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
2927 {
2928
2929 dec_struct_t * ps_dec;
2930 WORD32 ret = IV_SUCCESS;
2931
2932 ivd_ctl_set_config_ip_t *ps_ctl_ip =
2933 (ivd_ctl_set_config_ip_t *)pv_api_ip;
2934 ivd_ctl_set_config_op_t *ps_ctl_op =
2935 (ivd_ctl_set_config_op_t *)pv_api_op;
2936
2937 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
2938
2939 ps_dec->u4_skip_frm_mask = 0;
2940
2941 ps_ctl_op->u4_error_code = 0;
2942
2943 ps_dec->i4_app_skip_mode = ps_ctl_ip->e_frm_skip_mode;
2944
2945 /*Is it really supported test it when you so the corner testing using test app*/
2946
2947 if(ps_ctl_ip->e_frm_skip_mode != IVD_SKIP_NONE)
2948 {
2949
2950 if(ps_ctl_ip->e_frm_skip_mode == IVD_SKIP_P)
2951 ps_dec->u4_skip_frm_mask |= 1 << P_SLC_BIT;
2952 else if(ps_ctl_ip->e_frm_skip_mode == IVD_SKIP_B)
2953 ps_dec->u4_skip_frm_mask |= 1 << B_SLC_BIT;
2954 else if(ps_ctl_ip->e_frm_skip_mode == IVD_SKIP_PB)
2955 {
2956 ps_dec->u4_skip_frm_mask |= 1 << B_SLC_BIT;
2957 ps_dec->u4_skip_frm_mask |= 1 << P_SLC_BIT;
2958 }
2959 else if(ps_ctl_ip->e_frm_skip_mode == IVD_SKIP_I)
2960 ps_dec->u4_skip_frm_mask |= 1 << I_SLC_BIT;
2961 else
2962 {
2963 //dynamic parameter not supported
2964 //Put an appropriate error code to return the error..
2965 //when you do the error code tests and after that remove this comment
2966 ps_ctl_op->u4_error_code = (1 << IVD_UNSUPPORTEDPARAM);
2967 ret = IV_FAIL;
2968 }
2969 }
2970
2971 if((0 != ps_dec->u4_app_disp_width)
2972 && (ps_ctl_ip->u4_disp_wd
2973 != ps_dec->u4_app_disp_width))
2974 {
2975 ps_ctl_op->u4_error_code |= (1 << IVD_UNSUPPORTEDPARAM);
2976 ps_ctl_op->u4_error_code |= ERROR_DISP_WIDTH_INVALID;
2977 ret = IV_FAIL;
2978 }
2979 else
2980 {
2981 if(ps_ctl_ip->u4_disp_wd >= ps_dec->u2_pic_wd)
2982 {
2983 ps_dec->u4_app_disp_width = ps_ctl_ip->u4_disp_wd;
2984 }
2985 else if(0 == ps_dec->i4_header_decoded)
2986 {
2987 ps_dec->u4_app_disp_width = ps_ctl_ip->u4_disp_wd;
2988 }
2989 else if(ps_ctl_ip->u4_disp_wd == 0)
2990 {
2991 ps_dec->u4_app_disp_width = 0;
2992 }
2993 else
2994 {
2995 /*
2996 * Set the display width to zero. This will ensure that the wrong value we had stored (0xFFFFFFFF)
2997 * does not propogate.
2998 */
2999 ps_dec->u4_app_disp_width = 0;
3000 ps_ctl_op->u4_error_code |= (1 << IVD_UNSUPPORTEDPARAM);
3001 ps_ctl_op->u4_error_code |= ERROR_DISP_WIDTH_INVALID;
3002 ret = IV_FAIL;
3003 }
3004 }
3005 if(ps_ctl_ip->e_vid_dec_mode == IVD_DECODE_FRAME)
3006 ps_dec->i4_decode_header = 0;
3007 else if(ps_ctl_ip->e_vid_dec_mode == IVD_DECODE_HEADER)
3008 ps_dec->i4_decode_header = 1;
3009 else
3010 {
3011 ps_ctl_op->u4_error_code = (1 << IVD_UNSUPPORTEDPARAM);
3012 ps_dec->i4_decode_header = 1;
3013 ret = IV_FAIL;
3014 }
3015 ps_dec->e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
3016
3017 if((ps_ctl_ip->e_frm_out_mode != IVD_DECODE_FRAME_OUT) &&
3018 (ps_ctl_ip->e_frm_out_mode != IVD_DISPLAY_FRAME_OUT))
3019 {
3020 ps_ctl_op->u4_error_code = (1 << IVD_UNSUPPORTEDPARAM);
3021 ret = IV_FAIL;
3022 }
3023 ps_dec->e_frm_out_mode = ps_ctl_ip->e_frm_out_mode;
3024 return ret;
3025
3026 }
3027
3028 /*****************************************************************************/
3029 /* */
3030 /* Function Name : ih264d_set_default_params */
3031 /* */
3032 /* Description : */
3033 /* */
3034 /* Inputs :iv_obj_t decoder handle */
3035 /* :pv_api_ip pointer to input structure */
3036 /* :pv_api_op pointer to output structure */
3037 /* Outputs : */
3038 /* Returns : void */
3039 /* */
3040 /* Issues : none */
3041 /* */
3042 /* Revision History: */
3043 /* */
3044 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
3045 /* 08 08 2011 100421 Copied from set_params */
3046 /* */
3047 /*****************************************************************************/
ih264d_set_default_params(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3048 WORD32 ih264d_set_default_params(iv_obj_t *dec_hdl,
3049 void *pv_api_ip,
3050 void *pv_api_op)
3051 {
3052
3053 dec_struct_t * ps_dec;
3054 WORD32 ret = IV_SUCCESS;
3055
3056 ivd_ctl_set_config_op_t *ps_ctl_op =
3057 (ivd_ctl_set_config_op_t *)pv_api_op;
3058 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
3059 UNUSED(pv_api_ip);
3060
3061
3062 {
3063 ps_dec->u4_app_disp_width = 0;
3064 ps_dec->u4_skip_frm_mask = 0;
3065 ps_dec->i4_decode_header = 1;
3066
3067 ps_ctl_op->u4_error_code = 0;
3068 }
3069
3070
3071 return ret;
3072 }
3073 /*****************************************************************************/
3074 /* */
3075 /* Function Name : ih264d_reset */
3076 /* */
3077 /* Description : */
3078 /* */
3079 /* Inputs :iv_obj_t decoder handle */
3080 /* :pv_api_ip pointer to input structure */
3081 /* :pv_api_op pointer to output structure */
3082 /* Globals : <Does it use any global variables?> */
3083 /* Outputs : */
3084 /* Returns : void */
3085 /* */
3086 /* Issues : none */
3087 /* */
3088 /* Revision History: */
3089 /* */
3090 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
3091 /* 22 10 2008 100356 Draft */
3092 /* */
3093 /*****************************************************************************/
ih264d_delete(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3094 WORD32 ih264d_delete(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
3095 {
3096 dec_struct_t *ps_dec;
3097 ih264d_delete_ip_t *ps_ip = (ih264d_delete_ip_t *)pv_api_ip;
3098 ih264d_delete_op_t *ps_op = (ih264d_delete_op_t *)pv_api_op;
3099
3100 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
3101 UNUSED(ps_ip);
3102 ps_op->s_ivd_delete_op_t.u4_error_code = 0;
3103 ih264d_free_dynamic_bufs(ps_dec);
3104 ih264d_free_static_bufs(dec_hdl);
3105 return IV_SUCCESS;
3106 }
3107 /*****************************************************************************/
3108 /* */
3109 /* Function Name : ih264d_reset */
3110 /* */
3111 /* Description : */
3112 /* */
3113 /* Inputs :iv_obj_t decoder handle */
3114 /* :pv_api_ip pointer to input structure */
3115 /* :pv_api_op pointer to output structure */
3116 /* Globals : <Does it use any global variables?> */
3117 /* Outputs : */
3118 /* Returns : void */
3119 /* */
3120 /* Issues : none */
3121 /* */
3122 /* Revision History: */
3123 /* */
3124 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
3125 /* 22 10 2008 100356 Draft */
3126 /* */
3127 /*****************************************************************************/
ih264d_reset(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3128 WORD32 ih264d_reset(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
3129 {
3130 dec_struct_t * ps_dec;
3131 ivd_ctl_reset_op_t *ps_ctl_op = (ivd_ctl_reset_op_t *)pv_api_op;
3132 UNUSED(pv_api_ip);
3133 ps_ctl_op->u4_error_code = 0;
3134
3135 ps_dec = (dec_struct_t *)(dec_hdl->pv_codec_handle);
3136
3137 if(ps_dec != NULL)
3138 {
3139 ih264d_init_decoder(ps_dec);
3140 }
3141 else
3142 {
3143 H264_DEC_DEBUG_PRINT(
3144 "\nReset called without Initializing the decoder\n");
3145 ps_ctl_op->u4_error_code = ERROR_INIT_NOT_DONE;
3146 }
3147
3148 return IV_SUCCESS;
3149 }
3150
3151 /*****************************************************************************/
3152 /* */
3153 /* Function Name : ih264d_ctl */
3154 /* */
3155 /* Description : */
3156 /* */
3157 /* Inputs :iv_obj_t decoder handle */
3158 /* :pv_api_ip pointer to input structure */
3159 /* :pv_api_op pointer to output structure */
3160 /* Outputs : */
3161 /* Returns : void */
3162 /* */
3163 /* Issues : none */
3164 /* */
3165 /* Revision History: */
3166 /* */
3167 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
3168 /* 22 10 2008 100356 Draft */
3169 /* */
3170 /*****************************************************************************/
ih264d_ctl(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3171 WORD32 ih264d_ctl(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
3172 {
3173 ivd_ctl_set_config_ip_t *ps_ctl_ip;
3174 ivd_ctl_set_config_op_t *ps_ctl_op;
3175 WORD32 ret = IV_SUCCESS;
3176 UWORD32 subcommand;
3177 dec_struct_t *ps_dec = dec_hdl->pv_codec_handle;
3178
3179 if(ps_dec->init_done != 1)
3180 {
3181 //Return proper Error Code
3182 return IV_FAIL;
3183 }
3184 ps_ctl_ip = (ivd_ctl_set_config_ip_t*)pv_api_ip;
3185 ps_ctl_op = (ivd_ctl_set_config_op_t*)pv_api_op;
3186 ps_ctl_op->u4_error_code = 0;
3187 subcommand = ps_ctl_ip->e_sub_cmd;
3188
3189 switch(subcommand)
3190 {
3191 case IVD_CMD_CTL_GETPARAMS:
3192 ret = ih264d_get_status(dec_hdl, (void *)pv_api_ip,
3193 (void *)pv_api_op);
3194 break;
3195 case IVD_CMD_CTL_SETPARAMS:
3196 ret = ih264d_set_params(dec_hdl, (void *)pv_api_ip,
3197 (void *)pv_api_op);
3198 break;
3199 case IVD_CMD_CTL_RESET:
3200 ret = ih264d_reset(dec_hdl, (void *)pv_api_ip, (void *)pv_api_op);
3201 break;
3202 case IVD_CMD_CTL_SETDEFAULT:
3203 ret = ih264d_set_default_params(dec_hdl, (void *)pv_api_ip,
3204 (void *)pv_api_op);
3205 break;
3206 case IVD_CMD_CTL_FLUSH:
3207 ret = ih264d_set_flush_mode(dec_hdl, (void *)pv_api_ip,
3208 (void *)pv_api_op);
3209 break;
3210 case IVD_CMD_CTL_GETBUFINFO:
3211 ret = ih264d_get_buf_info(dec_hdl, (void *)pv_api_ip,
3212 (void *)pv_api_op);
3213 break;
3214 case IVD_CMD_CTL_GETVERSION:
3215 ret = ih264d_get_version(dec_hdl, (void *)pv_api_ip,
3216 (void *)pv_api_op);
3217 break;
3218 case IH264D_CMD_CTL_DEGRADE:
3219 ret = ih264d_set_degrade(dec_hdl, (void *)pv_api_ip,
3220 (void *)pv_api_op);
3221 break;
3222
3223 case IH264D_CMD_CTL_SET_NUM_CORES:
3224 ret = ih264d_set_num_cores(dec_hdl, (void *)pv_api_ip,
3225 (void *)pv_api_op);
3226 break;
3227 case IH264D_CMD_CTL_GET_BUFFER_DIMENSIONS:
3228 ret = ih264d_get_frame_dimensions(dec_hdl, (void *)pv_api_ip,
3229 (void *)pv_api_op);
3230 break;
3231 case IH264D_CMD_CTL_SET_PROCESSOR:
3232 ret = ih264d_set_processor(dec_hdl, (void *)pv_api_ip,
3233 (void *)pv_api_op);
3234 break;
3235 default:
3236 H264_DEC_DEBUG_PRINT("\ndo nothing\n")
3237 ;
3238 break;
3239 }
3240
3241 return ret;
3242 }
3243 /*****************************************************************************/
3244 /* */
3245 /* Function Name : ih264d_rel_display_frame */
3246 /* */
3247 /* Description : */
3248 /* */
3249 /* Inputs :iv_obj_t decoder handle */
3250 /* :pv_api_ip pointer to input structure */
3251 /* :pv_api_op pointer to output structure */
3252 /* Outputs : */
3253 /* Returns : void */
3254 /* */
3255 /* Issues : none */
3256 /* */
3257 /* Revision History: */
3258 /* */
3259 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
3260 /* 22 10 2008 100356 Draft */
3261 /* */
3262 /*****************************************************************************/
ih264d_rel_display_frame(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3263 WORD32 ih264d_rel_display_frame(iv_obj_t *dec_hdl,
3264 void *pv_api_ip,
3265 void *pv_api_op)
3266 {
3267
3268 ivd_rel_display_frame_ip_t *ps_rel_ip;
3269 ivd_rel_display_frame_op_t *ps_rel_op;
3270 UWORD32 buf_released = 0;
3271
3272 UWORD32 u4_ts = -1;
3273 dec_struct_t *ps_dec = dec_hdl->pv_codec_handle;
3274
3275 ps_rel_ip = (ivd_rel_display_frame_ip_t *)pv_api_ip;
3276 ps_rel_op = (ivd_rel_display_frame_op_t *)pv_api_op;
3277 ps_rel_op->u4_error_code = 0;
3278 u4_ts = ps_rel_ip->u4_disp_buf_id;
3279
3280 if(0 == ps_dec->u4_share_disp_buf)
3281 {
3282 ps_dec->u4_disp_buf_mapping[u4_ts] = 0;
3283 ps_dec->u4_disp_buf_to_be_freed[u4_ts] = 0;
3284 return IV_SUCCESS;
3285 }
3286
3287 if(ps_dec->pv_pic_buf_mgr != NULL)
3288 {
3289 if(1 == ps_dec->u4_disp_buf_mapping[u4_ts])
3290 {
3291 ih264_buf_mgr_release((buf_mgr_t *)ps_dec->pv_pic_buf_mgr,
3292 ps_rel_ip->u4_disp_buf_id,
3293 BUF_MGR_IO);
3294 ps_dec->u4_disp_buf_mapping[u4_ts] = 0;
3295 buf_released = 1;
3296 }
3297 }
3298
3299 if((1 == ps_dec->u4_share_disp_buf) && (0 == buf_released))
3300 ps_dec->u4_disp_buf_to_be_freed[u4_ts] = 1;
3301
3302 return IV_SUCCESS;
3303 }
3304
3305 /**
3306 *******************************************************************************
3307 *
3308 * @brief
3309 * Sets degrade params
3310 *
3311 * @par Description:
3312 * Sets degrade params.
3313 * Refer to ih264d_ctl_degrade_ip_t definition for details
3314 *
3315 * @param[in] ps_codec_obj
3316 * Pointer to codec object at API level
3317 *
3318 * @param[in] pv_api_ip
3319 * Pointer to input argument structure
3320 *
3321 * @param[out] pv_api_op
3322 * Pointer to output argument structure
3323 *
3324 * @returns Status
3325 *
3326 * @remarks
3327 *
3328 *
3329 *******************************************************************************
3330 */
3331
ih264d_set_degrade(iv_obj_t * ps_codec_obj,void * pv_api_ip,void * pv_api_op)3332 WORD32 ih264d_set_degrade(iv_obj_t *ps_codec_obj,
3333 void *pv_api_ip,
3334 void *pv_api_op)
3335 {
3336 ih264d_ctl_degrade_ip_t *ps_ip;
3337 ih264d_ctl_degrade_op_t *ps_op;
3338 dec_struct_t *ps_codec = (dec_struct_t *)ps_codec_obj->pv_codec_handle;
3339
3340 ps_ip = (ih264d_ctl_degrade_ip_t *)pv_api_ip;
3341 ps_op = (ih264d_ctl_degrade_op_t *)pv_api_op;
3342
3343 ps_codec->i4_degrade_type = ps_ip->i4_degrade_type;
3344 ps_codec->i4_nondegrade_interval = ps_ip->i4_nondegrade_interval;
3345 ps_codec->i4_degrade_pics = ps_ip->i4_degrade_pics;
3346
3347 ps_op->u4_error_code = 0;
3348 ps_codec->i4_degrade_pic_cnt = 0;
3349
3350 return IV_SUCCESS;
3351 }
3352
ih264d_get_frame_dimensions(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3353 WORD32 ih264d_get_frame_dimensions(iv_obj_t *dec_hdl,
3354 void *pv_api_ip,
3355 void *pv_api_op)
3356 {
3357 ih264d_ctl_get_frame_dimensions_ip_t *ps_ip;
3358 ih264d_ctl_get_frame_dimensions_op_t *ps_op;
3359 dec_struct_t *ps_dec = dec_hdl->pv_codec_handle;
3360 UWORD32 disp_wd, disp_ht, buffer_wd, buffer_ht, x_offset, y_offset;
3361
3362 ps_ip = (ih264d_ctl_get_frame_dimensions_ip_t *)pv_api_ip;
3363
3364 ps_op = (ih264d_ctl_get_frame_dimensions_op_t *)pv_api_op;
3365 UNUSED(ps_ip);
3366 if((NULL != ps_dec->ps_cur_sps) && (1 == (ps_dec->ps_cur_sps->u1_is_valid)))
3367 {
3368 disp_wd = ps_dec->u2_disp_width;
3369 disp_ht = ps_dec->u2_disp_height;
3370
3371 if(0 == ps_dec->u4_share_disp_buf)
3372 {
3373 buffer_wd = disp_wd;
3374 buffer_ht = disp_ht;
3375 }
3376 else
3377 {
3378 buffer_wd = ps_dec->u2_frm_wd_y;
3379 buffer_ht = ps_dec->u2_frm_ht_y;
3380 }
3381 }
3382 else
3383 {
3384 disp_wd = 0;
3385 disp_ht = 0;
3386
3387 if(0 == ps_dec->u4_share_disp_buf)
3388 {
3389 buffer_wd = disp_wd;
3390 buffer_ht = disp_ht;
3391 }
3392 else
3393 {
3394 buffer_wd = ALIGN16(disp_wd) + (PAD_LEN_Y_H << 1);
3395 buffer_ht = ALIGN16(disp_ht) + (PAD_LEN_Y_V << 2);
3396 }
3397 }
3398 if(ps_dec->u4_app_disp_width > buffer_wd)
3399 buffer_wd = ps_dec->u4_app_disp_width;
3400
3401 if(0 == ps_dec->u4_share_disp_buf)
3402 {
3403 x_offset = 0;
3404 y_offset = 0;
3405 }
3406 else
3407 {
3408 y_offset = (PAD_LEN_Y_V << 1);
3409 x_offset = PAD_LEN_Y_H;
3410
3411 if((NULL != ps_dec->ps_sps) && (1 == (ps_dec->ps_sps->u1_is_valid))
3412 && (0 != ps_dec->u2_crop_offset_y))
3413 {
3414 y_offset += ps_dec->u2_crop_offset_y / ps_dec->u2_frm_wd_y;
3415 x_offset += ps_dec->u2_crop_offset_y % ps_dec->u2_frm_wd_y;
3416 }
3417 }
3418
3419 ps_op->u4_disp_wd[0] = disp_wd;
3420 ps_op->u4_disp_ht[0] = disp_ht;
3421 ps_op->u4_buffer_wd[0] = buffer_wd;
3422 ps_op->u4_buffer_ht[0] = buffer_ht;
3423 ps_op->u4_x_offset[0] = x_offset;
3424 ps_op->u4_y_offset[0] = y_offset;
3425
3426 ps_op->u4_disp_wd[1] = ps_op->u4_disp_wd[2] = ((ps_op->u4_disp_wd[0] + 1)
3427 >> 1);
3428 ps_op->u4_disp_ht[1] = ps_op->u4_disp_ht[2] = ((ps_op->u4_disp_ht[0] + 1)
3429 >> 1);
3430 ps_op->u4_buffer_wd[1] = ps_op->u4_buffer_wd[2] = (ps_op->u4_buffer_wd[0]
3431 >> 1);
3432 ps_op->u4_buffer_ht[1] = ps_op->u4_buffer_ht[2] = (ps_op->u4_buffer_ht[0]
3433 >> 1);
3434 ps_op->u4_x_offset[1] = ps_op->u4_x_offset[2] =
3435 (ps_op->u4_x_offset[0] >> 1);
3436 ps_op->u4_y_offset[1] = ps_op->u4_y_offset[2] =
3437 (ps_op->u4_y_offset[0] >> 1);
3438
3439 if((ps_dec->u1_chroma_format == IV_YUV_420SP_UV)
3440 || (ps_dec->u1_chroma_format == IV_YUV_420SP_VU))
3441 {
3442 ps_op->u4_disp_wd[2] = 0;
3443 ps_op->u4_disp_ht[2] = 0;
3444 ps_op->u4_buffer_wd[2] = 0;
3445 ps_op->u4_buffer_ht[2] = 0;
3446 ps_op->u4_x_offset[2] = 0;
3447 ps_op->u4_y_offset[2] = 0;
3448
3449 ps_op->u4_disp_wd[1] <<= 1;
3450 ps_op->u4_buffer_wd[1] <<= 1;
3451 ps_op->u4_x_offset[1] <<= 1;
3452 }
3453
3454 return IV_SUCCESS;
3455
3456 }
3457
ih264d_set_num_cores(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3458 WORD32 ih264d_set_num_cores(iv_obj_t *dec_hdl, void *pv_api_ip, void *pv_api_op)
3459 {
3460 ih264d_ctl_set_num_cores_ip_t *ps_ip;
3461 ih264d_ctl_set_num_cores_op_t *ps_op;
3462 dec_struct_t *ps_dec = dec_hdl->pv_codec_handle;
3463
3464 ps_ip = (ih264d_ctl_set_num_cores_ip_t *)pv_api_ip;
3465 ps_op = (ih264d_ctl_set_num_cores_op_t *)pv_api_op;
3466 ps_op->u4_error_code = 0;
3467 ps_dec->u4_num_cores = ps_ip->u4_num_cores;
3468 if(ps_dec->u4_num_cores == 1)
3469 {
3470 ps_dec->u1_separate_parse = 0;
3471 }
3472 else
3473 {
3474 ps_dec->u1_separate_parse = 1;
3475 }
3476
3477 /*using only upto three threads currently*/
3478 if(ps_dec->u4_num_cores > 3)
3479 ps_dec->u4_num_cores = 3;
3480
3481 return IV_SUCCESS;
3482 }
3483
ih264d_fill_output_struct_from_context(dec_struct_t * ps_dec,ivd_video_decode_op_t * ps_dec_op)3484 void ih264d_fill_output_struct_from_context(dec_struct_t *ps_dec,
3485 ivd_video_decode_op_t *ps_dec_op)
3486 {
3487 if((ps_dec_op->u4_error_code & 0xff)
3488 != ERROR_DYNAMIC_RESOLUTION_NOT_SUPPORTED)
3489 {
3490 ps_dec_op->u4_pic_wd = (UWORD32)ps_dec->u2_disp_width;
3491 ps_dec_op->u4_pic_ht = (UWORD32)ps_dec->u2_disp_height;
3492 }
3493 ps_dec_op->e_pic_type = ps_dec->i4_frametype;
3494
3495 ps_dec_op->u4_new_seq = 0;
3496 ps_dec_op->u4_output_present = ps_dec->u4_output_present;
3497 ps_dec_op->u4_progressive_frame_flag =
3498 ps_dec->s_disp_op.u4_progressive_frame_flag;
3499
3500 ps_dec_op->u4_is_ref_flag = 1;
3501 if(ps_dec_op->u4_frame_decoded_flag)
3502 {
3503 if(ps_dec->ps_cur_slice->u1_nal_ref_idc == 0)
3504 ps_dec_op->u4_is_ref_flag = 0;
3505 }
3506
3507 ps_dec_op->e_output_format = ps_dec->s_disp_op.e_output_format;
3508 ps_dec_op->s_disp_frm_buf = ps_dec->s_disp_op.s_disp_frm_buf;
3509 ps_dec_op->e4_fld_type = ps_dec->s_disp_op.e4_fld_type;
3510 ps_dec_op->u4_ts = ps_dec->s_disp_op.u4_ts;
3511 ps_dec_op->u4_disp_buf_id = ps_dec->s_disp_op.u4_disp_buf_id;
3512 }
3513
3514 /*****************************************************************************/
3515 /* */
3516 /* Function Name : ih264d_api_function */
3517 /* */
3518 /* Description : */
3519 /* */
3520 /* Inputs :iv_obj_t decoder handle */
3521 /* :pv_api_ip pointer to input structure */
3522 /* :pv_api_op pointer to output structure */
3523 /* Outputs : */
3524 /* Returns : void */
3525 /* */
3526 /* Issues : none */
3527 /* */
3528 /* Revision History: */
3529 /* */
3530 /* DD MM YYYY Author(s) Changes (Describe the changes made) */
3531 /* 22 10 2008 100356 Draft */
3532 /* */
3533 /*****************************************************************************/
ih264d_api_function(iv_obj_t * dec_hdl,void * pv_api_ip,void * pv_api_op)3534 IV_API_CALL_STATUS_T ih264d_api_function(iv_obj_t *dec_hdl,
3535 void *pv_api_ip,
3536 void *pv_api_op)
3537 {
3538 UWORD32 command;
3539 UWORD32 *pu2_ptr_cmd;
3540 UWORD32 u4_api_ret;
3541 IV_API_CALL_STATUS_T e_status;
3542 e_status = api_check_struct_sanity(dec_hdl, pv_api_ip, pv_api_op);
3543
3544 if(e_status != IV_SUCCESS)
3545 {
3546 UWORD32 *ptr_err;
3547
3548 ptr_err = (UWORD32 *)pv_api_op;
3549 UNUSED(ptr_err);
3550 H264_DEC_DEBUG_PRINT("error code = %d\n", *(ptr_err + 1));
3551 return IV_FAIL;
3552 }
3553
3554 pu2_ptr_cmd = (UWORD32 *)pv_api_ip;
3555 pu2_ptr_cmd++;
3556
3557 command = *pu2_ptr_cmd;
3558 // H264_DEC_DEBUG_PRINT("inside lib = %d\n",command);
3559 switch(command)
3560 {
3561
3562 case IVD_CMD_CREATE:
3563 u4_api_ret = ih264d_create(dec_hdl, (void *)pv_api_ip,
3564 (void *)pv_api_op);
3565 break;
3566 case IVD_CMD_DELETE:
3567 u4_api_ret = ih264d_delete(dec_hdl, (void *)pv_api_ip,
3568 (void *)pv_api_op);
3569 break;
3570
3571 case IVD_CMD_VIDEO_DECODE:
3572 u4_api_ret = ih264d_video_decode(dec_hdl, (void *)pv_api_ip,
3573 (void *)pv_api_op);
3574 break;
3575
3576 case IVD_CMD_GET_DISPLAY_FRAME:
3577 u4_api_ret = ih264d_get_display_frame(dec_hdl, (void *)pv_api_ip,
3578 (void *)pv_api_op);
3579
3580 break;
3581
3582 case IVD_CMD_SET_DISPLAY_FRAME:
3583 u4_api_ret = ih264d_set_display_frame(dec_hdl, (void *)pv_api_ip,
3584 (void *)pv_api_op);
3585
3586 break;
3587
3588 case IVD_CMD_REL_DISPLAY_FRAME:
3589 u4_api_ret = ih264d_rel_display_frame(dec_hdl, (void *)pv_api_ip,
3590 (void *)pv_api_op);
3591 break;
3592
3593 case IVD_CMD_VIDEO_CTL:
3594 u4_api_ret = ih264d_ctl(dec_hdl, (void *)pv_api_ip,
3595 (void *)pv_api_op);
3596 break;
3597 default:
3598 u4_api_ret = IV_FAIL;
3599 break;
3600 }
3601
3602 return u4_api_ret;
3603 }
3604