Home | History | Annotate | Download | only in decoder
      1 /******************************************************************************
      2 *
      3 * Copyright (C) 2012 Ittiam Systems Pvt Ltd, Bangalore
      4 *
      5 * Licensed under the Apache License, Version 2.0 (the "License");
      6 * you may not use this file except in compliance with the License.
      7 * You may obtain a copy of the License at:
      8 *
      9 * http://www.apache.org/licenses/LICENSE-2.0
     10 *
     11 * Unless required by applicable law or agreed to in writing, software
     12 * distributed under the License is distributed on an "AS IS" BASIS,
     13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     14 * See the License for the specific language governing permissions and
     15 * limitations under the License.
     16 *
     17 ******************************************************************************/
     18 /*****************************************************************************/
     19 /*                                                                           */
     20 /*  File Name         : main.c                                               */
     21 /*                                                                           */
     22 /*  Description       : Contains an application that demonstrates use of HEVC*/
     23 /*                      decoder API                                          */
     24 /*                                                                           */
     25 /*  List of Functions :                                                      */
     26 /*                                                                           */
     27 /*  Issues / Problems : None                                                 */
     28 /*                                                                           */
     29 /*  Revision History  :                                                      */
     30 /*                                                                           */
     31 /*         DD MM YYYY   Author(s)       Changes                              */
     32 /*         07 09 2012   Harish          Initial Version                      */
     33 /*****************************************************************************/
     34 /*****************************************************************************/
     35 /* File Includes                                                             */
     36 /*****************************************************************************/
     37 #include <stdio.h>
     38 #include <string.h>
     39 #include <stdlib.h>
     40 
     41 #ifdef X86_MINGW
     42 #include <signal.h>
     43 #endif
     44 
     45 #ifndef IOS
     46 #include <malloc.h>
     47 #endif
     48 #ifdef IOS_DISPLAY
     49 #include "cast_types.h"
     50 #else
     51 #include "ihevc_typedefs.h"
     52 #endif
     53 
     54 #include "iv.h"
     55 #include "ivd.h"
     56 #include "ihevcd_cxa.h"
     57 #include "ithread.h"
     58 
     59 #ifdef WINDOWS_TIMER
     60 #include <windows.h>
     61 #else
     62 #include <sys/time.h>
     63 #endif
     64 
     65 #define ALIGN8(x) ((((x) + 7) >> 3) << 3)
     66 #define NUM_DISPLAY_BUFFERS 4
     67 #define DEFAULT_FPS         30
     68 
     69 #define ENABLE_DEGRADE 0
     70 #define MAX_DISP_BUFFERS    64
     71 #define EXTRA_DISP_BUFFERS  0
     72 #define STRLENGTH 1000
     73 
     74 #define ADAPTIVE_TEST
     75 #define ADAPTIVE_MAX_WD 8192
     76 #define ADAPTIVE_MAX_HT 4096
     77 //#define TEST_FLUSH
     78 #define FLUSH_FRM_CNT 100
     79 
     80 
     81 #ifdef IOS
     82 #define PATHLENMAX 500
     83 char filename_with_path[PATHLENMAX];
     84 #endif
     85 
     86 #ifdef PROFILE_ENABLE
     87 #ifdef X86_MSVC
     88 typedef  LARGE_INTEGER TIMER;
     89 #else
     90 //#ifdef X86_MINGW
     91 typedef struct timeval TIMER;
     92 //#endif
     93 #endif
     94 #else
     95 typedef WORD32 TIMER;
     96 #endif
     97 
     98 #ifdef PROFILE_ENABLE
     99 #ifdef X86_MSVC
    100 #define GETTIME(timer) QueryPerformanceCounter(timer);
    101 #else
    102 //#ifdef X86_MINGW
    103 #define GETTIME(timer) gettimeofday(timer,NULL);
    104 //#endif
    105 #endif
    106 
    107 #ifdef X86_MSVC
    108 #define ELAPSEDTIME(s_start_timer,s_end_timer, s_elapsed_time, frequency) \
    109                   { \
    110                    TIMER s_temp_time;   \
    111                    s_temp_time.LowPart = s_end_timer.LowPart - s_start_timer.LowPart ; \
    112                    s_elapsed_time = (UWORD32) ( ((DOUBLE)s_temp_time.LowPart / (DOUBLE)frequency.LowPart )  * 1000000); \
    113                 }
    114 #else
    115 //#ifdef X86_MINGW
    116 #define ELAPSEDTIME(s_start_timer,s_end_timer, s_elapsed_time, frequency) \
    117                    s_elapsed_time = ((s_end_timer.tv_sec - s_start_timer.tv_sec) * 1000000) + (s_end_timer.tv_usec - s_start_timer.tv_usec);
    118 //#endif
    119 #endif
    120 
    121 #else
    122 #define GETTIME(timer)
    123 #define ELAPSEDTIME(s_start_timer,s_end_timer, s_elapsed_time, frequency)
    124 #endif
    125 
    126 
    127 /* Function declarations */
    128 #ifndef MD5_DISABLE
    129 void calc_md5_cksum(UWORD8 *pu1_inbuf, UWORD32 u4_stride, UWORD32 u4_width, UWORD32 u4_height, UWORD8 *pu1_cksum_p);
    130 #else
    131 #define calc_md5_cksum(a, b, c, d, e)
    132 #endif
    133 #ifdef SDL_DISPLAY
    134 void* sdl_disp_init(UWORD32, UWORD32, WORD32, WORD32, WORD32, WORD32, WORD32, WORD32 *, WORD32 *);
    135 void sdl_alloc_disp_buffers(void *);
    136 void sdl_display(void *, WORD32);
    137 void sdl_set_disp_buffers(void *, WORD32, UWORD8 **, UWORD8 **, UWORD8 **);
    138 void sdl_disp_deinit(void *);
    139 void sdl_disp_usleep(UWORD32);
    140 IV_COLOR_FORMAT_T sdl_get_color_fmt(void);
    141 UWORD32 sdl_get_stride(void);
    142 #endif
    143 
    144 #ifdef INTEL_CE5300
    145 void* gdl_disp_init(UWORD32, UWORD32, WORD32, WORD32, WORD32, WORD32, WORD32, WORD32 *, WORD32 *);
    146 void gdl_alloc_disp_buffers(void *);
    147 void gdl_display(void *, WORD32);
    148 void gdl_set_disp_buffers(void *, WORD32, UWORD8 **, UWORD8 **, UWORD8 **);
    149 void gdl_disp_deinit(void *);
    150 void gdl_disp_usleep(UWORD32);
    151 IV_COLOR_FORMAT_T gdl_get_color_fmt(void);
    152 UWORD32 gdl_get_stride(void);
    153 #endif
    154 
    155 #ifdef FBDEV_DISPLAY
    156 void* fbd_disp_init(UWORD32, UWORD32, WORD32, WORD32, WORD32, WORD32, WORD32, WORD32 *, WORD32 *);
    157 void fbd_alloc_disp_buffers(void *);
    158 void fbd_display(void *, WORD32);
    159 void fbd_set_disp_buffers(void *, WORD32, UWORD8 **, UWORD8 **, UWORD8 **);
    160 void fbd_disp_deinit(void *);
    161 void fbd_disp_usleep(UWORD32);
    162 IV_COLOR_FORMAT_T fbd_get_color_fmt(void);
    163 UWORD32 fbd_get_stride(void);
    164 #endif
    165 
    166 #ifdef IOS_DISPLAY
    167 void* ios_disp_init(UWORD32, UWORD32, WORD32, WORD32, WORD32, WORD32, WORD32, WORD32 *, WORD32 *);
    168 void ios_alloc_disp_buffers(void *);
    169 void ios_display(void *, WORD32);
    170 void ios_set_disp_buffers(void *, WORD32, UWORD8 **, UWORD8 **, UWORD8 **);
    171 void ios_disp_deinit(void *);
    172 void ios_disp_usleep(UWORD32);
    173 IV_COLOR_FORMAT_T ios_get_color_fmt(void);
    174 UWORD32 ios_get_stride(void);
    175 #endif
    176 
    177 typedef struct
    178 {
    179     UWORD32 u4_piclen_flag;
    180     UWORD32 u4_file_save_flag;
    181     UWORD32 u4_chksum_save_flag;
    182     UWORD32 u4_max_frm_ts;
    183     IV_COLOR_FORMAT_T e_output_chroma_format;
    184     IVD_ARCH_T e_arch;
    185     IVD_SOC_T e_soc;
    186     UWORD32 dump_q_rd_idx;
    187     UWORD32 dump_q_wr_idx;
    188     WORD32  disp_q_wr_idx;
    189     WORD32  disp_q_rd_idx;
    190 
    191     void *cocodec_obj;
    192     UWORD32 share_disp_buf;
    193     UWORD32 num_disp_buf;
    194     UWORD32 b_pic_present;
    195     WORD32 i4_degrade_type;
    196     WORD32 i4_degrade_pics;
    197     UWORD32 u4_num_cores;
    198     UWORD32 disp_delay;
    199     WORD32 trace_enable;
    200     CHAR ac_trace_fname[STRLENGTH];
    201     CHAR ac_piclen_fname[STRLENGTH];
    202     CHAR ac_ip_fname[STRLENGTH];
    203     CHAR ac_op_fname[STRLENGTH];
    204     CHAR ac_op_chksum_fname[STRLENGTH];
    205     ivd_out_bufdesc_t s_disp_buffers[MAX_DISP_BUFFERS];
    206     iv_yuv_buf_t s_disp_frm_queue[MAX_DISP_BUFFERS];
    207     UWORD32 s_disp_frm_id_queue[MAX_DISP_BUFFERS];
    208     UWORD32 loopback;
    209     UWORD32 display;
    210     UWORD32 full_screen;
    211     UWORD32 fps;
    212     UWORD32 max_wd;
    213     UWORD32 max_ht;
    214     UWORD32 max_level;
    215 
    216     UWORD32 u4_strd;
    217 
    218     /* For signalling to display thread */
    219     UWORD32 u4_pic_wd;
    220     UWORD32 u4_pic_ht;
    221 
    222     /* For IOS diplay */
    223     WORD32 i4_screen_wd;
    224     WORD32 i4_screen_ht;
    225 
    226     //UWORD32 u4_output_present;
    227     WORD32  quit;
    228     WORD32  paused;
    229 
    230 
    231     void *pv_disp_ctx;
    232     void *display_thread_handle;
    233     WORD32 display_thread_created;
    234     volatile WORD32 display_init_done;
    235     volatile WORD32 display_deinit_flag;
    236 
    237     void* (*disp_init)(UWORD32, UWORD32, WORD32, WORD32, WORD32, WORD32, WORD32, WORD32 *, WORD32 *);
    238     void (*alloc_disp_buffers)(void *);
    239     void (*display_buffer)(void *, WORD32);
    240     void (*set_disp_buffers)(void *, WORD32, UWORD8 **, UWORD8 **, UWORD8 **);
    241     void (*disp_deinit)(void *);
    242     void (*disp_usleep)(UWORD32);
    243     IV_COLOR_FORMAT_T (*get_color_fmt)(void);
    244     UWORD32 (*get_stride)(void);
    245 } vid_dec_ctx_t;
    246 
    247 
    248 
    249 typedef enum
    250 {
    251     INVALID,
    252     HELP,
    253     VERSION,
    254     INPUT_FILE,
    255     OUTPUT,
    256     CHKSUM,
    257     SAVE_OUTPUT,
    258     SAVE_CHKSUM,
    259     CHROMA_FORMAT,
    260     NUM_FRAMES,
    261     NUM_CORES,
    262 
    263     SHARE_DISPLAY_BUF,
    264     LOOPBACK,
    265     DISPLAY,
    266     FULLSCREEN,
    267     FPS,
    268     TRACE,
    269     CONFIG,
    270 
    271     DEGRADE_TYPE,
    272     DEGRADE_PICS,
    273     ARCH,
    274     SOC,
    275     PICLEN,
    276     PICLEN_FILE,
    277 }ARGUMENT_T;
    278 
    279 typedef struct
    280 {
    281     CHAR argument_shortname[4];
    282     CHAR argument_name[128];
    283     ARGUMENT_T argument;
    284     CHAR description[512];
    285 }argument_t;
    286 
    287 static const argument_t argument_mapping[] =
    288 {
    289     { "-h",  "--help",                   HELP,
    290         "Print this help\n" },
    291     { "-c", "--config",      CONFIG,
    292         "config file (Default: test.cfg)\n" },
    293 
    294     { "-v",  "--version",                VERSION,
    295         "Version information\n" },
    296     { "-i",  "--input",                  INPUT_FILE,
    297         "Input file\n" },
    298     { "-o",  "--output",                 OUTPUT,
    299         "Output file\n" },
    300     { "--",  "--piclen",                 PICLEN,
    301         "Flag to signal if the decoder has to use a file containing number of bytes in each picture to be fed in each call\n" },
    302     { "--",  "--piclen_file",                 PICLEN_FILE,
    303         "File containing number of bytes in each picture - each line containing one size\n" },
    304     { "--",  "--chksum",          CHKSUM,
    305         "Output MD5 Checksum file\n" },
    306     { "-s", "--save_output",            SAVE_OUTPUT,
    307         "Save Output file\n" },
    308     { "--", "--save_chksum",            SAVE_CHKSUM,
    309         "Save Check sum file\n" },
    310     { "--",  "--chroma_format",          CHROMA_FORMAT,
    311         "Output Chroma format Supported values YUV_420P, YUV_422ILE, RGB_565, YUV_420SP_UV, YUV_420SP_VU\n" },
    312     { "-n", "--num_frames",             NUM_FRAMES,
    313         "Number of frames to be decoded\n" },
    314     { "--", "--num_cores",              NUM_CORES,
    315         "Number of cores to be used\n" },
    316     { "--",  "--degrade_type",  DEGRADE_TYPE,
    317         "Degrade type : 0: No degrade 0th bit set : Disable SAO 1st bit set : Disable deblocking 2nd bit set : Faster inter prediction filters 3rd bit set : Fastest inter prediction filters\n" },
    318     { "--",  "--degrade_pics",  DEGRADE_PICS,
    319         "Degrade pics : 0 : No degrade  1 : Only on non-reference frames  2 : Do not degrade every 4th or key frames  3 : All non-key frames  4 : All frames" },
    320     { "--", "--share_display_buf",      SHARE_DISPLAY_BUF,
    321         "Enable shared display buffer mode\n" },
    322     { "--", "--loopback",      LOOPBACK,
    323         "Enable playback in a loop\n" },
    324     { "--", "--display",      DISPLAY,
    325         "Enable display (uses SDL)\n" },
    326     { "--", "--fullscreen",      FULLSCREEN,
    327         "Enable full screen (Only for GDL and SDL)\n" },
    328     { "--", "--fps",      FPS,
    329         "FPS to be used for display \n" },
    330     { "-i",  "--trace",                   TRACE,
    331         "Trace file\n" },
    332     { "--",  "--arch", ARCH,
    333         "Set Architecture. Supported values  ARM_NONEON, ARM_A9Q, ARM_A7, ARM_A5, ARM_NEONINTR, X86_GENERIC, X86_SSSE3, X86_SSE4 \n" },
    334     { "--",  "--soc", SOC,
    335         "Set SOC. Supported values  GENERIC, HISI_37X \n" },
    336 };
    337 
    338 #define PEAK_WINDOW_SIZE            8
    339 #define DEFAULT_SHARE_DISPLAY_BUF   0
    340 #define STRIDE                      0
    341 #define DEFAULT_NUM_CORES           1
    342 
    343 #define DUMP_SINGLE_BUF 0
    344 #define IV_ISFATALERROR(x)         (((x) >> IVD_FATALERROR) & 0x1)
    345 
    346 #define ivd_cxa_api_function        ihevcd_cxa_api_function
    347 
    348 #ifdef IOS
    349 char filename_trace[PATHLENMAX];
    350 #endif
    351 
    352 #if ANDROID_NDK
    353 /*****************************************************************************/
    354 /*                                                                           */
    355 /*  Function Name : raise                                                    */
    356 /*                                                                           */
    357 /*  Description   : Needed as a workaround when the application is built in  */
    358 /*                  Android NDK. This is an exception to be called for divide*/
    359 /*                  by zero error                                            */
    360 /*                                                                           */
    361 /*  Inputs        : a                                                        */
    362 /*  Globals       :                                                          */
    363 /*  Processing    : None                                                     */
    364 /*                                                                           */
    365 /*  Outputs       :                                                          */
    366 /*  Returns       :                                                          */
    367 /*                                                                           */
    368 /*  Issues        :                                                          */
    369 /*                                                                           */
    370 /*  Revision History:                                                        */
    371 /*                                                                           */
    372 /*         DD MM YYYY   Author(s)       Changes                              */
    373 /*         07 09 2012   100189          Initial Version                      */
    374 /*                                                                           */
    375 /*****************************************************************************/
    376 int raise(int a)
    377 {
    378     printf("Divide by zero\n");
    379     return 0;
    380 }
    381 #endif
    382 
    383 #ifdef _WIN32
    384 /*****************************************************************************/
    385 /* Function to print library calls                                           */
    386 /*****************************************************************************/
    387 /*****************************************************************************/
    388 /*                                                                           */
    389 /*  Function Name : memalign                                                 */
    390 /*                                                                           */
    391 /*  Description   : Returns malloc data. Ideally should return aligned memory*/
    392 /*                  support alignment will be added later                    */
    393 /*                                                                           */
    394 /*  Inputs        : alignment                                                */
    395 /*                  size                                                     */
    396 /*  Globals       :                                                          */
    397 /*  Processing    :                                                          */
    398 /*                                                                           */
    399 /*  Outputs       :                                                          */
    400 /*  Returns       :                                                          */
    401 /*                                                                           */
    402 /*  Issues        :                                                          */
    403 /*                                                                           */
    404 /*  Revision History:                                                        */
    405 /*                                                                           */
    406 /*         DD MM YYYY   Author(s)       Changes                              */
    407 /*         07 09 2012   100189          Initial Version                      */
    408 /*                                                                           */
    409 /*****************************************************************************/
    410 
    411 void *ihevca_aligned_malloc(void *pv_ctxt, WORD32 alignment, WORD32 i4_size)
    412 {
    413     (void)pv_ctxt;
    414     return (void *)_aligned_malloc(i4_size, alignment);
    415 }
    416 
    417 void ihevca_aligned_free(void *pv_ctxt, void *pv_buf)
    418 {
    419     (void)pv_ctxt;
    420     _aligned_free(pv_buf);
    421     return;
    422 }
    423 #endif
    424 
    425 #if IOS
    426 void *ihevca_aligned_malloc(void *pv_ctxt, WORD32 alignment, WORD32 i4_size)
    427 {
    428     (void)pv_ctxt;
    429     return malloc(i4_size);
    430 }
    431 
    432 void ihevca_aligned_free(void *pv_ctxt, void *pv_buf)
    433 {
    434     (void)pv_ctxt;
    435     free(pv_buf);
    436     return;
    437 }
    438 #endif
    439 
    440 #if (!defined(IOS)) && (!defined(_WIN32))
    441 void *ihevca_aligned_malloc(void *pv_ctxt, WORD32 alignment, WORD32 i4_size)
    442 {
    443    (void)pv_ctxt;
    444     return memalign(alignment, i4_size);
    445 }
    446 
    447 void ihevca_aligned_free(void *pv_ctxt, void *pv_buf)
    448 {
    449     (void)pv_ctxt;
    450     free(pv_buf);
    451     return;
    452 }
    453 #endif
    454 /*****************************************************************************/
    455 /*                                                                           */
    456 /*  Function Name : set_degrade                                 */
    457 /*                                                                           */
    458 /*  Description   : Control call to set degrade level       */
    459 /*                                                                           */
    460 /*                                                                           */
    461 /*  Inputs        : codec_obj  - Codec Handle                                */
    462 /*                  type - degrade level value between 0 to 4                */
    463 /*                    0 : No degrade                                         */
    464 /*                    1st bit : Disable SAO                                  */
    465 /*                    2nd bit : Disable Deblock                              */
    466 /*                    3rd bit : Faster MC for non-ref                        */
    467 /*                    4th bit : Fastest MC for non-ref                       */
    468 /*                  pics - Pictures that are are degraded                    */
    469 /*                    0 : No degrade                                         */
    470 /*                    1 : Non-ref pictures                                   */
    471 /*                    2 : Pictures at given interval are not degraded        */
    472 /*                    3 : All non-key pictures                               */
    473 /*                    4 : All pictures                                       */
    474 /*  Globals       :                                                          */
    475 /*  Processing    : Calls degrade control to the codec                       */
    476 /*                                                                           */
    477 /*  Outputs       :                                                          */
    478 /*  Returns       : Control call return status                               */
    479 /*                                                                           */
    480 /*  Issues        :                                                          */
    481 /*                                                                           */
    482 /*  Revision History:                                                        */
    483 /*                                                                           */
    484 /*         DD MM YYYY   Author(s)       Changes                              */
    485 /*         07 09 2012   100189          Initial Version                      */
    486 /*                                                                           */
    487 /*****************************************************************************/
    488 
    489 IV_API_CALL_STATUS_T set_degrade(void *codec_obj, UWORD32 type, WORD32 pics)
    490 {
    491     ihevcd_cxa_ctl_degrade_ip_t s_ctl_ip;
    492     ihevcd_cxa_ctl_degrade_op_t s_ctl_op;
    493     void *pv_api_ip, *pv_api_op;
    494     IV_API_CALL_STATUS_T e_dec_status;
    495 
    496     s_ctl_ip.u4_size = sizeof(ihevcd_cxa_ctl_degrade_ip_t);
    497     s_ctl_ip.i4_degrade_type = type;
    498     s_ctl_ip.i4_nondegrade_interval = 4;
    499     s_ctl_ip.i4_degrade_pics = pics;
    500 
    501     s_ctl_op.u4_size = sizeof(ihevcd_cxa_ctl_degrade_op_t);
    502 
    503     pv_api_ip = (void *)&s_ctl_ip;
    504     pv_api_op = (void *)&s_ctl_op;
    505 
    506     s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
    507     s_ctl_ip.e_sub_cmd = (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_DEGRADE;
    508 
    509     e_dec_status = ivd_cxa_api_function((iv_obj_t *)codec_obj, pv_api_ip, pv_api_op);
    510 
    511     if(IV_SUCCESS != e_dec_status)
    512     {
    513         printf("Error in setting degrade level \n");
    514     }
    515     return (e_dec_status);
    516 
    517 }
    518 
    519 /*****************************************************************************/
    520 /*                                                                           */
    521 /*  Function Name : enable_skipb_frames                                      */
    522 /*                                                                           */
    523 /*  Description   : Control call to enable skipping of b frames              */
    524 /*                                                                           */
    525 /*                                                                           */
    526 /*  Inputs        : codec_obj : Codec handle                                 */
    527 /*  Globals       :                                                          */
    528 /*  Processing    : Calls enable skip B frames control                       */
    529 /*                                                                           */
    530 /*  Outputs       :                                                          */
    531 /*  Returns       : Control call return status                               */
    532 /*                                                                           */
    533 /*  Issues        :                                                          */
    534 /*                                                                           */
    535 /*  Revision History:                                                        */
    536 /*                                                                           */
    537 /*         DD MM YYYY   Author(s)       Changes                              */
    538 /*         07 09 2012   100189          Initial Version                      */
    539 /*                                                                           */
    540 /*****************************************************************************/
    541 
    542 IV_API_CALL_STATUS_T enable_skipb_frames(void *codec_obj,
    543                                          vid_dec_ctx_t *ps_app_ctx)
    544 {
    545     ivd_ctl_set_config_ip_t s_ctl_ip;
    546     ivd_ctl_set_config_op_t s_ctl_op;
    547     IV_API_CALL_STATUS_T e_dec_status;
    548 
    549     s_ctl_ip.u4_disp_wd = ps_app_ctx->u4_strd;
    550     s_ctl_ip.e_frm_skip_mode = IVD_SKIP_B;
    551 
    552     s_ctl_ip.e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
    553     s_ctl_ip.e_vid_dec_mode = IVD_DECODE_FRAME;
    554     s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
    555     s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_SETPARAMS;
    556     s_ctl_ip.u4_size = sizeof(ivd_ctl_set_config_ip_t);
    557     s_ctl_op.u4_size = sizeof(ivd_ctl_set_config_op_t);
    558 
    559     e_dec_status = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
    560                                         (void *)&s_ctl_op);
    561 
    562     if(IV_SUCCESS != e_dec_status)
    563     {
    564         printf("Error in Enable SkipB frames \n");
    565     }
    566 
    567     return e_dec_status;
    568 }
    569 /*****************************************************************************/
    570 /*                                                                           */
    571 /*  Function Name : disable_skipb_frames                                     */
    572 /*                                                                           */
    573 /*  Description   : Control call to disable skipping of b frames             */
    574 /*                                                                           */
    575 /*                                                                           */
    576 /*  Inputs        : codec_obj : Codec handle                                 */
    577 /*  Globals       :                                                          */
    578 /*  Processing    : Calls disable B frame skip control                       */
    579 /*                                                                           */
    580 /*  Outputs       :                                                          */
    581 /*  Returns       : Control call return status                               */
    582 /*                                                                           */
    583 /*  Issues        :                                                          */
    584 /*                                                                           */
    585 /*  Revision History:                                                        */
    586 /*                                                                           */
    587 /*         DD MM YYYY   Author(s)       Changes                              */
    588 /*         07 09 2012   100189          Initial Version                      */
    589 /*                                                                           */
    590 /*****************************************************************************/
    591 
    592 IV_API_CALL_STATUS_T disable_skipb_frames(void *codec_obj,
    593                                           vid_dec_ctx_t *ps_app_ctx)
    594 {
    595     ivd_ctl_set_config_ip_t s_ctl_ip;
    596     ivd_ctl_set_config_op_t s_ctl_op;
    597     IV_API_CALL_STATUS_T e_dec_status;
    598 
    599     s_ctl_ip.u4_disp_wd = ps_app_ctx->u4_strd;
    600     s_ctl_ip.e_frm_skip_mode = IVD_SKIP_NONE;
    601 
    602     s_ctl_ip.e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
    603     s_ctl_ip.e_vid_dec_mode = IVD_DECODE_FRAME;
    604     s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
    605     s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_SETPARAMS;
    606     s_ctl_ip.u4_size = sizeof(ivd_ctl_set_config_ip_t);
    607     s_ctl_op.u4_size = sizeof(ivd_ctl_set_config_op_t);
    608 
    609     e_dec_status = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
    610                                         (void *)&s_ctl_op);
    611 
    612     if(IV_SUCCESS != e_dec_status)
    613     {
    614         printf("Error in Disable SkipB frames\n");
    615     }
    616 
    617     return e_dec_status;
    618 }
    619 
    620 /*****************************************************************************/
    621 /*                                                                           */
    622 /*  Function Name : enable_skippb_frames                                     */
    623 /*                                                                           */
    624 /*  Description   : Control call to enable skipping of P & B frames          */
    625 /*                                                                           */
    626 /*                                                                           */
    627 /*  Inputs        : codec_obj : Codec handle                                 */
    628 /*  Globals       :                                                          */
    629 /*  Processing    : Calls enable skip P and B frames control                 */
    630 /*                                                                           */
    631 /*  Outputs       :                                                          */
    632 /*  Returns       : Control call return status                               */
    633 /*                                                                           */
    634 /*  Issues        :                                                          */
    635 /*                                                                           */
    636 /*  Revision History:                                                        */
    637 /*                                                                           */
    638 /*         DD MM YYYY   Author(s)       Changes                              */
    639 /*         07 09 2012   100189          Initial Version                      */
    640 /*                                                                           */
    641 /*****************************************************************************/
    642 
    643 IV_API_CALL_STATUS_T enable_skippb_frames(void *codec_obj,
    644                                           vid_dec_ctx_t *ps_app_ctx)
    645 {
    646     ivd_ctl_set_config_ip_t s_ctl_ip;
    647     ivd_ctl_set_config_op_t s_ctl_op;
    648     IV_API_CALL_STATUS_T e_dec_status;
    649 
    650     s_ctl_ip.u4_disp_wd = ps_app_ctx->u4_strd;
    651     s_ctl_ip.e_frm_skip_mode = IVD_SKIP_PB;
    652 
    653     s_ctl_ip.e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
    654     s_ctl_ip.e_vid_dec_mode = IVD_DECODE_FRAME;
    655     s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
    656     s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_SETPARAMS;
    657     s_ctl_ip.u4_size = sizeof(ivd_ctl_set_config_ip_t);
    658     s_ctl_op.u4_size = sizeof(ivd_ctl_set_config_op_t);
    659 
    660     e_dec_status = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
    661                                         (void *)&s_ctl_op);
    662     if(IV_SUCCESS != e_dec_status)
    663     {
    664         printf("Error in Enable SkipPB frames\n");
    665     }
    666 
    667     return e_dec_status;
    668 }
    669 
    670 /*****************************************************************************/
    671 /*                                                                           */
    672 /*  Function Name : disable_skippb_frames                                    */
    673 /*                                                                           */
    674 /*  Description   : Control call to disable skipping of P and B frames       */
    675 /*                                                                           */
    676 /*                                                                           */
    677 /*  Inputs        : codec_obj : Codec handle                                 */
    678 /*  Globals       :                                                          */
    679 /*  Processing    : Calls disable P and B frame skip control                 */
    680 /*                                                                           */
    681 /*  Outputs       :                                                          */
    682 /*  Returns       : Control call return status                               */
    683 /*                                                                           */
    684 /*  Issues        :                                                          */
    685 /*                                                                           */
    686 /*  Revision History:                                                        */
    687 /*                                                                           */
    688 /*         DD MM YYYY   Author(s)       Changes                              */
    689 /*         07 09 2012   100189          Initial Version                      */
    690 /*                                                                           */
    691 /*****************************************************************************/
    692 
    693 IV_API_CALL_STATUS_T disable_skippb_frames(void *codec_obj,
    694                                            vid_dec_ctx_t *ps_app_ctx)
    695 {
    696     ivd_ctl_set_config_ip_t s_ctl_ip;
    697     ivd_ctl_set_config_op_t s_ctl_op;
    698     IV_API_CALL_STATUS_T e_dec_status;
    699 
    700     s_ctl_ip.u4_disp_wd = ps_app_ctx->u4_strd;
    701     s_ctl_ip.e_frm_skip_mode = IVD_SKIP_NONE;
    702 
    703     s_ctl_ip.e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
    704     s_ctl_ip.e_vid_dec_mode = IVD_DECODE_FRAME;
    705     s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
    706     s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_SETPARAMS;
    707     s_ctl_ip.u4_size = sizeof(ivd_ctl_set_config_ip_t);
    708     s_ctl_op.u4_size = sizeof(ivd_ctl_set_config_op_t);
    709 
    710     e_dec_status = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
    711                                         (void *)&s_ctl_op);
    712     if(IV_SUCCESS != e_dec_status)
    713     {
    714         printf("Error in Disable SkipPB frames\n");
    715     }
    716 
    717     return e_dec_status;
    718 }
    719 
    720 /*****************************************************************************/
    721 /*                                                                           */
    722 /*  Function Name : release_disp_frame                                       */
    723 /*                                                                           */
    724 /*  Description   : Calls release display control - Used to signal to the    */
    725 /*                  decoder that this particular buffer has been displayed   */
    726 /*                  and that the codec is now free to write to this buffer   */
    727 /*                                                                           */
    728 /*                                                                           */
    729 /*  Inputs        : codec_obj : Codec Handle                                 */
    730 /*                  buf_id    : Buffer Id of the buffer to be released       */
    731 /*                              This id would have been returned earlier by  */
    732 /*                              the codec                                    */
    733 /*  Globals       :                                                          */
    734 /*  Processing    : Calls Release Display call                               */
    735 /*                                                                           */
    736 /*  Outputs       :                                                          */
    737 /*  Returns       : Status of release display call                           */
    738 /*                                                                           */
    739 /*  Issues        :                                                          */
    740 /*                                                                           */
    741 /*  Revision History:                                                        */
    742 /*                                                                           */
    743 /*         DD MM YYYY   Author(s)       Changes                              */
    744 /*         07 09 2012   100189          Initial Version                      */
    745 /*                                                                           */
    746 /*****************************************************************************/
    747 
    748 IV_API_CALL_STATUS_T release_disp_frame(void *codec_obj, UWORD32 buf_id)
    749 {
    750     ivd_rel_display_frame_ip_t s_video_rel_disp_ip;
    751     ivd_rel_display_frame_op_t s_video_rel_disp_op;
    752     IV_API_CALL_STATUS_T e_dec_status;
    753 
    754     s_video_rel_disp_ip.e_cmd = IVD_CMD_REL_DISPLAY_FRAME;
    755     s_video_rel_disp_ip.u4_size = sizeof(ivd_rel_display_frame_ip_t);
    756     s_video_rel_disp_op.u4_size = sizeof(ivd_rel_display_frame_op_t);
    757     s_video_rel_disp_ip.u4_disp_buf_id = buf_id;
    758 
    759     e_dec_status = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_video_rel_disp_ip,
    760                                         (void *)&s_video_rel_disp_op);
    761     if(IV_SUCCESS != e_dec_status)
    762     {
    763         printf("Error in Release Disp frame\n");
    764     }
    765 
    766 
    767     return (e_dec_status);
    768 }
    769 
    770 /*****************************************************************************/
    771 /*                                                                           */
    772 /*  Function Name : get_version                                      */
    773 /*                                                                           */
    774 /*  Description   : Control call to get codec version              */
    775 /*                                                                           */
    776 /*                                                                           */
    777 /*  Inputs        : codec_obj : Codec handle                                 */
    778 /*  Globals       :                                                          */
    779 /*  Processing    : Calls enable skip B frames control                       */
    780 /*                                                                           */
    781 /*  Outputs       :                                                          */
    782 /*  Returns       : Control call return status                               */
    783 /*                                                                           */
    784 /*  Issues        :                                                          */
    785 /*                                                                           */
    786 /*  Revision History:                                                        */
    787 /*                                                                           */
    788 /*         DD MM YYYY   Author(s)       Changes                              */
    789 /*         07 09 2012   100189          Initial Version                      */
    790 /*                                                                           */
    791 /*****************************************************************************/
    792 
    793 IV_API_CALL_STATUS_T get_version(void *codec_obj)
    794 {
    795     ivd_ctl_getversioninfo_ip_t s_ctl_dec_ip;
    796     ivd_ctl_getversioninfo_op_t s_ctl_dec_op;
    797     UWORD8 au1_buf[512];
    798     IV_API_CALL_STATUS_T status;
    799     s_ctl_dec_ip.e_cmd = IVD_CMD_VIDEO_CTL;
    800     s_ctl_dec_ip.e_sub_cmd = IVD_CMD_CTL_GETVERSION;
    801     s_ctl_dec_ip.u4_size = sizeof(ivd_ctl_getversioninfo_ip_t);
    802     s_ctl_dec_op.u4_size = sizeof(ivd_ctl_getversioninfo_op_t);
    803     s_ctl_dec_ip.pv_version_buffer = au1_buf;
    804     s_ctl_dec_ip.u4_version_buffer_size = sizeof(au1_buf);
    805 
    806     status = ivd_cxa_api_function((iv_obj_t *)codec_obj,
    807                                   (void *)&(s_ctl_dec_ip),
    808                                   (void *)&(s_ctl_dec_op));
    809 
    810     if(status != IV_SUCCESS)
    811     {
    812         printf("Error in Getting Version number e_dec_status = %d u4_error_code = %x\n",
    813                status, s_ctl_dec_op.u4_error_code);
    814     }
    815     else
    816     {
    817         printf("Ittiam Decoder Version number: %s\n",
    818                (char *)s_ctl_dec_ip.pv_version_buffer);
    819     }
    820     return status;
    821 }
    822 /*****************************************************************************/
    823 /*                                                                           */
    824 /*  Function Name : codec_exit                                               */
    825 /*                                                                           */
    826 /*  Description   : handles unrecoverable errors                             */
    827 /*  Inputs        : Error message                                            */
    828 /*  Globals       : None                                                     */
    829 /*  Processing    : Prints error message to console and exits.               */
    830 /*  Outputs       : Error mesage to the console                              */
    831 /*  Returns       : None                                                     */
    832 /*                                                                           */
    833 /*  Issues        :                                                          */
    834 /*                                                                           */
    835 /*  Revision History:                                                        */
    836 /*                                                                           */
    837 /*         DD MM YYYY   Author(s)       Changes (Describe the changes made)  */
    838 /*         07 06 2006   Sankar          Creation                             */
    839 /*                                                                           */
    840 /*****************************************************************************/
    841 void codec_exit(CHAR *pc_err_message)
    842 {
    843     printf("%s\n", pc_err_message);
    844     exit(-1);
    845 }
    846 
    847 /*****************************************************************************/
    848 /*                                                                           */
    849 /*  Function Name : dump_output                                              */
    850 /*                                                                           */
    851 /*  Description   : Used to dump output YUV                                  */
    852 /*  Inputs        : App context, disp output desc, File pointer              */
    853 /*  Globals       : None                                                     */
    854 /*  Processing    : Dumps to a file                                          */
    855 /*  Returns       : None                                                     */
    856 /*                                                                           */
    857 /*  Issues        :                                                          */
    858 /*                                                                           */
    859 /*  Revision History:                                                        */
    860 /*                                                                           */
    861 /*         DD MM YYYY   Author(s)       Changes (Describe the changes made)  */
    862 /*         07 06 2006   Sankar          Creation                             */
    863 /*                                                                           */
    864 /*****************************************************************************/
    865 void dump_output(vid_dec_ctx_t *ps_app_ctx,
    866                  iv_yuv_buf_t *ps_disp_frm_buf,
    867                  UWORD32 u4_disp_frm_id,
    868                  FILE *ps_op_file,
    869                  FILE *ps_op_chksum_file,
    870                  WORD32 i4_op_frm_ts,
    871                  UWORD32 file_save,
    872                  UWORD32 chksum_save)
    873 
    874 {
    875 
    876     UWORD32 i;
    877     iv_yuv_buf_t s_dump_disp_frm_buf;
    878     UWORD32 u4_disp_id;
    879 
    880     memset(&s_dump_disp_frm_buf, 0, sizeof(iv_yuv_buf_t));
    881 
    882     if(ps_app_ctx->share_disp_buf)
    883     {
    884         if(ps_app_ctx->dump_q_wr_idx == MAX_DISP_BUFFERS
    885                         )
    886             ps_app_ctx->dump_q_wr_idx = 0;
    887 
    888         if(ps_app_ctx->dump_q_rd_idx == MAX_DISP_BUFFERS
    889                         )
    890             ps_app_ctx->dump_q_rd_idx = 0;
    891 
    892         ps_app_ctx->s_disp_frm_queue[ps_app_ctx->dump_q_wr_idx] =
    893                         *ps_disp_frm_buf;
    894         ps_app_ctx->s_disp_frm_id_queue[ps_app_ctx->dump_q_wr_idx] =
    895                         u4_disp_frm_id;
    896         ps_app_ctx->dump_q_wr_idx++;
    897 
    898         if((WORD32)i4_op_frm_ts >= (WORD32)(ps_app_ctx->disp_delay - 1))
    899         {
    900             s_dump_disp_frm_buf =
    901                             ps_app_ctx->s_disp_frm_queue[ps_app_ctx->dump_q_rd_idx];
    902             u4_disp_id =
    903                             ps_app_ctx->s_disp_frm_id_queue[ps_app_ctx->dump_q_rd_idx];
    904             ps_app_ctx->dump_q_rd_idx++;
    905         }
    906         else
    907         {
    908             return;
    909         }
    910     }
    911     else
    912     {
    913         s_dump_disp_frm_buf = *ps_disp_frm_buf;
    914         u4_disp_id = u4_disp_frm_id;
    915     }
    916 
    917     release_disp_frame(ps_app_ctx->cocodec_obj, u4_disp_id);
    918 
    919     if(0 == file_save && 0 == chksum_save)
    920         return;
    921 
    922     if(NULL == s_dump_disp_frm_buf.pv_y_buf)
    923         return;
    924 
    925     if(ps_app_ctx->e_output_chroma_format == IV_YUV_420P)
    926     {
    927 #if DUMP_SINGLE_BUF
    928         {
    929             UWORD8 *buf = s_dump_disp_frm_buf.pv_y_buf - 80 - (s_dump_disp_frm_buf.u4_y_strd * 80);
    930 
    931             UWORD32 size = s_dump_disp_frm_buf.u4_y_strd * ((s_dump_disp_frm_buf.u4_y_ht + 160) + (s_dump_disp_frm_buf.u4_u_ht + 80));
    932             fwrite(buf, 1, size ,ps_op_file);
    933 
    934         }
    935 #else
    936         if(0 != file_save)
    937         {
    938             UWORD8 *buf;
    939 
    940             buf = (UWORD8 *)s_dump_disp_frm_buf.pv_y_buf;
    941             for(i = 0; i < s_dump_disp_frm_buf.u4_y_ht; i++)
    942             {
    943                 fwrite(buf, 1, s_dump_disp_frm_buf.u4_y_wd, ps_op_file);
    944                 buf += s_dump_disp_frm_buf.u4_y_strd;
    945             }
    946 
    947             buf = (UWORD8 *)s_dump_disp_frm_buf.pv_u_buf;
    948             for(i = 0; i < s_dump_disp_frm_buf.u4_u_ht; i++)
    949             {
    950                 fwrite(buf, 1, s_dump_disp_frm_buf.u4_u_wd, ps_op_file);
    951                 buf += s_dump_disp_frm_buf.u4_u_strd;
    952             }
    953             buf = (UWORD8 *)s_dump_disp_frm_buf.pv_v_buf;
    954             for(i = 0; i < s_dump_disp_frm_buf.u4_v_ht; i++)
    955             {
    956                 fwrite(buf, 1, s_dump_disp_frm_buf.u4_v_wd, ps_op_file);
    957                 buf += s_dump_disp_frm_buf.u4_v_strd;
    958             }
    959 
    960         }
    961 
    962         if(0 != chksum_save)
    963         {
    964             UWORD8 au1_y_chksum[16];
    965             UWORD8 au1_u_chksum[16];
    966             UWORD8 au1_v_chksum[16];
    967             calc_md5_cksum((UWORD8 *)s_dump_disp_frm_buf.pv_y_buf,
    968                            s_dump_disp_frm_buf.u4_y_strd,
    969                            s_dump_disp_frm_buf.u4_y_wd,
    970                            s_dump_disp_frm_buf.u4_y_ht,
    971                            au1_y_chksum);
    972             calc_md5_cksum((UWORD8 *)s_dump_disp_frm_buf.pv_u_buf,
    973                            s_dump_disp_frm_buf.u4_u_strd,
    974                            s_dump_disp_frm_buf.u4_u_wd,
    975                            s_dump_disp_frm_buf.u4_u_ht,
    976                            au1_u_chksum);
    977             calc_md5_cksum((UWORD8 *)s_dump_disp_frm_buf.pv_v_buf,
    978                            s_dump_disp_frm_buf.u4_v_strd,
    979                            s_dump_disp_frm_buf.u4_v_wd,
    980                            s_dump_disp_frm_buf.u4_v_ht,
    981                            au1_v_chksum);
    982 
    983             fwrite(au1_y_chksum, sizeof(UWORD8), 16, ps_op_chksum_file);
    984             fwrite(au1_u_chksum, sizeof(UWORD8), 16, ps_op_chksum_file);
    985             fwrite(au1_v_chksum, sizeof(UWORD8), 16, ps_op_chksum_file);
    986         }
    987 #endif
    988     }
    989     else if((ps_app_ctx->e_output_chroma_format == IV_YUV_420SP_UV)
    990                     || (ps_app_ctx->e_output_chroma_format == IV_YUV_420SP_VU))
    991     {
    992 #if DUMP_SINGLE_BUF
    993         {
    994 
    995             UWORD8 *buf = s_dump_disp_frm_buf.pv_y_buf - 24 - (s_dump_disp_frm_buf.u4_y_strd * 40);
    996 
    997             UWORD32 size = s_dump_disp_frm_buf.u4_y_strd * ((s_dump_disp_frm_buf.u4_y_ht + 80) + (s_dump_disp_frm_buf.u4_u_ht + 40));
    998             fwrite(buf, 1, size ,ps_op_file);
    999         }
   1000 #else
   1001         {
   1002             UWORD8 *buf;
   1003 
   1004             buf = (UWORD8 *)s_dump_disp_frm_buf.pv_y_buf;
   1005             for(i = 0; i < s_dump_disp_frm_buf.u4_y_ht; i++)
   1006             {
   1007                 fwrite(buf, 1, s_dump_disp_frm_buf.u4_y_wd, ps_op_file);
   1008                 buf += s_dump_disp_frm_buf.u4_y_strd;
   1009             }
   1010 
   1011             buf = (UWORD8 *)s_dump_disp_frm_buf.pv_u_buf;
   1012             for(i = 0; i < s_dump_disp_frm_buf.u4_u_ht; i++)
   1013             {
   1014                 fwrite(buf, 1, s_dump_disp_frm_buf.u4_u_wd, ps_op_file);
   1015                 buf += s_dump_disp_frm_buf.u4_u_strd;
   1016             }
   1017         }
   1018 #endif
   1019     }
   1020     else if(ps_app_ctx->e_output_chroma_format == IV_RGBA_8888)
   1021     {
   1022         UWORD8 *buf;
   1023 
   1024         buf = (UWORD8 *)s_dump_disp_frm_buf.pv_y_buf;
   1025         for(i = 0; i < s_dump_disp_frm_buf.u4_y_ht; i++)
   1026         {
   1027             fwrite(buf, 1, s_dump_disp_frm_buf.u4_y_wd * 4, ps_op_file);
   1028             buf += s_dump_disp_frm_buf.u4_y_strd * 4;
   1029         }
   1030     }
   1031     else
   1032     {
   1033         UWORD8 *buf;
   1034 
   1035         buf = (UWORD8 *)s_dump_disp_frm_buf.pv_y_buf;
   1036         for(i = 0; i < s_dump_disp_frm_buf.u4_y_ht; i++)
   1037         {
   1038             fwrite(buf, 1, s_dump_disp_frm_buf.u4_y_strd * 2, ps_op_file);
   1039             buf += s_dump_disp_frm_buf.u4_y_strd * 2;
   1040         }
   1041     }
   1042 
   1043     fflush(ps_op_file);
   1044     fflush(ps_op_chksum_file);
   1045 
   1046 }
   1047 
   1048 
   1049 /*****************************************************************************/
   1050 /*                                                                           */
   1051 /*  Function Name : print_usage                                              */
   1052 /*                                                                           */
   1053 /*  Description   : Prints argument format                                   */
   1054 /*                                                                           */
   1055 /*                                                                           */
   1056 /*  Inputs        :                                                          */
   1057 /*  Globals       :                                                          */
   1058 /*  Processing    : Prints argument format                                   */
   1059 /*                                                                           */
   1060 /*  Outputs       :                                                          */
   1061 /*  Returns       :                                                          */
   1062 /*                                                                           */
   1063 /*  Issues        :                                                          */
   1064 /*                                                                           */
   1065 /*  Revision History:                                                        */
   1066 /*                                                                           */
   1067 /*         DD MM YYYY   Author(s)       Changes                              */
   1068 /*         07 09 2012   100189          Initial Version                      */
   1069 /*                                                                           */
   1070 /*****************************************************************************/
   1071 
   1072 void print_usage(void)
   1073 {
   1074     WORD32 i = 0;
   1075     WORD32 num_entries = sizeof(argument_mapping) / sizeof(argument_t);
   1076     printf("\nUsage:\n");
   1077     while(i < num_entries)
   1078     {
   1079         printf("%-32s\t %s", argument_mapping[i].argument_name,
   1080                argument_mapping[i].description);
   1081         i++;
   1082     }
   1083 }
   1084 
   1085 /*****************************************************************************/
   1086 /*                                                                           */
   1087 /*  Function Name : get_argument                                             */
   1088 /*                                                                           */
   1089 /*  Description   : Gets argument for a given string                         */
   1090 /*                                                                           */
   1091 /*                                                                           */
   1092 /*  Inputs        : name                                                     */
   1093 /*  Globals       :                                                          */
   1094 /*  Processing    : Searches the given string in the array and returns       */
   1095 /*                  appropriate argument ID                                  */
   1096 /*                                                                           */
   1097 /*  Outputs       : Argument ID                                              */
   1098 /*  Returns       : Argument ID                                              */
   1099 /*                                                                           */
   1100 /*  Issues        :                                                          */
   1101 /*                                                                           */
   1102 /*  Revision History:                                                        */
   1103 /*                                                                           */
   1104 /*         DD MM YYYY   Author(s)       Changes                              */
   1105 /*         07 09 2012   100189          Initial Version                      */
   1106 /*                                                                           */
   1107 /*****************************************************************************/
   1108 
   1109 ARGUMENT_T get_argument(CHAR *name)
   1110 {
   1111     WORD32 i = 0;
   1112     WORD32 num_entries = sizeof(argument_mapping) / sizeof(argument_t);
   1113     while(i < num_entries)
   1114     {
   1115         if((0 == strcmp(argument_mapping[i].argument_name, name)) ||
   1116                         ((0 == strcmp(argument_mapping[i].argument_shortname, name)) &&
   1117                                         (0 != strcmp(argument_mapping[i].argument_shortname, "--"))))
   1118         {
   1119             return argument_mapping[i].argument;
   1120         }
   1121         i++;
   1122     }
   1123     return INVALID;
   1124 }
   1125 
   1126 /*****************************************************************************/
   1127 /*                                                                           */
   1128 /*  Function Name : get_argument                                             */
   1129 /*                                                                           */
   1130 /*  Description   : Gets argument for a given string                         */
   1131 /*                                                                           */
   1132 /*                                                                           */
   1133 /*  Inputs        : name                                                     */
   1134 /*  Globals       :                                                          */
   1135 /*  Processing    : Searches the given string in the array and returns       */
   1136 /*                  appropriate argument ID                                  */
   1137 /*                                                                           */
   1138 /*  Outputs       : Argument ID                                              */
   1139 /*  Returns       : Argument ID                                              */
   1140 /*                                                                           */
   1141 /*  Issues        :                                                          */
   1142 /*                                                                           */
   1143 /*  Revision History:                                                        */
   1144 /*                                                                           */
   1145 /*         DD MM YYYY   Author(s)       Changes                              */
   1146 /*         07 09 2012   100189          Initial Version                      */
   1147 /*                                                                           */
   1148 /*****************************************************************************/
   1149 
   1150 void parse_argument(vid_dec_ctx_t *ps_app_ctx, CHAR *argument, CHAR *value)
   1151 {
   1152     ARGUMENT_T arg;
   1153 
   1154     arg = get_argument(argument);
   1155     switch(arg)
   1156     {
   1157         case HELP:
   1158             print_usage();
   1159             exit(-1);
   1160         case VERSION:
   1161             break;
   1162         case INPUT_FILE:
   1163             sscanf(value, "%s", ps_app_ctx->ac_ip_fname);
   1164             //input_passed = 1;
   1165             break;
   1166 
   1167         case OUTPUT:
   1168             sscanf(value, "%s", ps_app_ctx->ac_op_fname);
   1169             break;
   1170 
   1171         case CHKSUM:
   1172             sscanf(value, "%s", ps_app_ctx->ac_op_chksum_fname);
   1173             break;
   1174 
   1175         case SAVE_OUTPUT:
   1176             sscanf(value, "%d", &ps_app_ctx->u4_file_save_flag);
   1177             break;
   1178 
   1179         case SAVE_CHKSUM:
   1180             sscanf(value, "%d", &ps_app_ctx->u4_chksum_save_flag);
   1181             break;
   1182 
   1183         case CHROMA_FORMAT:
   1184             if((strcmp(value, "YUV_420P")) == 0)
   1185                 ps_app_ctx->e_output_chroma_format = IV_YUV_420P;
   1186             else if((strcmp(value, "YUV_422ILE")) == 0)
   1187                 ps_app_ctx->e_output_chroma_format = IV_YUV_422ILE;
   1188             else if((strcmp(value, "RGB_565")) == 0)
   1189                 ps_app_ctx->e_output_chroma_format = IV_RGB_565;
   1190             else if((strcmp(value, "RGBA_8888")) == 0)
   1191                 ps_app_ctx->e_output_chroma_format = IV_RGBA_8888;
   1192             else if((strcmp(value, "YUV_420SP_UV")) == 0)
   1193                 ps_app_ctx->e_output_chroma_format = IV_YUV_420SP_UV;
   1194             else if((strcmp(value, "YUV_420SP_VU")) == 0)
   1195                 ps_app_ctx->e_output_chroma_format = IV_YUV_420SP_VU;
   1196             else
   1197             {
   1198                 printf("\nInvalid colour format setting it to IV_YUV_420P\n");
   1199                 ps_app_ctx->e_output_chroma_format = IV_YUV_420P;
   1200             }
   1201 
   1202             break;
   1203         case NUM_FRAMES:
   1204             sscanf(value, "%d", &ps_app_ctx->u4_max_frm_ts);
   1205             break;
   1206 
   1207         case NUM_CORES:
   1208             sscanf(value, "%d", &ps_app_ctx->u4_num_cores);
   1209             break;
   1210         case DEGRADE_PICS:
   1211             sscanf(value, "%d", &ps_app_ctx->i4_degrade_pics);
   1212             break;
   1213         case DEGRADE_TYPE:
   1214             sscanf(value, "%d", &ps_app_ctx->i4_degrade_type);
   1215             break;
   1216         case SHARE_DISPLAY_BUF:
   1217             sscanf(value, "%d", &ps_app_ctx->share_disp_buf);
   1218             break;
   1219         case LOOPBACK:
   1220             sscanf(value, "%d", &ps_app_ctx->loopback);
   1221             break;
   1222         case DISPLAY:
   1223 #if defined(SDL_DISPLAY) || defined(FBDEV_DISPLAY) || defined(INTEL_CE5300) || defined(IOS_DISPLAY)
   1224             sscanf(value, "%d", &ps_app_ctx->display);
   1225 #else
   1226             ps_app_ctx->display = 0;
   1227 #endif
   1228             break;
   1229         case FULLSCREEN:
   1230             sscanf(value, "%d", &ps_app_ctx->full_screen);
   1231             break;
   1232         case FPS:
   1233             sscanf(value, "%d", &ps_app_ctx->fps);
   1234             if(ps_app_ctx->fps <= 0)
   1235                 ps_app_ctx->fps = DEFAULT_FPS;
   1236             break;
   1237         case ARCH:
   1238             if((strcmp(value, "ARM_NONEON")) == 0)
   1239                 ps_app_ctx->e_arch = ARCH_ARM_NONEON;
   1240             else if((strcmp(value, "ARM_A9Q")) == 0)
   1241                 ps_app_ctx->e_arch = ARCH_ARM_A9Q;
   1242             else if((strcmp(value, "ARM_A7")) == 0)
   1243                 ps_app_ctx->e_arch = ARCH_ARM_A7;
   1244             else if((strcmp(value, "ARM_A5")) == 0)
   1245                 ps_app_ctx->e_arch = ARCH_ARM_A5;
   1246             else if((strcmp(value, "ARM_NEONINTR")) == 0)
   1247                 ps_app_ctx->e_arch = ARCH_ARM_NEONINTR;
   1248             else if((strcmp(value, "X86_GENERIC")) == 0)
   1249                 ps_app_ctx->e_arch = ARCH_X86_GENERIC;
   1250             else if((strcmp(value, "X86_SSSE3")) == 0)
   1251                 ps_app_ctx->e_arch = ARCH_X86_SSSE3;
   1252             else if((strcmp(value, "X86_SSE42")) == 0)
   1253                 ps_app_ctx->e_arch = ARCH_X86_SSE42;
   1254             else if((strcmp(value, "X86_AVX2")) == 0)
   1255                 ps_app_ctx->e_arch = ARCH_X86_AVX2;
   1256             else if((strcmp(value, "MIPS_GENERIC")) == 0)
   1257                 ps_app_ctx->e_arch = ARCH_MIPS_GENERIC;
   1258             else if((strcmp(value, "MIPS_32")) == 0)
   1259                 ps_app_ctx->e_arch = ARCH_MIPS_32;
   1260             else if((strcmp(value, "ARMV8_GENERIC")) == 0)
   1261                 ps_app_ctx->e_arch = ARCH_ARMV8_GENERIC;
   1262             else
   1263             {
   1264                 printf("\nInvalid Arch. Setting it to ARM_A9Q\n");
   1265                 ps_app_ctx->e_arch = ARCH_ARM_A9Q;
   1266             }
   1267 
   1268             break;
   1269         case SOC:
   1270             if((strcmp(value, "GENERIC")) == 0)
   1271                 ps_app_ctx->e_soc = SOC_GENERIC;
   1272             else if((strcmp(value, "HISI_37X")) == 0)
   1273                 ps_app_ctx->e_soc = SOC_HISI_37X;
   1274             else
   1275             {
   1276                 ps_app_ctx->e_soc = atoi(value);
   1277 /*
   1278                 printf("\nInvalid SOC. Setting it to GENERIC\n");
   1279                 ps_app_ctx->e_soc = SOC_GENERIC;
   1280 */
   1281             }
   1282             break;
   1283         case PICLEN:
   1284             sscanf(value, "%d", &ps_app_ctx->u4_piclen_flag);
   1285             break;
   1286 
   1287         case PICLEN_FILE:
   1288             sscanf(value, "%s", ps_app_ctx->ac_piclen_fname);
   1289             break;
   1290 
   1291         case INVALID:
   1292         default:
   1293             printf("Ignoring argument :  %s\n", argument);
   1294             break;
   1295     }
   1296 }
   1297 
   1298 /*****************************************************************************/
   1299 /*                                                                           */
   1300 /*  Function Name : read_cfg_file                                            */
   1301 /*                                                                           */
   1302 /*  Description   : Reads arguments from a configuration file                */
   1303 /*                                                                           */
   1304 /*                                                                           */
   1305 /*  Inputs        : ps_app_ctx  : Application context                        */
   1306 /*                  fp_cfg_file : Configuration file handle                  */
   1307 /*  Globals       :                                                          */
   1308 /*  Processing    : Parses the arguments and fills in the application context*/
   1309 /*                                                                           */
   1310 /*  Outputs       : Arguments parsed                                         */
   1311 /*  Returns       : None                                                     */
   1312 /*                                                                           */
   1313 /*  Issues        :                                                          */
   1314 /*                                                                           */
   1315 /*  Revision History:                                                        */
   1316 /*                                                                           */
   1317 /*         DD MM YYYY   Author(s)       Changes                              */
   1318 /*         07 09 2012   100189          Initial Version                      */
   1319 /*                                                                           */
   1320 /*****************************************************************************/
   1321 
   1322 void read_cfg_file(vid_dec_ctx_t *ps_app_ctx, FILE *fp_cfg_file)
   1323 {
   1324 
   1325     CHAR line[STRLENGTH];
   1326     CHAR description[STRLENGTH];
   1327     CHAR value[STRLENGTH];
   1328     CHAR argument[STRLENGTH];
   1329     void *ret;
   1330     while(0 == feof(fp_cfg_file))
   1331     {
   1332         line[0] = '\0';
   1333         ret = fgets(line, STRLENGTH, fp_cfg_file);
   1334         if(NULL == ret)
   1335             break;
   1336         argument[0] = '\0';
   1337         /* Reading Input File Name */
   1338         sscanf(line, "%s %s %s", argument, value, description);
   1339         if(argument[0] == '\0')
   1340             continue;
   1341 
   1342         parse_argument(ps_app_ctx, argument, value);
   1343     }
   1344 
   1345 
   1346 }
   1347 
   1348 /*!
   1349 **************************************************************************
   1350 * \if Function name : dispq_producer_dequeue \endif
   1351 *
   1352 * \brief
   1353 *    This function gets a free buffer index where display data can be written
   1354 *    This is a blocking call and can be exited by setting quit to true in
   1355 *    the application context
   1356 *
   1357 * \param[in]  ps_app_ctx  : Pointer to application context
   1358 *
   1359 * \return
   1360 *    returns Next free buffer index for producer
   1361 *
   1362 * \author
   1363 *  Ittiam
   1364 *
   1365 **************************************************************************
   1366 */
   1367 WORD32 dispq_producer_dequeue(vid_dec_ctx_t *ps_app_ctx)
   1368 {
   1369     WORD32 idx;
   1370 
   1371     /* If there is no free buffer wait */
   1372 
   1373     while(((ps_app_ctx->disp_q_wr_idx + 1) % NUM_DISPLAY_BUFFERS) == ps_app_ctx->disp_q_rd_idx)
   1374     {
   1375 
   1376         ithread_msleep(1);
   1377 
   1378         if(ps_app_ctx->quit)
   1379             return (-1);
   1380     }
   1381 
   1382     idx = ps_app_ctx->disp_q_wr_idx;
   1383     return (idx);
   1384 }
   1385 
   1386 /*!
   1387 **************************************************************************
   1388 * \if Function name : dispq_producer_queue \endif
   1389 *
   1390 * \brief
   1391 *    This function adds buffer which can be displayed
   1392 *
   1393 * \param[in]  ps_app_ctx  : Pointer to application context
   1394 *
   1395 * \return
   1396 *    returns Next free buffer index for producer
   1397 *
   1398 * \author
   1399 *  Ittiam
   1400 *
   1401 **************************************************************************
   1402 */
   1403 WORD32 dispq_producer_queue(vid_dec_ctx_t *ps_app_ctx)
   1404 {
   1405     ps_app_ctx->disp_q_wr_idx++;
   1406     if(ps_app_ctx->disp_q_wr_idx == NUM_DISPLAY_BUFFERS)
   1407         ps_app_ctx->disp_q_wr_idx = 0;
   1408 
   1409     return (0);
   1410 }
   1411 /*!
   1412 **************************************************************************
   1413 * \if Function name : dispq_consumer_dequeue \endif
   1414 *
   1415 * \brief
   1416 *    This function gets a free buffer index where display data can be written
   1417 *    This is a blocking call and can be exited by setting quit to true in
   1418 *    the application context
   1419 *
   1420 * \param[in]  ps_app_ctx  : Pointer to application context
   1421 *
   1422 * \return
   1423 *    returns Next free buffer index for producer
   1424 *
   1425 * \author
   1426 *  Ittiam
   1427 *
   1428 **************************************************************************
   1429 */
   1430 WORD32 dispq_consumer_dequeue(vid_dec_ctx_t *ps_app_ctx)
   1431 {
   1432     WORD32 idx;
   1433 
   1434     /* If there is no free buffer wait */
   1435 
   1436     while(ps_app_ctx->disp_q_wr_idx == ps_app_ctx->disp_q_rd_idx)
   1437     {
   1438 
   1439         ithread_msleep(1);
   1440 
   1441         if(ps_app_ctx->quit)
   1442             return (-1);
   1443     }
   1444 
   1445     idx = ps_app_ctx->disp_q_rd_idx;
   1446     return (idx);
   1447 }
   1448 
   1449 /*!
   1450 **************************************************************************
   1451 * \if Function name : dispq_producer_queue \endif
   1452 *
   1453 * \brief
   1454 *    This function adds buffer which can be displayed
   1455 *
   1456 * \param[in]  ps_app_ctx  : Pointer to application context
   1457 *
   1458 * \return
   1459 *    returns Next free buffer index for producer
   1460 *
   1461 * \author
   1462 *  Ittiam
   1463 *
   1464 **************************************************************************
   1465 */
   1466 WORD32 dispq_consumer_queue(vid_dec_ctx_t *ps_app_ctx)
   1467 {
   1468     ps_app_ctx->disp_q_rd_idx++;
   1469     if(ps_app_ctx->disp_q_rd_idx == NUM_DISPLAY_BUFFERS)
   1470         ps_app_ctx->disp_q_rd_idx = 0;
   1471 
   1472     return (0);
   1473 }
   1474 
   1475 /*****************************************************************************/
   1476 /*                                                                           */
   1477 /*  Function Name : display_thread                                           */
   1478 /*                                                                           */
   1479 /*  Description   : Thread to display the frame                              */
   1480 /*                                                                           */
   1481 /*                                                                           */
   1482 /*  Inputs        : pv_ctx  : Application context                            */
   1483 /*                                                                           */
   1484 /*  Globals       :                                                          */
   1485 /*  Processing    : Wait for a buffer to get produced by decoder and display */
   1486 /*                  that frame                                               */
   1487 /*                                                                           */
   1488 /*  Outputs       :                                                          */
   1489 /*  Returns       : None                                                     */
   1490 /*                                                                           */
   1491 /*  Issues        : Pause followed by quit is making some deadlock condn     */
   1492 /*                  If decoder was lagging initially and then fasten up,     */
   1493 /*                  display will also go at faster rate till it reaches      */
   1494 /*                  equilibrium wrt the initial time                         */
   1495 /*                                                                           */
   1496 /*  Revision History:                                                        */
   1497 /*                                                                           */
   1498 /*         DD MM YYYY   Author(s)       Changes                              */
   1499 /*         07 05 2013   100578          Initial Version                      */
   1500 /*                                                                           */
   1501 /*****************************************************************************/
   1502 
   1503 WORD32 display_thread(void *pv_ctx)
   1504 {
   1505     vid_dec_ctx_t *ps_app_ctx = (vid_dec_ctx_t *)pv_ctx;
   1506 
   1507 
   1508     UWORD32 frm_duration; /* in us */
   1509     UWORD32 current_time;
   1510     UWORD32 expected_time;
   1511     TIMER   s_end_timer;
   1512     TIMER   s_first_frame_time;
   1513     UWORD32 first_frame_displayed;
   1514 
   1515 #ifdef WINDOWS_TIMER
   1516     TIMER frequency;
   1517 #endif
   1518 
   1519 #ifdef WINDOWS_TIMER
   1520     QueryPerformanceFrequency(&frequency);
   1521 #endif
   1522     first_frame_displayed = 0;
   1523     expected_time = 0;
   1524     frm_duration = 1000000 / ps_app_ctx->fps;
   1525 
   1526     /* Init display and allocate display buffers */
   1527     ps_app_ctx->pv_disp_ctx = (void *)ps_app_ctx->disp_init(ps_app_ctx->u4_pic_wd,
   1528                                                             ps_app_ctx->u4_pic_ht,
   1529                                                             ps_app_ctx->i4_screen_wd,
   1530                                                             ps_app_ctx->i4_screen_ht,
   1531                                                             ps_app_ctx->max_wd,
   1532                                                             ps_app_ctx->max_ht,
   1533                                                             ps_app_ctx->full_screen,
   1534                                                             &ps_app_ctx->quit,
   1535                                                             &ps_app_ctx->paused);
   1536     ps_app_ctx->alloc_disp_buffers(ps_app_ctx->pv_disp_ctx);
   1537 
   1538     ps_app_ctx->display_init_done = 1;
   1539 
   1540     while(1)
   1541     {
   1542         WORD32 rd_idx;
   1543 
   1544         rd_idx = dispq_consumer_dequeue(ps_app_ctx);
   1545         if(ps_app_ctx->quit)
   1546             break;
   1547 
   1548         ps_app_ctx->display_buffer(ps_app_ctx->pv_disp_ctx, rd_idx);
   1549 
   1550         if(0 == first_frame_displayed)
   1551         {
   1552             GETTIME(&s_first_frame_time);
   1553             first_frame_displayed = 1;
   1554         }
   1555 
   1556         /*********************************************************************/
   1557         /* Sleep based on the expected time of arrival of current buffer and */
   1558         /* the Current frame                                                 */
   1559         /*********************************************************************/
   1560 
   1561         GETTIME(&s_end_timer);
   1562         ELAPSEDTIME(s_first_frame_time, s_end_timer, current_time, frequency);
   1563 
   1564         /* time in micro second */
   1565         expected_time += frm_duration;
   1566 
   1567         //printf("current_time %d expected_time %d diff %d \n", current_time, expected_time, (expected_time - current_time));
   1568         /* sleep for the diff. in time */
   1569         if(current_time < expected_time)
   1570             ps_app_ctx->disp_usleep((expected_time - current_time));
   1571         else
   1572             expected_time += (current_time - expected_time);
   1573 
   1574         dispq_consumer_queue(ps_app_ctx);
   1575 
   1576     }
   1577 
   1578 
   1579     while(0 == ps_app_ctx->display_deinit_flag)
   1580     {
   1581         ps_app_ctx->disp_usleep(1000);
   1582     }
   1583     ps_app_ctx->disp_deinit(ps_app_ctx->pv_disp_ctx);
   1584 
   1585     /* destroy the display thread */
   1586     ithread_exit(ps_app_ctx->display_thread_handle);
   1587 
   1588     return 0;
   1589 }
   1590 
   1591 void flush_output(iv_obj_t *codec_obj,
   1592                   vid_dec_ctx_t *ps_app_ctx,
   1593                   ivd_out_bufdesc_t *ps_out_buf,
   1594                   UWORD8 *pu1_bs_buf,
   1595                   UWORD32 *pu4_op_frm_ts,
   1596                   FILE *ps_op_file,
   1597                   FILE *ps_op_chksum_file,
   1598                   UWORD32 u4_ip_frm_ts,
   1599                   UWORD32 u4_bytes_remaining)
   1600 {
   1601     WORD32 ret;
   1602 
   1603     do
   1604     {
   1605 
   1606         ivd_ctl_flush_ip_t s_ctl_ip;
   1607         ivd_ctl_flush_op_t s_ctl_op;
   1608 
   1609         if(*pu4_op_frm_ts >= (ps_app_ctx->u4_max_frm_ts + ps_app_ctx->disp_delay))
   1610             break;
   1611 
   1612         s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   1613         s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_FLUSH;
   1614         s_ctl_ip.u4_size = sizeof(ivd_ctl_flush_ip_t);
   1615         s_ctl_op.u4_size = sizeof(ivd_ctl_flush_op_t);
   1616         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
   1617                                    (void *)&s_ctl_op);
   1618 
   1619         if(ret != IV_SUCCESS)
   1620         {
   1621             printf("Error in Setting the decoder in flush mode\n");
   1622         }
   1623 
   1624         if(IV_SUCCESS == ret)
   1625         {
   1626             ivd_video_decode_ip_t s_video_decode_ip;
   1627             ivd_video_decode_op_t s_video_decode_op;
   1628 
   1629             s_video_decode_ip.e_cmd = IVD_CMD_VIDEO_DECODE;
   1630             s_video_decode_ip.u4_ts = u4_ip_frm_ts;
   1631             s_video_decode_ip.pv_stream_buffer = pu1_bs_buf;
   1632             s_video_decode_ip.u4_num_Bytes = u4_bytes_remaining;
   1633             s_video_decode_ip.u4_size = sizeof(ivd_video_decode_ip_t);
   1634             s_video_decode_ip.s_out_buffer.u4_min_out_buf_size[0] =
   1635                             ps_out_buf->u4_min_out_buf_size[0];
   1636             s_video_decode_ip.s_out_buffer.u4_min_out_buf_size[1] =
   1637                             ps_out_buf->u4_min_out_buf_size[1];
   1638             s_video_decode_ip.s_out_buffer.u4_min_out_buf_size[2] =
   1639                             ps_out_buf->u4_min_out_buf_size[2];
   1640 
   1641             s_video_decode_ip.s_out_buffer.pu1_bufs[0] =
   1642                             ps_out_buf->pu1_bufs[0];
   1643             s_video_decode_ip.s_out_buffer.pu1_bufs[1] =
   1644                             ps_out_buf->pu1_bufs[1];
   1645             s_video_decode_ip.s_out_buffer.pu1_bufs[2] =
   1646                             ps_out_buf->pu1_bufs[2];
   1647             s_video_decode_ip.s_out_buffer.u4_num_bufs =
   1648                             ps_out_buf->u4_num_bufs;
   1649 
   1650             s_video_decode_op.u4_size = sizeof(ivd_video_decode_op_t);
   1651 
   1652             /*****************************************************************************/
   1653             /*   API Call: Video Decode                                                  */
   1654             /*****************************************************************************/
   1655             ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_video_decode_ip,
   1656                                        (void *)&s_video_decode_op);
   1657 
   1658             if(1 == s_video_decode_op.u4_output_present)
   1659             {
   1660                 dump_output(ps_app_ctx, &(s_video_decode_op.s_disp_frm_buf),
   1661                             s_video_decode_op.u4_disp_buf_id, ps_op_file,
   1662                             ps_op_chksum_file,
   1663                             *pu4_op_frm_ts, ps_app_ctx->u4_file_save_flag,
   1664                             ps_app_ctx->u4_chksum_save_flag);
   1665 
   1666                 (*pu4_op_frm_ts)++;
   1667             }
   1668         }
   1669     }while(IV_SUCCESS == ret);
   1670 
   1671 }
   1672 
   1673 #ifdef X86_MINGW
   1674 void sigsegv_handler()
   1675 {
   1676     printf("Segmentation fault, Exiting.. \n");
   1677     exit(-1);
   1678 }
   1679 #endif
   1680 
   1681 UWORD32 default_get_stride(void)
   1682 {
   1683     return 0;
   1684 }
   1685 
   1686 
   1687 IV_COLOR_FORMAT_T default_get_color_fmt(void)
   1688 {
   1689     return IV_YUV_420P;
   1690 }
   1691 /*****************************************************************************/
   1692 /*                                                                           */
   1693 /*  Function Name : main                                                     */
   1694 /*                                                                           */
   1695 /*  Description   : Application to demonstrate codec API                     */
   1696 /*                                                                           */
   1697 /*                                                                           */
   1698 /*  Inputs        : argc    - Number of arguments                            */
   1699 /*                  argv[]  - Arguments                                      */
   1700 /*  Globals       :                                                          */
   1701 /*  Processing    : Shows how to use create, process, control and delete     */
   1702 /*                                                                           */
   1703 /*  Outputs       : Codec output in a file                                   */
   1704 /*  Returns       :                                                          */
   1705 /*                                                                           */
   1706 /*  Issues        : Assumes both PROFILE_ENABLE to be                        */
   1707 /*                  defined for multithread decode-display working           */
   1708 /*                                                                           */
   1709 /*  Revision History:                                                        */
   1710 /*                                                                           */
   1711 /*         DD MM YYYY   Author(s)       Changes                              */
   1712 /*         07 09 2012   100189          Initial Version                      */
   1713 /*         09 05 2013   100578          Multithread decode-display           */
   1714 /*****************************************************************************/
   1715 #ifdef IOS
   1716 int hevcdec_main(char *homedir, char *documentdir, int screen_wd, int screen_ht)
   1717 #else
   1718 int main(WORD32 argc, CHAR *argv[])
   1719 #endif
   1720 {
   1721     CHAR ac_cfg_fname[STRLENGTH];
   1722     FILE *fp_cfg_file = NULL;
   1723     FILE *ps_piclen_file = NULL;
   1724     FILE *ps_ip_file = NULL;
   1725     FILE *ps_op_file = NULL;
   1726     FILE *ps_op_chksum_file = NULL;
   1727     WORD32 ret;
   1728     CHAR ac_error_str[STRLENGTH];
   1729     vid_dec_ctx_t s_app_ctx;
   1730     UWORD8 *pu1_bs_buf = NULL;
   1731 
   1732     ivd_out_bufdesc_t *ps_out_buf;
   1733     UWORD32 u4_num_bytes_dec = 0;
   1734     UWORD32 file_pos = 0;
   1735 
   1736     UWORD32 u4_ip_frm_ts = 0, u4_op_frm_ts = 0;
   1737 
   1738     WORD32 u4_bytes_remaining = 0;
   1739     UWORD32 i;
   1740     UWORD32 u4_ip_buf_len;
   1741     UWORD32 frm_cnt = 0;
   1742     WORD32 total_bytes_comsumed;
   1743 
   1744 #ifdef PROFILE_ENABLE
   1745     UWORD32 u4_tot_cycles = 0;
   1746     UWORD32 u4_tot_fmt_cycles = 0;
   1747     UWORD32 peak_window[PEAK_WINDOW_SIZE];
   1748     UWORD32 peak_window_idx = 0;
   1749     UWORD32 peak_avg_max = 0;
   1750 #ifdef INTEL_CE5300
   1751     UWORD32 time_consumed = 0;
   1752     UWORD32 bytes_consumed = 0;
   1753 #endif
   1754 #endif
   1755 
   1756 #ifdef WINDOWS_TIMER
   1757     TIMER frequency;
   1758 #endif
   1759     WORD32 width = 0, height = 0;
   1760     iv_obj_t *codec_obj;
   1761 #if defined(GPU_BUILD) && !defined(X86)
   1762 //    int ioctl_init();
   1763 //    ioctl_init();
   1764 #endif
   1765 
   1766 #ifdef X86_MINGW
   1767     //For getting printfs without any delay
   1768     setvbuf(stdout, NULL, _IONBF, 0);
   1769     setvbuf(stderr, NULL, _IONBF, 0);
   1770 #endif
   1771 #ifdef IOS
   1772     sprintf(filename_trace, "%s/iostrace.txt", homedir);
   1773     printf("\ntrace file name = %s", filename_trace);
   1774 #endif
   1775 
   1776 #ifdef X86_MINGW
   1777     {
   1778         signal(SIGSEGV, sigsegv_handler);
   1779     }
   1780 #endif
   1781 
   1782 
   1783 #ifndef IOS
   1784     /* Usage */
   1785     if(argc < 2)
   1786     {
   1787         printf("Using test.cfg as configuration file \n");
   1788         strcpy(ac_cfg_fname, "test.cfg");
   1789     }
   1790     else if(argc == 2)
   1791     {
   1792         strcpy(ac_cfg_fname, argv[1]);
   1793     }
   1794 
   1795 #else
   1796     strcpy(ac_cfg_fname, "test.cfg");
   1797 
   1798 #endif
   1799 
   1800 
   1801     /***********************************************************************/
   1802     /*                  Initialize Application parameters                  */
   1803     /***********************************************************************/
   1804 
   1805     strcpy(s_app_ctx.ac_ip_fname, "\0");
   1806     s_app_ctx.dump_q_wr_idx = 0;
   1807     s_app_ctx.dump_q_rd_idx = 0;
   1808     s_app_ctx.display_thread_created = 0;
   1809     s_app_ctx.disp_q_wr_idx = 0;
   1810     s_app_ctx.disp_q_rd_idx = 0;
   1811     s_app_ctx.disp_delay = 0;
   1812     s_app_ctx.loopback = 0;
   1813     s_app_ctx.display = 0;
   1814     s_app_ctx.full_screen = 0;
   1815     s_app_ctx.u4_piclen_flag = 0;
   1816     s_app_ctx.fps = DEFAULT_FPS;
   1817     file_pos = 0;
   1818     total_bytes_comsumed = 0;
   1819     u4_ip_frm_ts = 0;
   1820     u4_op_frm_ts = 0;
   1821 #ifdef PROFILE_ENABLE
   1822     memset(peak_window, 0, sizeof(WORD32) * PEAK_WINDOW_SIZE);
   1823 #endif
   1824     s_app_ctx.share_disp_buf = DEFAULT_SHARE_DISPLAY_BUF;
   1825     s_app_ctx.u4_num_cores = DEFAULT_NUM_CORES;
   1826     s_app_ctx.i4_degrade_type = 0;
   1827     s_app_ctx.i4_degrade_pics = 0;
   1828     s_app_ctx.e_arch = ARCH_ARM_A9Q;
   1829     s_app_ctx.e_soc = SOC_GENERIC;
   1830 
   1831     s_app_ctx.u4_strd = STRIDE;
   1832 
   1833     s_app_ctx.display_thread_handle           = malloc(ithread_get_handle_size());
   1834     s_app_ctx.quit          = 0;
   1835     s_app_ctx.paused        = 0;
   1836     //s_app_ctx.u4_output_present = 0;
   1837 
   1838     s_app_ctx.get_stride = &default_get_stride;
   1839 
   1840     s_app_ctx.get_color_fmt = &default_get_color_fmt;
   1841 
   1842     /* Set function pointers for display */
   1843 #ifdef SDL_DISPLAY
   1844     s_app_ctx.disp_init = &sdl_disp_init;
   1845     s_app_ctx.alloc_disp_buffers = &sdl_alloc_disp_buffers;
   1846     s_app_ctx.display_buffer = &sdl_display;
   1847     s_app_ctx.set_disp_buffers = &sdl_set_disp_buffers;
   1848     s_app_ctx.disp_deinit = &sdl_disp_deinit;
   1849     s_app_ctx.disp_usleep = &sdl_disp_usleep;
   1850     s_app_ctx.get_color_fmt = &sdl_get_color_fmt;
   1851     s_app_ctx.get_stride = &sdl_get_stride;
   1852 #endif
   1853 
   1854 #ifdef FBDEV_DISPLAY
   1855     s_app_ctx.disp_init = &fbd_disp_init;
   1856     s_app_ctx.alloc_disp_buffers = &fbd_alloc_disp_buffers;
   1857     s_app_ctx.display_buffer = &fbd_display;
   1858     s_app_ctx.set_disp_buffers = &fbd_set_disp_buffers;
   1859     s_app_ctx.disp_deinit = &fbd_disp_deinit;
   1860     s_app_ctx.disp_usleep = &fbd_disp_usleep;
   1861     s_app_ctx.get_color_fmt = &fbd_get_color_fmt;
   1862     s_app_ctx.get_stride = &fbd_get_stride;
   1863 #endif
   1864 
   1865 #ifdef INTEL_CE5300
   1866     s_app_ctx.disp_init = &gdl_disp_init;
   1867     s_app_ctx.alloc_disp_buffers = &gdl_alloc_disp_buffers;
   1868     s_app_ctx.display_buffer = &gdl_display;
   1869     s_app_ctx.set_disp_buffers = &gdl_set_disp_buffers;
   1870     s_app_ctx.disp_deinit = &gdl_disp_deinit;
   1871     s_app_ctx.disp_usleep = &gdl_disp_usleep;
   1872     s_app_ctx.get_color_fmt = &gdl_get_color_fmt;
   1873     s_app_ctx.get_stride = &gdl_get_stride;
   1874 #endif
   1875 
   1876 #ifdef IOS_DISPLAY
   1877     s_app_ctx.disp_init = &ios_disp_init;
   1878     s_app_ctx.alloc_disp_buffers = &ios_alloc_disp_buffers;
   1879     s_app_ctx.display_buffer = &ios_display;
   1880     s_app_ctx.set_disp_buffers = &ios_set_disp_buffers;
   1881     s_app_ctx.disp_deinit = &ios_disp_deinit;
   1882     s_app_ctx.disp_usleep = &ios_disp_usleep;
   1883     s_app_ctx.get_color_fmt = &ios_get_color_fmt;
   1884     s_app_ctx.get_stride = &ios_get_stride;
   1885 #endif
   1886 
   1887     s_app_ctx.display_deinit_flag = 0;
   1888     s_app_ctx.e_output_chroma_format = IV_YUV_420SP_UV;
   1889     /*************************************************************************/
   1890     /* Parse arguments                                                       */
   1891     /*************************************************************************/
   1892 
   1893 #ifndef IOS
   1894     /* Read command line arguments */
   1895     if(argc > 2)
   1896     {
   1897         for(i = 1; i < (UWORD32)argc; i += 2)
   1898         {
   1899             if(CONFIG == get_argument(argv[i]))
   1900             {
   1901                 strcpy(ac_cfg_fname, argv[i + 1]);
   1902                 if((fp_cfg_file = fopen(ac_cfg_fname, "r")) == NULL)
   1903                 {
   1904                     sprintf(ac_error_str, "Could not open Configuration file %s",
   1905                             ac_cfg_fname);
   1906                     codec_exit(ac_error_str);
   1907                 }
   1908                 read_cfg_file(&s_app_ctx, fp_cfg_file);
   1909                 fclose(fp_cfg_file);
   1910             }
   1911             else
   1912             {
   1913                 parse_argument(&s_app_ctx, argv[i], argv[i + 1]);
   1914             }
   1915         }
   1916     }
   1917     else
   1918     {
   1919         if((fp_cfg_file = fopen(ac_cfg_fname, "r")) == NULL)
   1920         {
   1921             sprintf(ac_error_str, "Could not open Configuration file %s",
   1922                     ac_cfg_fname);
   1923             codec_exit(ac_error_str);
   1924         }
   1925         read_cfg_file(&s_app_ctx, fp_cfg_file);
   1926         fclose(fp_cfg_file);
   1927     }
   1928 #else
   1929     sprintf(filename_with_path, "%s/%s", homedir, ac_cfg_fname);
   1930     if((fp_cfg_file = fopen(filename_with_path, "r")) == NULL)
   1931     {
   1932         sprintf(ac_error_str, "Could not open Configuration file %s",
   1933                 ac_cfg_fname);
   1934         codec_exit(ac_error_str);
   1935 
   1936     }
   1937     read_cfg_file(&s_app_ctx, fp_cfg_file);
   1938     fclose(fp_cfg_file);
   1939 
   1940 #endif
   1941 #ifdef PRINT_PICSIZE
   1942     /* If the binary is used for only getting number of bytes in each picture, then disable the following features */
   1943     s_app_ctx.u4_piclen_flag = 0;
   1944     s_app_ctx.u4_file_save_flag = 0;
   1945     s_app_ctx.u4_chksum_save_flag = 0;
   1946     s_app_ctx.i4_degrade_pics = 0;
   1947     s_app_ctx.i4_degrade_type = 0;
   1948     s_app_ctx.loopback = 0;
   1949     s_app_ctx.share_disp_buf = 0;
   1950     s_app_ctx.display = 0;
   1951 #endif
   1952 
   1953     /* If display is enabled, then turn off shared mode and get color format that is supported by display */
   1954     if(1 == s_app_ctx.display)
   1955     {
   1956         s_app_ctx.share_disp_buf = 0;
   1957         s_app_ctx.e_output_chroma_format = s_app_ctx.get_color_fmt();
   1958     }
   1959     if(strcmp(s_app_ctx.ac_ip_fname, "\0") == 0)
   1960     {
   1961         printf("\nNo input file given for decoding\n");
   1962         exit(-1);
   1963     }
   1964 
   1965 
   1966     /***********************************************************************/
   1967     /*          create the file object for input file                      */
   1968     /***********************************************************************/
   1969 #ifdef IOS
   1970     sprintf(filename_with_path, "%s/%s", homedir, s_app_ctx.ac_ip_fname);
   1971     ps_ip_file = fopen(filename_with_path, "rb");
   1972 #else
   1973     ps_ip_file = fopen(s_app_ctx.ac_ip_fname, "rb");
   1974 #endif
   1975     if(NULL == ps_ip_file)
   1976     {
   1977         sprintf(ac_error_str, "Could not open input file %s",
   1978                 s_app_ctx.ac_ip_fname);
   1979         codec_exit(ac_error_str);
   1980     }
   1981     /***********************************************************************/
   1982     /*          create the file object for input file                      */
   1983     /***********************************************************************/
   1984     if(1 == s_app_ctx.u4_piclen_flag)
   1985     {
   1986 #ifdef IOS
   1987         sprintf(filename_with_path, "%s/%s", homedir, s_app_ctx.ac_piclen_fname);
   1988         ps_piclen_file = fopen(filename_with_path, "rb");
   1989 #else
   1990         ps_piclen_file = fopen(s_app_ctx.ac_piclen_fname, "rb");
   1991 #endif
   1992         if(NULL == ps_piclen_file)
   1993         {
   1994             sprintf(ac_error_str, "Could not open piclen file %s",
   1995                     s_app_ctx.ac_piclen_fname);
   1996             codec_exit(ac_error_str);
   1997         }
   1998     }
   1999 
   2000     /***********************************************************************/
   2001     /*          create the file object for output file                     */
   2002     /***********************************************************************/
   2003     if(1 == s_app_ctx.u4_file_save_flag)
   2004     {
   2005 #ifdef IOS
   2006         sprintf(filename_with_path, "%s/%s", documentdir, s_app_ctx.ac_op_fname);
   2007         ps_op_file = fopen(filename_with_path, "wb");
   2008 #else
   2009         ps_op_file = fopen(s_app_ctx.ac_op_fname, "wb");
   2010 #endif
   2011 
   2012         if(NULL == ps_op_file)
   2013         {
   2014             sprintf(ac_error_str, "Could not open output file %s",
   2015                     s_app_ctx.ac_op_fname);
   2016             codec_exit(ac_error_str);
   2017         }
   2018     }
   2019 
   2020     /***********************************************************************/
   2021     /*          create the file object for check sum file                  */
   2022     /***********************************************************************/
   2023     if(1 == s_app_ctx.u4_chksum_save_flag)
   2024     {
   2025 #if IOS
   2026         sprintf(filename_with_path, "%s/%s", documentdir, s_app_ctx.ac_op_chksum_fname);
   2027         ps_op_chksum_file = fopen(filename_with_path, "wb");
   2028 #else
   2029         ps_op_chksum_file = fopen(s_app_ctx.ac_op_chksum_fname, "wb");
   2030 #endif
   2031         if(NULL == ps_op_chksum_file)
   2032         {
   2033             sprintf(ac_error_str, "Could not open check sum file %s",
   2034                     s_app_ctx.ac_op_chksum_fname);
   2035             codec_exit(ac_error_str);
   2036         }
   2037     }
   2038     /***********************************************************************/
   2039     /*                      Create decoder instance                        */
   2040     /***********************************************************************/
   2041     {
   2042 
   2043         ps_out_buf = (ivd_out_bufdesc_t *)malloc(sizeof(ivd_out_bufdesc_t));
   2044 
   2045         /*****************************************************************************/
   2046         /*   API Call: Initialize the Decoder                                        */
   2047         /*****************************************************************************/
   2048         {
   2049             ihevcd_cxa_create_ip_t s_create_ip;
   2050             ihevcd_cxa_create_op_t s_create_op;
   2051             void *fxns = &ivd_cxa_api_function;
   2052 
   2053             s_create_ip.s_ivd_create_ip_t.e_cmd = IVD_CMD_CREATE;
   2054             s_create_ip.s_ivd_create_ip_t.u4_share_disp_buf = s_app_ctx.share_disp_buf;
   2055             s_create_ip.s_ivd_create_ip_t.e_output_format = (IV_COLOR_FORMAT_T)s_app_ctx.e_output_chroma_format;
   2056             s_create_ip.s_ivd_create_ip_t.pf_aligned_alloc = ihevca_aligned_malloc;
   2057             s_create_ip.s_ivd_create_ip_t.pf_aligned_free = ihevca_aligned_free;
   2058             s_create_ip.s_ivd_create_ip_t.pv_mem_ctxt = NULL;
   2059             s_create_ip.s_ivd_create_ip_t.u4_size = sizeof(ihevcd_cxa_create_ip_t);
   2060             s_create_op.s_ivd_create_op_t.u4_size = sizeof(ihevcd_cxa_create_op_t);
   2061 
   2062 
   2063 
   2064             ret = ivd_cxa_api_function(NULL, (void *)&s_create_ip,
   2065                                        (void *)&s_create_op);
   2066             if(ret != IV_SUCCESS)
   2067             {
   2068                 sprintf(ac_error_str, "Error in Create %8x\n",
   2069                         s_create_op.s_ivd_create_op_t.u4_error_code);
   2070                 codec_exit(ac_error_str);
   2071             }
   2072             codec_obj = (iv_obj_t*)s_create_op.s_ivd_create_op_t.pv_handle;
   2073             codec_obj->pv_fxns = fxns;
   2074             codec_obj->u4_size = sizeof(iv_obj_t);
   2075             s_app_ctx.cocodec_obj = codec_obj;
   2076         }
   2077 
   2078     }
   2079 
   2080 
   2081     /*************************************************************************/
   2082     /* set num of cores                                                      */
   2083     /*************************************************************************/
   2084     {
   2085 
   2086         ihevcd_cxa_ctl_set_num_cores_ip_t s_ctl_set_cores_ip;
   2087         ihevcd_cxa_ctl_set_num_cores_op_t s_ctl_set_cores_op;
   2088 
   2089         s_ctl_set_cores_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2090         s_ctl_set_cores_ip.e_sub_cmd = (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_SET_NUM_CORES;
   2091         s_ctl_set_cores_ip.u4_num_cores = s_app_ctx.u4_num_cores;
   2092         s_ctl_set_cores_ip.u4_size = sizeof(ihevcd_cxa_ctl_set_num_cores_ip_t);
   2093         s_ctl_set_cores_op.u4_size = sizeof(ihevcd_cxa_ctl_set_num_cores_op_t);
   2094 
   2095         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_set_cores_ip,
   2096                                    (void *)&s_ctl_set_cores_op);
   2097         if(ret != IV_SUCCESS)
   2098         {
   2099             sprintf(ac_error_str, "\nError in setting number of cores");
   2100             codec_exit(ac_error_str);
   2101         }
   2102 
   2103     }
   2104     /*************************************************************************/
   2105     /* set processsor                                                        */
   2106     /*************************************************************************/
   2107     {
   2108 
   2109         ihevcd_cxa_ctl_set_processor_ip_t s_ctl_set_num_processor_ip;
   2110         ihevcd_cxa_ctl_set_processor_op_t s_ctl_set_num_processor_op;
   2111 
   2112         s_ctl_set_num_processor_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2113         s_ctl_set_num_processor_ip.e_sub_cmd = (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_SET_PROCESSOR;
   2114         s_ctl_set_num_processor_ip.u4_arch = s_app_ctx.e_arch;
   2115         s_ctl_set_num_processor_ip.u4_soc = s_app_ctx.e_soc;
   2116         s_ctl_set_num_processor_ip.u4_size = sizeof(ihevcd_cxa_ctl_set_processor_ip_t);
   2117         s_ctl_set_num_processor_op.u4_size = sizeof(ihevcd_cxa_ctl_set_processor_op_t);
   2118 
   2119         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_set_num_processor_ip,
   2120                                    (void *)&s_ctl_set_num_processor_op);
   2121         if(ret != IV_SUCCESS)
   2122         {
   2123             sprintf(ac_error_str, "\nError in setting Processor type");
   2124             codec_exit(ac_error_str);
   2125         }
   2126 
   2127     }
   2128 
   2129     flush_output(codec_obj, &s_app_ctx, ps_out_buf,
   2130                  pu1_bs_buf, &u4_op_frm_ts,
   2131                  ps_op_file, ps_op_chksum_file,
   2132                  u4_ip_frm_ts, u4_bytes_remaining);
   2133 
   2134     /*****************************************************************************/
   2135     /*   Decode header to get width and height and buffer sizes                  */
   2136     /*****************************************************************************/
   2137     {
   2138         ivd_video_decode_ip_t s_video_decode_ip;
   2139         ivd_video_decode_op_t s_video_decode_op;
   2140 
   2141 
   2142 
   2143         {
   2144             ivd_ctl_set_config_ip_t s_ctl_ip;
   2145             ivd_ctl_set_config_op_t s_ctl_op;
   2146 
   2147 
   2148             s_ctl_ip.u4_disp_wd = STRIDE;
   2149             if(1 == s_app_ctx.display)
   2150                 s_ctl_ip.u4_disp_wd = s_app_ctx.get_stride();
   2151 
   2152             s_ctl_ip.e_frm_skip_mode = IVD_SKIP_NONE;
   2153             s_ctl_ip.e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
   2154             s_ctl_ip.e_vid_dec_mode = IVD_DECODE_HEADER;
   2155             s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2156             s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_SETPARAMS;
   2157             s_ctl_ip.u4_size = sizeof(ivd_ctl_set_config_ip_t);
   2158             s_ctl_op.u4_size = sizeof(ivd_ctl_set_config_op_t);
   2159 
   2160             ret = ivd_cxa_api_function((iv_obj_t*)codec_obj, (void *)&s_ctl_ip,
   2161                                        (void *)&s_ctl_op);
   2162             if(ret != IV_SUCCESS)
   2163             {
   2164                 sprintf(ac_error_str,
   2165                         "\nError in setting the codec in header decode mode");
   2166                 codec_exit(ac_error_str);
   2167             }
   2168         }
   2169 
   2170         /* Allocate input buffer for header */
   2171         u4_ip_buf_len = 256 * 1024;
   2172         pu1_bs_buf = (UWORD8 *)malloc(u4_ip_buf_len);
   2173 
   2174         if(pu1_bs_buf == NULL)
   2175         {
   2176             sprintf(ac_error_str,
   2177                     "\nAllocation failure for input buffer of i4_size %d",
   2178                     u4_ip_buf_len);
   2179             codec_exit(ac_error_str);
   2180         }
   2181 
   2182         do
   2183         {
   2184             WORD32 numbytes;
   2185             if(0 == s_app_ctx.u4_piclen_flag)
   2186             {
   2187                 fseek(ps_ip_file, file_pos, SEEK_SET);
   2188                 numbytes = u4_ip_buf_len;
   2189             }
   2190             else
   2191             {
   2192                 WORD32 entries;
   2193                 entries = fscanf(ps_piclen_file, "%d\n", &numbytes);
   2194                 if(1 != entries)
   2195                     numbytes = u4_ip_buf_len;
   2196             }
   2197 
   2198             u4_bytes_remaining = fread(pu1_bs_buf, sizeof(UWORD8), numbytes,
   2199                                        ps_ip_file);
   2200 
   2201             if(0 == u4_bytes_remaining)
   2202             {
   2203                 sprintf(ac_error_str, "\nUnable to read from input file");
   2204                 codec_exit(ac_error_str);
   2205             }
   2206 
   2207             s_video_decode_ip.e_cmd = IVD_CMD_VIDEO_DECODE;
   2208             s_video_decode_ip.u4_ts = u4_ip_frm_ts;
   2209             s_video_decode_ip.pv_stream_buffer = pu1_bs_buf;
   2210             s_video_decode_ip.u4_num_Bytes = u4_bytes_remaining;
   2211             s_video_decode_ip.u4_size = sizeof(ivd_video_decode_ip_t);
   2212             s_video_decode_op.u4_size = sizeof(ivd_video_decode_op_t);
   2213 
   2214             /*****************************************************************************/
   2215             /*   API Call: Header Decode                                                  */
   2216             /*****************************************************************************/
   2217             ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_video_decode_ip,
   2218                                        (void *)&s_video_decode_op);
   2219 
   2220             if(ret != IV_SUCCESS)
   2221             {
   2222                 sprintf(ac_error_str, "\nError in header decode %x",
   2223                         s_video_decode_op.u4_error_code);
   2224                 // codec_exit(ac_error_str);
   2225             }
   2226 
   2227             u4_num_bytes_dec = s_video_decode_op.u4_num_bytes_consumed;
   2228 #ifndef PROFILE_ENABLE
   2229             printf("%d\n",s_video_decode_op.u4_num_bytes_consumed);
   2230 #endif
   2231             file_pos += u4_num_bytes_dec;
   2232             total_bytes_comsumed += u4_num_bytes_dec;
   2233         }while(ret != IV_SUCCESS);
   2234 
   2235         /* copy pic_wd and pic_ht to initialize buffers */
   2236         s_app_ctx.u4_pic_wd = s_video_decode_op.u4_pic_wd;
   2237         s_app_ctx.u4_pic_ht = s_video_decode_op.u4_pic_ht;
   2238 
   2239         free(pu1_bs_buf);
   2240 
   2241 #if IOS_DISPLAY
   2242         s_app_ctx.i4_screen_wd = screen_wd;
   2243         s_app_ctx.i4_screen_ht = screen_ht;
   2244 #endif
   2245         {
   2246 
   2247             ivd_ctl_getbufinfo_ip_t s_ctl_ip;
   2248             ivd_ctl_getbufinfo_op_t s_ctl_op;
   2249             WORD32 outlen = 0;
   2250 
   2251             s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2252             s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_GETBUFINFO;
   2253             s_ctl_ip.u4_size = sizeof(ivd_ctl_getbufinfo_ip_t);
   2254             s_ctl_op.u4_size = sizeof(ivd_ctl_getbufinfo_op_t);
   2255             ret = ivd_cxa_api_function((iv_obj_t*)codec_obj, (void *)&s_ctl_ip,
   2256                                        (void *)&s_ctl_op);
   2257             if(ret != IV_SUCCESS)
   2258             {
   2259                 sprintf(ac_error_str, "Error in Get Buf Info %x", s_ctl_op.u4_error_code);
   2260                 codec_exit(ac_error_str);
   2261             }
   2262 
   2263             /* Allocate bitstream buffer */
   2264             u4_ip_buf_len = s_ctl_op.u4_min_in_buf_size[0];
   2265 #ifdef ADAPTIVE_TEST
   2266             u4_ip_buf_len = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT * 3 >> 1;
   2267 #endif
   2268             pu1_bs_buf = (UWORD8 *)malloc(u4_ip_buf_len);
   2269 
   2270             if(pu1_bs_buf == NULL)
   2271             {
   2272                 sprintf(ac_error_str,
   2273                         "\nAllocation failure for input buffer of i4_size %d",
   2274                         u4_ip_buf_len);
   2275                 codec_exit(ac_error_str);
   2276             }
   2277 
   2278 #ifdef ADAPTIVE_TEST
   2279             switch(s_app_ctx.e_output_chroma_format)
   2280             {
   2281                 case IV_YUV_420P:
   2282                 {
   2283                     s_ctl_op.u4_min_out_buf_size[0] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT;
   2284                     s_ctl_op.u4_min_out_buf_size[1] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT >> 2;
   2285                     s_ctl_op.u4_min_out_buf_size[2] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT >> 2;
   2286                     break;
   2287                 }
   2288                 case IV_YUV_420SP_UV:
   2289                 case IV_YUV_420SP_VU:
   2290                 {
   2291                     s_ctl_op.u4_min_out_buf_size[0] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT;
   2292                     s_ctl_op.u4_min_out_buf_size[1] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT >> 1;
   2293                     s_ctl_op.u4_min_out_buf_size[2] = 0;
   2294                     break;
   2295                 }
   2296                 case IV_YUV_422ILE:
   2297                 {
   2298                     s_ctl_op.u4_min_out_buf_size[0] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT * 2;
   2299                     s_ctl_op.u4_min_out_buf_size[1] = 0;
   2300                     s_ctl_op.u4_min_out_buf_size[2] = 0;
   2301                     break;
   2302                 }
   2303                 case IV_RGBA_8888:
   2304                 {
   2305                     s_ctl_op.u4_min_out_buf_size[0] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT * 4;
   2306                     s_ctl_op.u4_min_out_buf_size[1] = 0;
   2307                     s_ctl_op.u4_min_out_buf_size[2] = 0;
   2308                     break;
   2309                 }
   2310                 case IV_RGB_565:
   2311                 {
   2312                     s_ctl_op.u4_min_out_buf_size[0] = ADAPTIVE_MAX_WD * ADAPTIVE_MAX_HT * 2;
   2313                     s_ctl_op.u4_min_out_buf_size[1] = 0;
   2314                     s_ctl_op.u4_min_out_buf_size[2] = 0;
   2315                     break;
   2316                 }
   2317                 default:
   2318                     break;
   2319 
   2320             }
   2321 #endif
   2322             /* Allocate output buffer only if display buffers are not shared */
   2323             /* Or if shared and output is 420P */
   2324             if((0 == s_app_ctx.share_disp_buf) || (IV_YUV_420P == s_app_ctx.e_output_chroma_format))
   2325             {
   2326                 ps_out_buf->u4_min_out_buf_size[0] =
   2327                                 s_ctl_op.u4_min_out_buf_size[0];
   2328                 ps_out_buf->u4_min_out_buf_size[1] =
   2329                                 s_ctl_op.u4_min_out_buf_size[1];
   2330                 ps_out_buf->u4_min_out_buf_size[2] =
   2331                                 s_ctl_op.u4_min_out_buf_size[2];
   2332 
   2333                 outlen = s_ctl_op.u4_min_out_buf_size[0];
   2334                 if(s_ctl_op.u4_min_num_out_bufs > 1)
   2335                     outlen += s_ctl_op.u4_min_out_buf_size[1];
   2336 
   2337                 if(s_ctl_op.u4_min_num_out_bufs > 2)
   2338                     outlen += s_ctl_op.u4_min_out_buf_size[2];
   2339 
   2340                 ps_out_buf->pu1_bufs[0] = (UWORD8 *)malloc(outlen);
   2341                 if(ps_out_buf->pu1_bufs[0] == NULL)
   2342                 {
   2343                     sprintf(ac_error_str, "\nAllocation failure for output buffer of i4_size %d",
   2344                             outlen);
   2345                     codec_exit(ac_error_str);
   2346                 }
   2347 
   2348                 if(s_ctl_op.u4_min_num_out_bufs > 1)
   2349                     ps_out_buf->pu1_bufs[1] = ps_out_buf->pu1_bufs[0]
   2350                                     + (s_ctl_op.u4_min_out_buf_size[0]);
   2351 
   2352                 if(s_ctl_op.u4_min_num_out_bufs > 2)
   2353                     ps_out_buf->pu1_bufs[2] = ps_out_buf->pu1_bufs[1]
   2354                                     + (s_ctl_op.u4_min_out_buf_size[1]);
   2355 
   2356                 ps_out_buf->u4_num_bufs = s_ctl_op.u4_min_num_out_bufs;
   2357             }
   2358 
   2359 #ifdef APP_EXTRA_BUFS
   2360             s_app_ctx.disp_delay = EXTRA_DISP_BUFFERS;
   2361             s_ctl_op.u4_num_disp_bufs += EXTRA_DISP_BUFFERS;
   2362 #endif
   2363 
   2364             /*****************************************************************************/
   2365             /*   API Call: Allocate display buffers for display buffer shared case       */
   2366             /*****************************************************************************/
   2367 
   2368             for(i = 0; i < s_ctl_op.u4_num_disp_bufs; i++)
   2369             {
   2370 
   2371                 s_app_ctx.s_disp_buffers[i].u4_min_out_buf_size[0] =
   2372                                 s_ctl_op.u4_min_out_buf_size[0];
   2373                 s_app_ctx.s_disp_buffers[i].u4_min_out_buf_size[1] =
   2374                                 s_ctl_op.u4_min_out_buf_size[1];
   2375                 s_app_ctx.s_disp_buffers[i].u4_min_out_buf_size[2] =
   2376                                 s_ctl_op.u4_min_out_buf_size[2];
   2377 
   2378                 outlen = s_ctl_op.u4_min_out_buf_size[0];
   2379                 if(s_ctl_op.u4_min_num_out_bufs > 1)
   2380                     outlen += s_ctl_op.u4_min_out_buf_size[1];
   2381 
   2382                 if(s_ctl_op.u4_min_num_out_bufs > 2)
   2383                     outlen += s_ctl_op.u4_min_out_buf_size[2];
   2384 
   2385                 s_app_ctx.s_disp_buffers[i].pu1_bufs[0] = (UWORD8 *)malloc(outlen);
   2386 
   2387                 if(s_app_ctx.s_disp_buffers[i].pu1_bufs[0] == NULL)
   2388                 {
   2389                     sprintf(ac_error_str,
   2390                             "\nAllocation failure for output buffer of i4_size %d",
   2391                             outlen);
   2392                     codec_exit(ac_error_str);
   2393                 }
   2394 
   2395                 if(s_ctl_op.u4_min_num_out_bufs > 1)
   2396                     s_app_ctx.s_disp_buffers[i].pu1_bufs[1] =
   2397                                     s_app_ctx.s_disp_buffers[i].pu1_bufs[0]
   2398                                                     + (s_ctl_op.u4_min_out_buf_size[0]);
   2399 
   2400                 if(s_ctl_op.u4_min_num_out_bufs > 2)
   2401                     s_app_ctx.s_disp_buffers[i].pu1_bufs[2] =
   2402                                     s_app_ctx.s_disp_buffers[i].pu1_bufs[1]
   2403                                                     + (s_ctl_op.u4_min_out_buf_size[1]);
   2404 
   2405                 s_app_ctx.s_disp_buffers[i].u4_num_bufs =
   2406                                 s_ctl_op.u4_min_num_out_bufs;
   2407             }
   2408             s_app_ctx.num_disp_buf = s_ctl_op.u4_num_disp_bufs;
   2409         }
   2410 
   2411         /* Create display thread and wait for the display buffers to be initialized */
   2412         if(1 == s_app_ctx.display)
   2413         {
   2414             if(0 == s_app_ctx.display_thread_created)
   2415             {
   2416                 s_app_ctx.display_init_done = 0;
   2417                 ithread_create(s_app_ctx.display_thread_handle, NULL,
   2418                                                     (void *) &display_thread, (void *) &s_app_ctx);
   2419                 s_app_ctx.display_thread_created = 1;
   2420 
   2421                 while(1)
   2422                 {
   2423                     if(s_app_ctx.display_init_done)
   2424                         break;
   2425 
   2426                     ithread_msleep(1);
   2427                 }
   2428             }
   2429             s_app_ctx.u4_strd = s_app_ctx.get_stride();
   2430         }
   2431 
   2432 
   2433         /*****************************************************************************/
   2434         /*   API Call: Send the allocated display buffers to codec                   */
   2435         /*****************************************************************************/
   2436         {
   2437             ivd_set_display_frame_ip_t s_set_display_frame_ip;
   2438             ivd_set_display_frame_op_t s_set_display_frame_op;
   2439 
   2440             s_set_display_frame_ip.e_cmd = IVD_CMD_SET_DISPLAY_FRAME;
   2441             s_set_display_frame_ip.u4_size = sizeof(ivd_set_display_frame_ip_t);
   2442             s_set_display_frame_op.u4_size = sizeof(ivd_set_display_frame_op_t);
   2443 
   2444             s_set_display_frame_ip.num_disp_bufs = s_app_ctx.num_disp_buf;
   2445 
   2446             memcpy(&(s_set_display_frame_ip.s_disp_buffer),
   2447                    &(s_app_ctx.s_disp_buffers),
   2448                    s_app_ctx.num_disp_buf * sizeof(ivd_out_bufdesc_t));
   2449 
   2450             ret = ivd_cxa_api_function((iv_obj_t *)codec_obj,
   2451                                        (void *)&s_set_display_frame_ip,
   2452                                        (void *)&s_set_display_frame_op);
   2453 
   2454             if(IV_SUCCESS != ret)
   2455             {
   2456                 sprintf(ac_error_str, "Error in Set display frame");
   2457                 codec_exit(ac_error_str);
   2458             }
   2459 
   2460         }
   2461 
   2462     }
   2463 
   2464     /*************************************************************************/
   2465     /* Get frame dimensions for display buffers such as x_offset,y_offset    */
   2466     /* etc. This information might be needed to set display buffer           */
   2467     /* offsets in case of shared display buffer mode                         */
   2468     /*************************************************************************/
   2469     {
   2470 
   2471         ihevcd_cxa_ctl_get_frame_dimensions_ip_t s_ctl_get_frame_dimensions_ip;
   2472         ihevcd_cxa_ctl_get_frame_dimensions_op_t s_ctl_get_frame_dimensions_op;
   2473 
   2474         s_ctl_get_frame_dimensions_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2475         s_ctl_get_frame_dimensions_ip.e_sub_cmd =
   2476                         (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_GET_BUFFER_DIMENSIONS;
   2477         s_ctl_get_frame_dimensions_ip.u4_size =
   2478                         sizeof(ihevcd_cxa_ctl_get_frame_dimensions_ip_t);
   2479         s_ctl_get_frame_dimensions_op.u4_size =
   2480                         sizeof(ihevcd_cxa_ctl_get_frame_dimensions_op_t);
   2481 
   2482         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_get_frame_dimensions_ip,
   2483                                    (void *)&s_ctl_get_frame_dimensions_op);
   2484         if(IV_SUCCESS != ret)
   2485         {
   2486             sprintf(ac_error_str, "Error in Get buffer Dimensions");
   2487             codec_exit(ac_error_str);
   2488         }
   2489 
   2490 /*
   2491         printf("Frame offsets due to padding\n");
   2492         printf("s_ctl_get_frame_dimensions_op.x_offset[0] %d s_ctl_get_frame_dimensions_op.y_offset[0] %d\n",
   2493                s_ctl_get_frame_dimensions_op.u4_x_offset[0],
   2494                s_ctl_get_frame_dimensions_op.u4_y_offset[0]);
   2495 */
   2496     }
   2497 
   2498 
   2499     /*************************************************************************/
   2500     /* Get VUI parameters                                                    */
   2501     /*************************************************************************/
   2502     {
   2503 
   2504         ihevcd_cxa_ctl_get_vui_params_ip_t s_ctl_get_vui_params_ip;
   2505         ihevcd_cxa_ctl_get_vui_params_op_t s_ctl_get_vui_params_op;
   2506 
   2507         s_ctl_get_vui_params_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2508         s_ctl_get_vui_params_ip.e_sub_cmd =
   2509                         (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_GET_VUI_PARAMS;
   2510         s_ctl_get_vui_params_ip.u4_size =
   2511                         sizeof(ihevcd_cxa_ctl_get_vui_params_ip_t);
   2512         s_ctl_get_vui_params_op.u4_size =
   2513                         sizeof(ihevcd_cxa_ctl_get_vui_params_op_t);
   2514 
   2515         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_get_vui_params_ip,
   2516                                    (void *)&s_ctl_get_vui_params_op);
   2517         if(IV_SUCCESS != ret)
   2518         {
   2519             sprintf(ac_error_str, "Error in Get VUI params");
   2520             //codec_exit(ac_error_str);
   2521         }
   2522 
   2523     }
   2524 
   2525 
   2526     /*************************************************************************/
   2527     /* Set the decoder in frame decode mode. It was set in header decode     */
   2528     /* mode earlier                                                          */
   2529     /*************************************************************************/
   2530     {
   2531 
   2532         ivd_ctl_set_config_ip_t s_ctl_ip;
   2533         ivd_ctl_set_config_op_t s_ctl_op;
   2534 
   2535         s_ctl_ip.u4_disp_wd = STRIDE;
   2536         if(1 == s_app_ctx.display)
   2537             s_ctl_ip.u4_disp_wd = s_app_ctx.get_stride();
   2538         s_ctl_ip.e_frm_skip_mode = IVD_SKIP_NONE;
   2539 
   2540         s_ctl_ip.e_frm_out_mode = IVD_DISPLAY_FRAME_OUT;
   2541         s_ctl_ip.e_vid_dec_mode = IVD_DECODE_FRAME;
   2542         s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2543         s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_SETPARAMS;
   2544         s_ctl_ip.u4_size = sizeof(ivd_ctl_set_config_ip_t);
   2545 
   2546         s_ctl_op.u4_size = sizeof(ivd_ctl_set_config_op_t);
   2547 
   2548         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip, (void *)&s_ctl_op);
   2549 
   2550         if(IV_SUCCESS != ret)
   2551         {
   2552             sprintf(ac_error_str, "Error in Set Parameters");
   2553             //codec_exit(ac_error_str);
   2554         }
   2555 
   2556     }
   2557     /*************************************************************************/
   2558     /* If required disable deblocking and sao at given level                 */
   2559     /*************************************************************************/
   2560     set_degrade(codec_obj, s_app_ctx.i4_degrade_type, s_app_ctx.i4_degrade_pics);
   2561 #ifdef WINDOWS_TIMER
   2562     QueryPerformanceFrequency(&frequency);
   2563 #endif
   2564 #ifndef PRINT_PICSIZE
   2565     get_version(codec_obj);
   2566 #endif
   2567     while(u4_op_frm_ts < (s_app_ctx.u4_max_frm_ts + s_app_ctx.disp_delay))
   2568     {
   2569 
   2570 #ifdef TEST_FLUSH
   2571         if(u4_ip_frm_ts == FLUSH_FRM_CNT)
   2572         {
   2573             ivd_ctl_flush_ip_t s_ctl_ip;
   2574             ivd_ctl_flush_op_t s_ctl_op;
   2575 
   2576             s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2577             s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_FLUSH;
   2578             s_ctl_ip.u4_size = sizeof(ivd_ctl_flush_ip_t);
   2579             s_ctl_op.u4_size = sizeof(ivd_ctl_flush_op_t);
   2580             ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
   2581                                        (void *)&s_ctl_op);
   2582 
   2583             if(ret != IV_SUCCESS)
   2584             {
   2585                 printf("Error in Setting the decoder in flush mode\n");
   2586             }
   2587             file_pos = 0;
   2588 
   2589             fseek(ps_ip_file, file_pos, SEEK_SET);
   2590 
   2591         }
   2592 #endif
   2593         if(u4_ip_frm_ts < s_app_ctx.num_disp_buf)
   2594         {
   2595             release_disp_frame(codec_obj, u4_ip_frm_ts);
   2596         }
   2597 
   2598 
   2599         /*************************************************************************/
   2600         /* set num of cores                                                      */
   2601         /*************************************************************************/
   2602 #ifdef DYNAMIC_NUMCORES
   2603         {
   2604 
   2605             ihevcd_cxa_ctl_set_num_cores_ip_t s_ctl_set_cores_ip;
   2606             ihevcd_cxa_ctl_set_num_cores_op_t s_ctl_set_cores_op;
   2607 
   2608             s_ctl_set_cores_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2609             s_ctl_set_cores_ip.e_sub_cmd = IHEVCD_CXA_CMD_CTL_SET_NUM_CORES;
   2610             s_ctl_set_cores_ip.u4_num_cores =  1 + 3 * (u4_ip_frm_ts % 2);
   2611             s_ctl_set_cores_ip.u4_size = sizeof(ihevcd_cxa_ctl_set_num_cores_ip_t);
   2612             s_ctl_set_cores_op.u4_size = sizeof(ihevcd_cxa_ctl_set_num_cores_op_t);
   2613 
   2614             ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_set_cores_ip,
   2615                                        (void *)&s_ctl_set_cores_op);
   2616             if(ret != IV_SUCCESS)
   2617             {
   2618                 sprintf(ac_error_str, "\nError in setting number of cores");
   2619                 codec_exit(ac_error_str);
   2620             }
   2621 
   2622         }
   2623 #endif
   2624         /***********************************************************************/
   2625         /*   Seek the file to start of current frame, this is equavelent of    */
   2626         /*   having a parcer which tells the start of current frame            */
   2627         /***********************************************************************/
   2628         {
   2629             WORD32 numbytes;
   2630 
   2631             if(0 == s_app_ctx.u4_piclen_flag)
   2632             {
   2633                 fseek(ps_ip_file, file_pos, SEEK_SET);
   2634                 numbytes = u4_ip_buf_len;
   2635             }
   2636             else
   2637             {
   2638                 WORD32 entries;
   2639                 entries = fscanf(ps_piclen_file, "%d\n", &numbytes);
   2640                 if(1 != entries)
   2641                     numbytes = u4_ip_buf_len;
   2642             }
   2643 
   2644             u4_bytes_remaining = fread(pu1_bs_buf, sizeof(UWORD8),
   2645                                        numbytes, ps_ip_file);
   2646 
   2647             if(u4_bytes_remaining == 0)
   2648             {
   2649                 if(1 == s_app_ctx.loopback)
   2650                 {
   2651                     file_pos = 0;
   2652                     if(0 == s_app_ctx.u4_piclen_flag)
   2653                     {
   2654                         fseek(ps_ip_file, file_pos, SEEK_SET);
   2655                         numbytes = u4_ip_buf_len;
   2656                     }
   2657                     else
   2658                     {
   2659                         WORD32 entries;
   2660                         entries = fscanf(ps_piclen_file, "%d\n", &numbytes);
   2661                         if(1 != entries)
   2662                             numbytes = u4_ip_buf_len;
   2663                     }
   2664 
   2665 
   2666                     u4_bytes_remaining = fread(pu1_bs_buf, sizeof(UWORD8),
   2667                                                numbytes, ps_ip_file);
   2668                 }
   2669                 else
   2670                     break;
   2671             }
   2672         }
   2673 
   2674         /*********************************************************************/
   2675         /* Following calls can be enabled at diffent times                   */
   2676         /*********************************************************************/
   2677 #if ENABLE_DEGRADE
   2678         if(u4_op_frm_ts >= 10000)
   2679             disable_deblocking(codec_obj, 4);
   2680 
   2681         if(u4_op_frm_ts == 30000)
   2682             enable_deblocking(codec_obj);
   2683 
   2684         if(u4_op_frm_ts == 10000)
   2685             enable_skippb_frames(codec_obj);
   2686 
   2687         if(u4_op_frm_ts == 60000)
   2688             disable_skippb_frames(codec_obj);
   2689 
   2690         if(u4_op_frm_ts == 30000)
   2691             enable_skipb_frames(codec_obj);
   2692 
   2693         if(u4_op_frm_ts == 60000)
   2694             disable_skipb_frames(codec_obj);
   2695 #endif
   2696 
   2697 
   2698         {
   2699             ivd_video_decode_ip_t s_video_decode_ip;
   2700             ivd_video_decode_op_t s_video_decode_op;
   2701 #ifdef PROFILE_ENABLE
   2702             UWORD32 s_elapsed_time;
   2703             TIMER s_start_timer;
   2704             TIMER s_end_timer;
   2705 #endif
   2706 
   2707 
   2708             s_video_decode_ip.e_cmd = IVD_CMD_VIDEO_DECODE;
   2709             s_video_decode_ip.u4_ts = u4_ip_frm_ts;
   2710             s_video_decode_ip.pv_stream_buffer = pu1_bs_buf;
   2711             s_video_decode_ip.u4_num_Bytes = u4_bytes_remaining;
   2712             s_video_decode_ip.u4_size = sizeof(ivd_video_decode_ip_t);
   2713             s_video_decode_ip.s_out_buffer.u4_min_out_buf_size[0] =
   2714                             ps_out_buf->u4_min_out_buf_size[0];
   2715             s_video_decode_ip.s_out_buffer.u4_min_out_buf_size[1] =
   2716                             ps_out_buf->u4_min_out_buf_size[1];
   2717             s_video_decode_ip.s_out_buffer.u4_min_out_buf_size[2] =
   2718                             ps_out_buf->u4_min_out_buf_size[2];
   2719 
   2720             s_video_decode_ip.s_out_buffer.pu1_bufs[0] =
   2721                             ps_out_buf->pu1_bufs[0];
   2722             s_video_decode_ip.s_out_buffer.pu1_bufs[1] =
   2723                             ps_out_buf->pu1_bufs[1];
   2724             s_video_decode_ip.s_out_buffer.pu1_bufs[2] =
   2725                             ps_out_buf->pu1_bufs[2];
   2726             s_video_decode_ip.s_out_buffer.u4_num_bufs =
   2727                             ps_out_buf->u4_num_bufs;
   2728             s_video_decode_op.u4_size = sizeof(ivd_video_decode_op_t);
   2729 
   2730             /* Get display buffer pointers */
   2731             if(1 == s_app_ctx.display)
   2732             {
   2733                 WORD32 wr_idx;
   2734 
   2735                 wr_idx = dispq_producer_dequeue(&s_app_ctx);
   2736 
   2737                 if(s_app_ctx.quit)
   2738                     break;
   2739 
   2740                 s_app_ctx.set_disp_buffers(s_app_ctx.pv_disp_ctx, wr_idx,
   2741                                            &s_video_decode_ip.s_out_buffer.pu1_bufs[0],
   2742                                            &s_video_decode_ip.s_out_buffer.pu1_bufs[1],
   2743                                            &s_video_decode_ip.s_out_buffer.pu1_bufs[2]);
   2744             }
   2745 
   2746             /*****************************************************************************/
   2747             /*   API Call: Video Decode                                                  */
   2748             /*****************************************************************************/
   2749 
   2750             GETTIME(&s_start_timer);
   2751 
   2752             ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_video_decode_ip,
   2753                                        (void *)&s_video_decode_op);
   2754 
   2755 
   2756             GETTIME(&s_end_timer);
   2757             ELAPSEDTIME(s_start_timer, s_end_timer, s_elapsed_time, frequency);
   2758 #ifdef PROFILE_ENABLE
   2759             {
   2760                 UWORD32 peak_avg, id;
   2761                 u4_tot_cycles += s_elapsed_time;
   2762                 peak_window[peak_window_idx++] = s_elapsed_time;
   2763                 if(peak_window_idx == PEAK_WINDOW_SIZE)
   2764                     peak_window_idx = 0;
   2765                 peak_avg = 0;
   2766                 for(id = 0; id < PEAK_WINDOW_SIZE; id++)
   2767                 {
   2768                     peak_avg += peak_window[id];
   2769                 }
   2770                 peak_avg /= PEAK_WINDOW_SIZE;
   2771                 if(peak_avg > peak_avg_max)
   2772                     peak_avg_max = peak_avg;
   2773                 frm_cnt++;
   2774 
   2775                 printf("FrameNum: %4d TimeTaken(microsec): %6d AvgTime: %6d PeakAvgTimeMax: %6d Output: %2d NumBytes: %6d \n",
   2776                        frm_cnt, s_elapsed_time, u4_tot_cycles / frm_cnt, peak_avg_max, s_video_decode_op.u4_output_present, s_video_decode_op.u4_num_bytes_consumed);
   2777 
   2778             }
   2779 #ifdef INTEL_CE5300
   2780             time_consumed += s_elapsed_time;
   2781             bytes_consumed += s_video_decode_op.u4_num_bytes_consumed;
   2782             if(!(frm_cnt % (s_app_ctx.fps)))
   2783             {
   2784                 time_consumed = time_consumed / s_app_ctx.fps;
   2785                 printf("Average decode time(micro sec) for the last second = %6d\n", time_consumed);
   2786                 printf("Average bitrate(kb) for the last second = %6d\n", (bytes_consumed * 8) / 1024);
   2787                 time_consumed = 0;
   2788                 bytes_consumed = 0;
   2789 
   2790             }
   2791 #endif
   2792 #else
   2793             printf("%d\n", s_video_decode_op.u4_num_bytes_consumed);
   2794 #endif
   2795 
   2796             if(ret != IV_SUCCESS)
   2797             {
   2798                 printf("Error in video Frame decode : ret %x Error %x\n", ret,
   2799                        s_video_decode_op.u4_error_code);
   2800             }
   2801 
   2802             if((IV_SUCCESS != ret) &&
   2803                             ((s_video_decode_op.u4_error_code & 0xFF) == IVD_RES_CHANGED))
   2804             {
   2805                 ivd_ctl_reset_ip_t s_ctl_ip;
   2806                 ivd_ctl_reset_op_t s_ctl_op;
   2807 
   2808                 flush_output(codec_obj, &s_app_ctx, ps_out_buf,
   2809                              pu1_bs_buf, &u4_op_frm_ts,
   2810                              ps_op_file, ps_op_chksum_file,
   2811                              u4_ip_frm_ts, u4_bytes_remaining);
   2812 
   2813                 s_ctl_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2814                 s_ctl_ip.e_sub_cmd = IVD_CMD_CTL_RESET;
   2815                 s_ctl_ip.u4_size = sizeof(ivd_ctl_reset_ip_t);
   2816                 s_ctl_op.u4_size = sizeof(ivd_ctl_reset_op_t);
   2817 
   2818                 ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_ip,
   2819                                            (void *)&s_ctl_op);
   2820                 if(IV_SUCCESS != ret)
   2821                 {
   2822                     sprintf(ac_error_str, "Error in Reset");
   2823                     codec_exit(ac_error_str);
   2824                 }
   2825                 /*************************************************************************/
   2826                 /* set num of cores                                                      */
   2827                 /*************************************************************************/
   2828                 {
   2829 
   2830                     ihevcd_cxa_ctl_set_num_cores_ip_t s_ctl_set_cores_ip;
   2831                     ihevcd_cxa_ctl_set_num_cores_op_t s_ctl_set_cores_op;
   2832 
   2833                     s_ctl_set_cores_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2834                     s_ctl_set_cores_ip.e_sub_cmd = (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_SET_NUM_CORES;
   2835                     s_ctl_set_cores_ip.u4_num_cores = s_app_ctx.u4_num_cores;
   2836                     s_ctl_set_cores_ip.u4_size = sizeof(ihevcd_cxa_ctl_set_num_cores_ip_t);
   2837                     s_ctl_set_cores_op.u4_size = sizeof(ihevcd_cxa_ctl_set_num_cores_op_t);
   2838 
   2839                     ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_set_cores_ip,
   2840                                                (void *)&s_ctl_set_cores_op);
   2841                     if(ret != IV_SUCCESS)
   2842                     {
   2843                         sprintf(ac_error_str, "\nError in setting number of cores");
   2844                         codec_exit(ac_error_str);
   2845                     }
   2846 
   2847                 }
   2848                 /*************************************************************************/
   2849                 /* set processsor                                                        */
   2850                 /*************************************************************************/
   2851                 {
   2852 
   2853                     ihevcd_cxa_ctl_set_processor_ip_t s_ctl_set_num_processor_ip;
   2854                     ihevcd_cxa_ctl_set_processor_op_t s_ctl_set_num_processor_op;
   2855 
   2856                     s_ctl_set_num_processor_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2857                     s_ctl_set_num_processor_ip.e_sub_cmd = (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_SET_PROCESSOR;
   2858                     s_ctl_set_num_processor_ip.u4_arch = s_app_ctx.e_arch;
   2859                     s_ctl_set_num_processor_ip.u4_soc = s_app_ctx.e_soc;
   2860                     s_ctl_set_num_processor_ip.u4_size = sizeof(ihevcd_cxa_ctl_set_processor_ip_t);
   2861                     s_ctl_set_num_processor_op.u4_size = sizeof(ihevcd_cxa_ctl_set_processor_op_t);
   2862 
   2863                     ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_ctl_set_num_processor_ip,
   2864                                                (void *)&s_ctl_set_num_processor_op);
   2865                     if(ret != IV_SUCCESS)
   2866                     {
   2867                         sprintf(ac_error_str, "\nError in setting Processor type");
   2868                         codec_exit(ac_error_str);
   2869                     }
   2870 
   2871                 }
   2872             }
   2873             /*************************************************************************/
   2874             /* Get SEI mastering display color volume parameters                     */
   2875             /*************************************************************************/
   2876             if(1 == s_video_decode_op.u4_output_present)
   2877             {
   2878 
   2879                 ihevcd_cxa_ctl_get_sei_mastering_params_ip_t s_ctl_get_sei_mastering_params_ip;
   2880                 ihevcd_cxa_ctl_get_sei_mastering_params_op_t s_ctl_get_sei_mastering_params_op;
   2881 
   2882                 s_ctl_get_sei_mastering_params_ip.e_cmd = IVD_CMD_VIDEO_CTL;
   2883                 s_ctl_get_sei_mastering_params_ip.e_sub_cmd =
   2884                                 (IVD_CONTROL_API_COMMAND_TYPE_T)IHEVCD_CXA_CMD_CTL_GET_SEI_MASTERING_PARAMS;
   2885                 s_ctl_get_sei_mastering_params_ip.u4_size =
   2886                                 sizeof(ihevcd_cxa_ctl_get_sei_mastering_params_ip_t);
   2887                 s_ctl_get_sei_mastering_params_op.u4_size =
   2888                                 sizeof(ihevcd_cxa_ctl_get_sei_mastering_params_op_t);
   2889 
   2890                 ret = ivd_cxa_api_function((iv_obj_t *)codec_obj,
   2891                                      (void *)&s_ctl_get_sei_mastering_params_ip,
   2892                                      (void *)&s_ctl_get_sei_mastering_params_op);
   2893                 if(IV_SUCCESS != ret)
   2894                 {
   2895                     sprintf(ac_error_str, "Error in Get SEI mastering params");
   2896                     //codec_exit(ac_error_str);
   2897                 }
   2898 
   2899             }
   2900 
   2901 
   2902             if((1 == s_app_ctx.display) &&
   2903                             (1 == s_video_decode_op.u4_output_present))
   2904             {
   2905                 dispq_producer_queue(&s_app_ctx);
   2906             }
   2907 
   2908             if(IV_B_FRAME == s_video_decode_op.e_pic_type)
   2909                 s_app_ctx.b_pic_present |= 1;
   2910 
   2911             u4_num_bytes_dec = s_video_decode_op.u4_num_bytes_consumed;
   2912 
   2913             file_pos += u4_num_bytes_dec;
   2914             total_bytes_comsumed += u4_num_bytes_dec;
   2915             u4_ip_frm_ts++;
   2916 
   2917 
   2918             if(1 == s_video_decode_op.u4_output_present)
   2919             {
   2920                 width = s_video_decode_op.s_disp_frm_buf.u4_y_wd;
   2921                 height = s_video_decode_op.s_disp_frm_buf.u4_y_ht;
   2922                 dump_output(&s_app_ctx, &(s_video_decode_op.s_disp_frm_buf),
   2923                             s_video_decode_op.u4_disp_buf_id, ps_op_file,
   2924                             ps_op_chksum_file,
   2925                             u4_op_frm_ts, s_app_ctx.u4_file_save_flag,
   2926                             s_app_ctx.u4_chksum_save_flag);
   2927 
   2928                 u4_op_frm_ts++;
   2929             }
   2930             else
   2931             {
   2932                 if((s_video_decode_op.u4_error_code >> IVD_FATALERROR) & 1)
   2933                 {
   2934                     printf("Fatal error\n");
   2935                     break;
   2936                 }
   2937             }
   2938 
   2939         }
   2940     }
   2941 
   2942     /***********************************************************************/
   2943     /*      To get the last decoded frames, call process with NULL input    */
   2944     /***********************************************************************/
   2945     flush_output(codec_obj, &s_app_ctx, ps_out_buf,
   2946                  pu1_bs_buf, &u4_op_frm_ts,
   2947                  ps_op_file, ps_op_chksum_file,
   2948                  u4_ip_frm_ts, u4_bytes_remaining);
   2949 
   2950     /* set disp_end flag */
   2951     s_app_ctx.quit = 1;
   2952 
   2953 
   2954 #ifdef PROFILE_ENABLE
   2955     printf("Summary\n");
   2956     printf("Input filename                  : %s\n", s_app_ctx.ac_ip_fname);
   2957     printf("Output Width                    : %-4d\n", width);
   2958     printf("Output Height                   : %-4d\n", height);
   2959 
   2960     if(frm_cnt)
   2961     {
   2962         double avg = u4_tot_cycles / frm_cnt;
   2963         double bytes_avg = total_bytes_comsumed / frm_cnt;
   2964         double bitrate = (bytes_avg * 8 * s_app_ctx.fps) / 1000000;
   2965         printf("Bitrate @ %2d fps(mbps)          : %-6.2f\n", s_app_ctx.fps, bitrate);
   2966         printf("Average decode time(micro sec)  : %-6d\n", (WORD32)avg);
   2967         printf("Avg Peak decode time(%2d frames) : %-6d\n", PEAK_WINDOW_SIZE, (WORD32)peak_avg_max);
   2968         avg = (u4_tot_cycles + u4_tot_fmt_cycles) * 1.0 / frm_cnt;
   2969 
   2970         if(0 == s_app_ctx.share_disp_buf)
   2971             printf("FPS achieved (with format conv) : %-3.2f\n", 1000000 / avg);
   2972         else
   2973             printf("FPS achieved                    : %-3.2f\n", 1000000 / avg);
   2974     }
   2975 #endif
   2976     /***********************************************************************/
   2977     /*   Clear the decoder, close all the files, free all the memory       */
   2978     /***********************************************************************/
   2979     if(1 == s_app_ctx.display)
   2980     {
   2981         s_app_ctx.display_deinit_flag = 1;
   2982         /* wait for display to finish */
   2983         if(s_app_ctx.display_thread_created)
   2984         {
   2985             ithread_join(s_app_ctx.display_thread_handle, NULL);
   2986         }
   2987         free(s_app_ctx.display_thread_handle);
   2988     }
   2989 
   2990     {
   2991         ivd_delete_ip_t s_delete_dec_ip;
   2992         ivd_delete_op_t s_delete_dec_op;
   2993 
   2994         s_delete_dec_ip.e_cmd = IVD_CMD_DELETE;
   2995         s_delete_dec_ip.u4_size = sizeof(ivd_delete_ip_t);
   2996         s_delete_dec_op.u4_size = sizeof(ivd_delete_op_t);
   2997 
   2998         ret = ivd_cxa_api_function((iv_obj_t *)codec_obj, (void *)&s_delete_dec_ip,
   2999                                    (void *)&s_delete_dec_op);
   3000 
   3001         if(IV_SUCCESS != ret)
   3002         {
   3003             sprintf(ac_error_str, "Error in Codec delete");
   3004             codec_exit(ac_error_str);
   3005         }
   3006     }
   3007     /***********************************************************************/
   3008     /*              Close all the files and free all the memory            */
   3009     /***********************************************************************/
   3010     {
   3011         fclose(ps_ip_file);
   3012 
   3013         if(1 == s_app_ctx.u4_file_save_flag)
   3014         {
   3015             fclose(ps_op_file);
   3016         }
   3017         if(1 == s_app_ctx.u4_chksum_save_flag)
   3018         {
   3019             fclose(ps_op_chksum_file);
   3020         }
   3021 
   3022     }
   3023 
   3024     if(0 == s_app_ctx.share_disp_buf)
   3025     {
   3026         free(ps_out_buf->pu1_bufs[0]);
   3027     }
   3028 
   3029     for(i = 0; i < s_app_ctx.num_disp_buf; i++)
   3030     {
   3031         free(s_app_ctx.s_disp_buffers[i].pu1_bufs[0]);
   3032     }
   3033 
   3034     free(ps_out_buf);
   3035     free(pu1_bs_buf);
   3036 
   3037     if(s_app_ctx.display_thread_handle)
   3038         free(s_app_ctx.display_thread_handle);
   3039 
   3040     return (0);
   3041 }
   3042