Support for level greater than level at init in Decoder

Added support to check num_ref_frames  in SPS
and num_reorder_frames in VUI before returning error for level

Bug: 22860270

Change-Id: I392bab419385ca239836d200f9f2b064915a8a46
This commit is contained in:
Hamsalekha S 2015-07-28 14:41:24 +05:30 committed by Marco Nelissen
parent e789d1d2e2
commit 8a50328131
4 changed files with 87 additions and 12 deletions

View file

@ -78,7 +78,8 @@ IV_API_CALL_STATUS_T ih264d_api_function(iv_obj_t *ps_handle, void *pv_api_ip,vo
typedef enum {
IH264D_VID_HDR_DEC_NUM_FRM_BUF_NOT_SUFFICIENT = IVD_DUMMY_ELEMENT_FOR_CODEC_EXTENSIONS + 1,
IH264D_UNSUPPORTED_LEVEL = IVD_DUMMY_ELEMENT_FOR_CODEC_EXTENSIONS + 2
IH264D_UNSUPPORTED_LEVEL = IVD_DUMMY_ELEMENT_FOR_CODEC_EXTENSIONS + 2,
IH264D_UNSUPPORTED_NUM_REF_FRAMES = IVD_DUMMY_ELEMENT_FOR_CODEC_EXTENSIONS + 3
}IH264D_ERROR_CODES_T;

View file

@ -728,6 +728,12 @@ WORD32 ih264d_parse_sps(dec_struct_t *ps_dec, dec_bit_stream_t *ps_bitstrm)
return ERROR_NUM_REF;
}
ps_seq->u1_num_ref_frames = u4_temp;
if(ps_seq->u1_num_ref_frames > ps_dec->u4_num_ref_frames_at_init)
{
return IH264D_UNSUPPORTED_NUM_REF_FRAMES;
}
COPYTHECONTEXT("SPS: num_ref_frames",ps_seq->u1_num_ref_frames);
ps_seq->u1_gaps_in_frame_num_value_allowed_flag = ih264d_get_bit_h264(
@ -930,10 +936,6 @@ WORD32 ih264d_parse_sps(dec_struct_t *ps_dec, dec_bit_stream_t *ps_bitstrm)
ps_dec->u2_disp_width = i4_cropped_wd;
}
if(ps_dec->u4_level_at_init < u1_level_idc)
{
return IH264D_UNSUPPORTED_LEVEL;
}
ps_seq->u1_is_valid = TRUE;
@ -944,6 +946,44 @@ WORD32 ih264d_parse_sps(dec_struct_t *ps_dec, dec_bit_stream_t *ps_bitstrm)
return ret;
}
if(ps_dec->u4_level_at_init < u1_level_idc)
{
UWORD32 u4_num_pic_bufs_reqd, u4_num_reorder_frames,
u4_num_mv_bufs_reqd;
UWORD32 u4_num_pic_bufs_memory, u4_num_mv_bufs_memory;
UWORD32 u4_num_ref_frames;
u4_num_ref_frames = ps_seq->u1_num_ref_frames;
if(1 == ps_seq->u1_vui_parameters_present_flag)
{
u4_num_reorder_frames = ps_seq->s_vui.u4_num_reorder_frames;
}
else
{
u4_num_reorder_frames = ps_dec->u4_num_reorder_frames_at_init;
}
u4_num_pic_bufs_reqd = u4_num_ref_frames + u4_num_reorder_frames + 1;
u4_num_pic_bufs_memory = ih264d_get_numbuf_dpb_bank(ps_dec, u2_frm_wd_y,
u2_frm_ht_y);
u4_num_mv_bufs_reqd = u4_num_ref_frames + 1;
if(u4_num_mv_bufs_reqd < 2)
u4_num_mv_bufs_reqd = 2;
u4_num_mv_bufs_memory = ih264d_get_numbuf_mv_bank(ps_dec, u2_pic_wd,
u2_pic_ht);
if((u4_num_pic_bufs_reqd > u4_num_pic_bufs_memory)
|| (u4_num_mv_bufs_reqd > u4_num_mv_bufs_memory))
{
return IH264D_UNSUPPORTED_LEVEL;
}
}
ps_dec->u2_pic_wd = u2_pic_wd;
ps_dec->u2_pic_ht = u2_pic_ht;

View file

@ -831,7 +831,7 @@ WORD32 ih264d_init_dec_mb_grp(dec_struct_t *ps_dec)
/*!
**************************************************************************
* \if Function name : get_numbuf_dpb_bank \endif
* \if Function name : ih264d_get_numbuf_dpb_bank \endif
*
* \brief
* Initializes the picture.
@ -844,7 +844,7 @@ WORD32 ih264d_init_dec_mb_grp(dec_struct_t *ps_dec)
* NON -IDR picture is encountered.
**************************************************************************
*/
static WORD32 get_numbuf_dpb_bank(dec_struct_t *ps_dec)
WORD32 ih264d_get_numbuf_dpb_bank(dec_struct_t *ps_dec, UWORD32 u4_frame_wd, UWORD32 u4_frame_ht)
{
WORD32 i4_DPB_size;
WORD32 i4_pic_size;
@ -852,13 +852,11 @@ static WORD32 get_numbuf_dpb_bank(dec_struct_t *ps_dec)
UWORD32 Ysize;
UWORD32 UVsize;
UWORD32 one_frm_size;
UWORD32 luma_height;
luma_height = ps_dec->u2_pic_ht;
i4_DPB_size = ps_dec->ps_mem_tab[MEM_REC_REF_PIC].u4_mem_size;
Ysize = (ps_dec->u2_frm_wd_y) * (luma_height + (PAD_LEN_Y_V << 2));
Ysize = u4_frame_wd * u4_frame_ht;
UVsize = Ysize >> 2;
@ -889,6 +887,32 @@ static WORD32 get_numbuf_dpb_bank(dec_struct_t *ps_dec)
return i4_num_buf_alloc;
}
/*!
**************************************************************************
* \if Function name : ih264d_get_numbuf_mv_bank \endif
*
* \brief
* Computes number of MVbank buffers that can be allocated.
*
* \return
* Number of MV bank buffers that can be allocated.
*
* \note
**************************************************************************
*/
UWORD32 ih264d_get_numbuf_mv_bank(dec_struct_t *ps_dec, UWORD32 width,
UWORD32 height)
{
UWORD32 u4_mv_bank_size,one_frame_size;
UWORD32 u4_num_buf_alloc;
u4_mv_bank_size = ps_dec->ps_mem_tab[MEM_REC_MVBANK].u4_mem_size;
one_frame_size = sizeof(mv_pred_t)
* ((width * (height + PAD_MV_BANK_ROW)) >> 4);
u4_num_buf_alloc = u4_mv_bank_size / one_frame_size;
return u4_num_buf_alloc;
}
/*!
**************************************************************************
* \if Function name : ih264d_init_pic \endif
@ -955,7 +979,8 @@ WORD32 ih264d_init_pic(dec_struct_t *ps_dec,
if(ps_dec->u4_share_disp_buf == 0)
{
i4_pic_bufs = get_numbuf_dpb_bank(ps_dec);
i4_pic_bufs = ih264d_get_numbuf_dpb_bank(ps_dec, ps_dec->u2_frm_wd_y,
ps_dec->u2_frm_ht_y);
}
else
{
@ -2514,6 +2539,7 @@ WORD32 ih264d_create_mv_bank(void *pv_dec,
UWORD8 *pu1_col_zero_flag_buf;
dec_struct_t *ps_dec = (dec_struct_t *)pv_dec;
WORD32 buf_ret;
UWORD32 u4_num_bufs;
pu1_mv_buf_mgr_base = ps_dec->ps_mem_tab[MEM_REC_MV_BUF_MGR].pv_base;
u4_mv_buf_mgr_mem_used = 0;
@ -2532,7 +2558,11 @@ WORD32 ih264d_create_mv_bank(void *pv_dec,
u4_mv_buf_mgr_mem_used += sizeof(col_mv_buf_t) * (H264_MAX_REF_PICS * 2);
u4_mv_buf_mgr_mem_used = ALIGN128(u4_mv_buf_mgr_mem_used);
for(i = 0 ; i < ps_dec->u1_max_dec_frame_buffering + 1; i++)
u4_num_bufs = ih264d_get_numbuf_mv_bank(ps_dec, ui_width, ui_height);
u4_num_bufs = MIN(u4_num_bufs, ps_dec->u1_pic_bufs);
for(i = 0 ; i < u4_num_bufs ; i++)
{
pu1_col_zero_flag_buf = pu1_mv_buf_mgr_base + u4_mv_buf_mgr_mem_used;
u4_mv_buf_mgr_mem_used += col_flag_buffer_size;

View file

@ -97,5 +97,9 @@ WORD32 ih264d_get_next_nal_unit(UWORD8 *pu1_buf,
UWORD32 u4_cur_pos,
UWORD32 u4_max_ofst,
UWORD32 *pu4_length_of_start_code);
UWORD32 ih264d_get_numbuf_mv_bank(dec_struct_t *ps_dec, UWORD32 width, UWORD32 height);
WORD32 ih264d_get_numbuf_dpb_bank(dec_struct_t *ps_dec,
UWORD32 u2_frame_wd,
UWORD32 u2_frame_ht);
#endif /* _IH264D_UTILS_H_ */