Example #1
0
static bool hevc_parse_scaling_list_rbsp( bs_t *p_bs )
{
    if( bs_remain( p_bs ) < 16 )
        return false;

    for( int i=0; i<4; i++ )
    {
        for( int j=0; j<6; j += (i == 3) ? 3 : 1 )
        {
            if( bs_read1( p_bs ) == 0 )
                bs_read_ue( p_bs );
            else
            {
                unsigned nextCoef = 8;
                unsigned coefNum = __MIN( 64, (1 << (4 + (i << 1))));
                if( i > 1 )
                {
                    nextCoef = bs_read_se( p_bs ) + 8;
                }
                for( unsigned k=0; k<coefNum; k++ )
                {
                    nextCoef = ( nextCoef + bs_read_se( p_bs ) + 256 ) % 256;
                }
            }
        }
    }

    return true;
}
Example #2
0
//7.3.2.1.1 Scaling list syntax
void read_scaling_list(bs_t* b, int* scalingList, int sizeOfScalingList, int useDefaultScalingMatrixFlag)
{
	int j;
	if (scalingList == NULL)
	{
		return;
	}

	int lastScale = 8;
	int nextScale = 8;
	for (j = 0; j < sizeOfScalingList; j++)
	{
		if (nextScale != 0)
		{
			int delta_scale = bs_read_se(b);
			nextScale = (lastScale + delta_scale + 256) % 256;
			useDefaultScalingMatrixFlag = (j == 0 && nextScale == 0);
		}
		scalingList[j] = (nextScale == 0) ? lastScale : nextScale;
		lastScale = scalingList[j];
	}
}
Example #3
0
int h264_parse_sps( const uint8_t *p_sps_buf, int i_sps_size,
                    struct nal_sps *p_sps )
{
    uint8_t *pb_dec = NULL;
    int     i_dec = 0;
    bs_t s;
    int i_tmp;

    if (i_sps_size < 5 || (p_sps_buf[4] & 0x1f) != NAL_SPS)
        return -1;

    memset( p_sps, 0, sizeof(struct nal_sps) );
    CreateRbspFromNAL( &pb_dec, &i_dec, &p_sps_buf[5],
                      i_sps_size - 5 );

    bs_init( &s, pb_dec, i_dec );
    int i_profile_idc = bs_read( &s, 8 );
    p_sps->i_profile = i_profile_idc;
    p_sps->i_profile_compatibility = bs_read( &s, 8 );
    p_sps->i_level = bs_read( &s, 8 );
    /* sps id */
    p_sps->i_id = bs_read_ue( &s );
    if( p_sps->i_id >= SPS_MAX || p_sps->i_id < 0 )
    {
        free( pb_dec );
        return -1;
    }

    if( i_profile_idc == PROFILE_H264_HIGH || i_profile_idc == PROFILE_H264_HIGH_10 ||
        i_profile_idc == PROFILE_H264_HIGH_422 || i_profile_idc == PROFILE_H264_HIGH_444_PREDICTIVE ||
        i_profile_idc ==  PROFILE_H264_CAVLC_INTRA || i_profile_idc ==  PROFILE_H264_SVC_BASELINE ||
        i_profile_idc ==  PROFILE_H264_SVC_HIGH )
    {
        /* chroma_format_idc */
        const int i_chroma_format_idc = bs_read_ue( &s );
        if( i_chroma_format_idc == 3 )
            bs_skip( &s, 1 ); /* separate_colour_plane_flag */
        /* bit_depth_luma_minus8 */
        bs_read_ue( &s );
        /* bit_depth_chroma_minus8 */
        bs_read_ue( &s );
        /* qpprime_y_zero_transform_bypass_flag */
        bs_skip( &s, 1 );
        /* seq_scaling_matrix_present_flag */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            for( int i = 0; i < ((3 != i_chroma_format_idc) ? 8 : 12); i++ )
            {
                /* seq_scaling_list_present_flag[i] */
                i_tmp = bs_read( &s, 1 );
                if( !i_tmp )
                    continue;
                const int i_size_of_scaling_list = (i < 6 ) ? 16 : 64;
                /* scaling_list (...) */
                int i_lastscale = 8;
                int i_nextscale = 8;
                for( int j = 0; j < i_size_of_scaling_list; j++ )
                {
                    if( i_nextscale != 0 )
                    {
                        /* delta_scale */
                        i_tmp = bs_read_se( &s );
                        i_nextscale = ( i_lastscale + i_tmp + 256 ) % 256;
                        /* useDefaultScalingMatrixFlag = ... */
                    }
                    /* scalinglist[j] */
                    i_lastscale = ( i_nextscale == 0 ) ? i_lastscale : i_nextscale;
                }
            }
        }
    }

    /* Skip i_log2_max_frame_num */
    p_sps->i_log2_max_frame_num = bs_read_ue( &s );
    if( p_sps->i_log2_max_frame_num > 12)
        p_sps->i_log2_max_frame_num = 12;
    /* Read poc_type */
    p_sps->i_pic_order_cnt_type = bs_read_ue( &s );
    if( p_sps->i_pic_order_cnt_type == 0 )
    {
        /* skip i_log2_max_poc_lsb */
        p_sps->i_log2_max_pic_order_cnt_lsb = bs_read_ue( &s );
        if( p_sps->i_log2_max_pic_order_cnt_lsb > 12 )
            p_sps->i_log2_max_pic_order_cnt_lsb = 12;
    }
    else if( p_sps->i_pic_order_cnt_type == 1 )
    {
        int i_cycle;
        /* skip b_delta_pic_order_always_zero */
        p_sps->i_delta_pic_order_always_zero_flag = bs_read( &s, 1 );
        /* skip i_offset_for_non_ref_pic */
        bs_read_se( &s );
        /* skip i_offset_for_top_to_bottom_field */
        bs_read_se( &s );
        /* read i_num_ref_frames_in_poc_cycle */
        i_cycle = bs_read_ue( &s );
        if( i_cycle > 256 ) i_cycle = 256;
        while( i_cycle > 0 )
        {
            /* skip i_offset_for_ref_frame */
            bs_read_se(&s );
            i_cycle--;
        }
    }
    /* i_num_ref_frames */
    bs_read_ue( &s );
    /* b_gaps_in_frame_num_value_allowed */
    bs_skip( &s, 1 );

    /* Read size */
    p_sps->i_width  = 16 * ( bs_read_ue( &s ) + 1 );
    p_sps->i_height = 16 * ( bs_read_ue( &s ) + 1 );

    /* b_frame_mbs_only */
    p_sps->b_frame_mbs_only = bs_read( &s, 1 );
    p_sps->i_height *=  ( 2 - p_sps->b_frame_mbs_only );
    if( p_sps->b_frame_mbs_only == 0 )
    {
        bs_skip( &s, 1 );
    }
    /* b_direct8x8_inference */
    bs_skip( &s, 1 );

    /* crop */
    i_tmp = bs_read( &s, 1 );
    if( i_tmp )
    {
        /* left */
        bs_read_ue( &s );
        /* right */
        bs_read_ue( &s );
        /* top */
        bs_read_ue( &s );
        /* bottom */
        bs_read_ue( &s );
    }

    /* vui */
    i_tmp = bs_read( &s, 1 );
    if( i_tmp )
    {
        p_sps->vui.b_valid = true;
        /* read the aspect ratio part if any */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            static const struct { int w, h; } sar[17] =
            {
                { 0,   0 }, { 1,   1 }, { 12, 11 }, { 10, 11 },
                { 16, 11 }, { 40, 33 }, { 24, 11 }, { 20, 11 },
                { 32, 11 }, { 80, 33 }, { 18, 11 }, { 15, 11 },
                { 64, 33 }, { 160,99 }, {  4,  3 }, {  3,  2 },
                {  2,  1 },
            };
            int i_sar = bs_read( &s, 8 );
            int w, h;

            if( i_sar < 17 )
            {
                w = sar[i_sar].w;
                h = sar[i_sar].h;
            }
            else if( i_sar == 255 )
            {
                w = bs_read( &s, 16 );
                h = bs_read( &s, 16 );
            }
            else
            {
                w = 0;
                h = 0;
            }

            if( w != 0 && h != 0 )
            {
                p_sps->vui.i_sar_num = w;
                p_sps->vui.i_sar_den = h;
            }
            else
            {
                p_sps->vui.i_sar_num = 1;
                p_sps->vui.i_sar_den = 1;
            }
        }

        /* overscan */
        i_tmp = bs_read( &s, 1 );
        if ( i_tmp )
            bs_read( &s, 1 );

        /* video signal type */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            bs_read( &s, 4 );
            /* colour desc */
            bs_read( &s, 1 );
            if ( i_tmp )
                bs_read( &s, 24 );
        }

        /* chroma loc info */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            bs_read_ue( &s );
            bs_read_ue( &s );
        }

        /* timing info */
        p_sps->vui.b_timing_info_present_flag = bs_read( &s, 1 );
        if( p_sps->vui.b_timing_info_present_flag )
        {
            p_sps->vui.i_num_units_in_tick = bs_read( &s, 32 );
            p_sps->vui.i_time_scale = bs_read( &s, 32 );
            p_sps->vui.b_fixed_frame_rate = bs_read( &s, 1 );
        }

        /* Nal hrd & VC1 hrd parameters */
        p_sps->vui.b_cpb_dpb_delays_present_flag = false;
        for ( int i=0; i<2; i++ )
        {
            i_tmp = bs_read( &s, 1 );
            if( i_tmp )
            {
                p_sps->vui.b_cpb_dpb_delays_present_flag = true;
                uint32_t count = bs_read_ue( &s ) + 1;
                bs_read( &s, 4 );
                bs_read( &s, 4 );
                for( uint32_t i=0; i<count; i++ )
                {
                    bs_read_ue( &s );
                    bs_read_ue( &s );
                    bs_read( &s, 1 );
                }
                bs_read( &s, 5 );
                p_sps->vui.i_cpb_removal_delay_length_minus1 = bs_read( &s, 5 );
                p_sps->vui.i_dpb_output_delay_length_minus1 = bs_read( &s, 5 );
                bs_read( &s, 5 );
            }
        }

        if( p_sps->vui.b_cpb_dpb_delays_present_flag )
            bs_read( &s, 1 );

        /* pic struct info */
        p_sps->vui.b_pic_struct_present_flag = bs_read( &s, 1 );

        /* + unparsed remains */
    }

    free( pb_dec );

    return 0;
}
Example #4
0
//7.3.2.1 Sequence parameter set RBSP syntax
void read_seq_parameter_set_rbsp(sps_t *sps, bs_t* b)
{
	int i;

	// NOTE can't read directly into sps because seq_parameter_set_id not yet known and so sps is not selected

	int profile_idc = bs_read(b, 8);
	int constraint_set0_flag = bs_read(b, 1);
	int constraint_set1_flag = bs_read(b, 1);
	int constraint_set2_flag = bs_read(b, 1);
	int constraint_set3_flag = bs_read(b, 1);
	int constraint_set4_flag = bs_read(b, 1);
	int constraint_set5_flag = bs_read(b, 1);
	int reserved_zero_2bits = bs_read(b, 2);  /* all 0's */
	int level_idc = bs_read(b, 8);
	int seq_parameter_set_id = bs_read_ue(b);

	memset(sps, 0, sizeof(sps_t));

	sps->chroma_format_idc = 1;

	sps->profile_idc = profile_idc; // bs_read(b, 8);
	sps->constraint_set0_flag = constraint_set0_flag;//bs_read(b, 1);
	sps->constraint_set1_flag = constraint_set1_flag;//bs_read(b, 1);
	sps->constraint_set2_flag = constraint_set2_flag;//bs_read(b, 1);
	sps->constraint_set3_flag = constraint_set3_flag;//bs_read(b, 1);
	sps->constraint_set4_flag = constraint_set4_flag;//bs_read(b, 1);
	sps->constraint_set5_flag = constraint_set5_flag;//bs_read(b, 1);
	sps->reserved_zero_2bits = reserved_zero_2bits;//bs_read(b,2);
	sps->level_idc = level_idc; //bs_read(b, 8);
	sps->seq_parameter_set_id = seq_parameter_set_id; // bs_read_ue(b);
	if (sps->profile_idc == 100 || sps->profile_idc == 110 ||
		sps->profile_idc == 122 || sps->profile_idc == 144)
	{
		sps->chroma_format_idc = bs_read_ue(b);
		if (sps->chroma_format_idc == 3)
		{
			sps->residual_colour_transform_flag = bs_read(b, 1);
		}
		sps->bit_depth_luma_minus8 = bs_read_ue(b);
		sps->bit_depth_chroma_minus8 = bs_read_ue(b);
		sps->qpprime_y_zero_transform_bypass_flag = bs_read(b, 1);
		sps->seq_scaling_matrix_present_flag = bs_read(b, 1);
		if (sps->seq_scaling_matrix_present_flag)
		{
			for (i = 0; i < 8; i++)
			{
				sps->seq_scaling_list_present_flag[i] = bs_read(b, 1);
				if (sps->seq_scaling_list_present_flag[i])
				{
					if (i < 6)
					{
						read_scaling_list(b, sps->ScalingList4x4[i], 16,
							sps->UseDefaultScalingMatrix4x4Flag[i]);
					}
					else
					{
						read_scaling_list(b, sps->ScalingList8x8[i - 6], 64,
							sps->UseDefaultScalingMatrix8x8Flag[i - 6]);
					}
				}
			}
		}
	}
	sps->log2_max_frame_num_minus4 = bs_read_ue(b);
	sps->pic_order_cnt_type = bs_read_ue(b);
	if (sps->pic_order_cnt_type == 0)
	{
		sps->log2_max_pic_order_cnt_lsb_minus4 = bs_read_ue(b);
	}
	else if (sps->pic_order_cnt_type == 1)
	{
		sps->delta_pic_order_always_zero_flag = bs_read(b, 1);
		sps->offset_for_non_ref_pic = bs_read_se(b);
		sps->offset_for_top_to_bottom_field = bs_read_se(b);
		sps->num_ref_frames_in_pic_order_cnt_cycle = bs_read_ue(b);
		for (i = 0; i < sps->num_ref_frames_in_pic_order_cnt_cycle; i++)
		{
			sps->offset_for_ref_frame[i] = bs_read_se(b);
		}
	}
	sps->num_ref_frames = bs_read_ue(b);
	sps->gaps_in_frame_num_value_allowed_flag = bs_read(b, 1);
	sps->pic_width_in_mbs_minus1 = bs_read_ue(b);
	sps->pic_height_in_map_units_minus1 = bs_read_ue(b);
	sps->frame_mbs_only_flag = bs_read(b, 1);
	if (!sps->frame_mbs_only_flag)
	{
		sps->mb_adaptive_frame_field_flag = bs_read(b, 1);
	}
	sps->direct_8x8_inference_flag = bs_read(b, 1);
	sps->frame_cropping_flag = bs_read(b, 1);
	if (sps->frame_cropping_flag)
	{
		sps->frame_crop_left_offset = bs_read_ue(b);
		sps->frame_crop_right_offset = bs_read_ue(b);
		sps->frame_crop_top_offset = bs_read_ue(b);
		sps->frame_crop_bottom_offset = bs_read_ue(b);
	}
	sps->vui_parameters_present_flag = bs_read(b, 1);
	if (sps->vui_parameters_present_flag)
	{
		read_vui_parameters(sps, b);
	}
	//read_rbsp_trailing_bits(h, b);
}
Example #5
0
void Parser::parse(int *pb_nal_start)
{
	h264_t *h = &h264;
    bs_t s;
    *pb_nal_start = 0;

    if( nal.i_type == NAL_SPS || nal.i_type == NAL_PPS )
        *pb_nal_start = 1;

    bs_init( &s, nal.p_payload, nal.i_payload );
    if( nal.i_type == NAL_SPS )
    {
        int i_tmp;

        i_tmp = bs_read( &s, 8 );
        bs_skip( &s, 1+1+1 + 5 + 8 );
        /* sps id */
        bs_read_ue( &s );

        if( i_tmp >= 100 )
        {
            b_hiprofile = 1;
			bs_read_ue( &s ); // chroma_format_idc
            bs_read_ue( &s ); // bit_depth_luma_minus8
            bs_read_ue( &s ); // bit_depth_chroma_minus8
            bs_skip( &s, 1 ); // qpprime_y_zero_transform_bypass_flag
            if( bs_read( &s, 1 ) ) // seq_scaling_matrix_present_flag
            {
                int i, j;
                for( i = 0; i < 8; i++ )
                {
                    if( bs_read( &s, 1 ) ) // seq_scaling_list_present_flag[i]
                    {
                        uint8 i_tmp = 8;
                        for( j = 0; j < (i<6?16:64); j++ )
                        {
                            i_tmp += bs_read_se( &s );
                            if( i_tmp == 0 )
                                break;
                        }
                    }
                }
            }
        }

        /* Skip i_log2_max_frame_num */
        h->i_log2_max_frame_num = bs_read_ue( &s ) + 4;
        /* Read poc_type */
        h->i_poc_type = bs_read_ue( &s );
        if( h->i_poc_type == 0 )
        {
            h->i_log2_max_poc_lsb = bs_read_ue( &s ) + 4;
        }
        else if( h->i_poc_type == 1 )
        {
            int i_cycle;
            /* skip b_delta_pic_order_always_zero */
            bs_skip( &s, 1 );
            /* skip i_offset_for_non_ref_pic */
            bs_read_se( &s );
            /* skip i_offset_for_top_to_bottom_field */
            bs_read_se( &s );
            /* read i_num_ref_frames_in_poc_cycle */
            i_cycle = bs_read_ue( &s ); 
            if( i_cycle > 256 ) i_cycle = 256;
            while( i_cycle > 0 )
            {
                /* skip i_offset_for_ref_frame */
                bs_read_se(&s );
            }
        }
        /* i_num_ref_frames */
        bs_read_ue( &s );
        /* b_gaps_in_frame_num_value_allowed */
        bs_skip( &s, 1 );

        /* Read size */
        h->i_width  = 16 * ( bs_read_ue( &s ) + 1 );
        h->i_height = 32 * ( bs_read_ue( &s ) + 1 );

        /* b_frame_mbs_only */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp == 1 )
        {
			// fix: progressive, half height
			h->i_height /= 2;
		}
		else
		{
			// mb_adaptive_frame_field_flag
            bs_skip( &s, 1 );
        }
        /* b_direct8x8_inference */
        bs_skip( &s, 1 );

        /* crop ? */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
			// fix: no cropping

            /* left */
            //h->i_width -= 2 * bs_read_ue( &s );
            /* right */
            //h->i_width -= 2 * bs_read_ue( &s );
            /* top */
            //h->i_height -= 2 * bs_read_ue( &s );
            /* bottom */
            //h->i_height -= 2 * bs_read_ue( &s );
        }

        /* vui: ignored */
    }
    else if( nal.i_type >= NAL_SLICE && nal.i_type <= NAL_SLICE_IDR )
    {
        int i_tmp;

        /* i_first_mb */
        bs_read_ue( &s );
        /* picture type */
        switch( bs_read_ue( &s ) )
        {
            case 0: case 5: /* P */
            case 1: case 6: /* B */
            case 3: case 8: /* SP */
                h->b_key = 0;
                break;
            case 2: case 7: /* I */
            case 4: case 9: /* SI */
				// fix: key flags in high profile
                h->b_key = (nal.i_type == NAL_SLICE_IDR || (b_hiprofile && nal.i_type == NAL_SLICE));
                break;
        }
        /* pps id */
        bs_read_ue( &s );

        /* frame num */
        i_tmp = bs_read( &s, h->i_log2_max_frame_num );

        if( i_tmp != h->i_frame_num )
            *pb_nal_start = 1;

        h->i_frame_num = i_tmp;

        if( nal.i_type == NAL_SLICE_IDR )
        {
            i_tmp = bs_read_ue( &s );
            if( h->i_nal_type == NAL_SLICE_IDR && h->i_idr_pic_id != i_tmp )
                *pb_nal_start = 1;

            h->i_idr_pic_id = i_tmp;
        }

        if( h->i_poc_type == 0 )
        {
            i_tmp = bs_read( &s, h->i_log2_max_poc_lsb );
            if( i_tmp != h->i_poc )
                *pb_nal_start = 1;
            h->i_poc = i_tmp;
        }
    }
    h->i_nal_type = nal.i_type;
    h->i_ref_idc = nal.i_ref_idc;
}
Example #6
0
static bool h264_parse_sequence_parameter_set_rbsp( bs_t *p_bs,
                                                    h264_sequence_parameter_set_t *p_sps )
{
    int i_tmp;

    int i_profile_idc = bs_read( p_bs, 8 );
    p_sps->i_profile = i_profile_idc;
    p_sps->i_constraint_set_flags = bs_read( p_bs, 8 );
    p_sps->i_level = bs_read( p_bs, 8 );
    /* sps id */
    uint32_t i_sps_id = bs_read_ue( p_bs );
    if( i_sps_id > H264_SPS_ID_MAX )
        return false;
    p_sps->i_id = i_sps_id;

    if( i_profile_idc == PROFILE_H264_HIGH ||
        i_profile_idc == PROFILE_H264_HIGH_10 ||
        i_profile_idc == PROFILE_H264_HIGH_422 ||
        i_profile_idc == PROFILE_H264_HIGH_444 || /* Old one, no longer on spec */
        i_profile_idc == PROFILE_H264_HIGH_444_PREDICTIVE ||
        i_profile_idc == PROFILE_H264_CAVLC_INTRA ||
        i_profile_idc == PROFILE_H264_SVC_BASELINE ||
        i_profile_idc == PROFILE_H264_SVC_HIGH ||
        i_profile_idc == PROFILE_H264_MVC_MULTIVIEW_HIGH ||
        i_profile_idc == PROFILE_H264_MVC_STEREO_HIGH ||
        i_profile_idc == PROFILE_H264_MVC_MULTIVIEW_DEPTH_HIGH ||
        i_profile_idc == PROFILE_H264_MVC_ENHANCED_MULTIVIEW_DEPTH_HIGH ||
        i_profile_idc == PROFILE_H264_MFC_HIGH )
    {
        /* chroma_format_idc */
        p_sps->i_chroma_idc = bs_read_ue( p_bs );
        if( p_sps->i_chroma_idc == 3 )
            bs_skip( p_bs, 1 ); /* separate_colour_plane_flag */
        /* bit_depth_luma_minus8 */
        p_sps->i_bit_depth_luma = bs_read_ue( p_bs ) + 8;
        /* bit_depth_chroma_minus8 */
        p_sps->i_bit_depth_chroma = bs_read_ue( p_bs ) + 8;
        /* qpprime_y_zero_transform_bypass_flag */
        bs_skip( p_bs, 1 );
        /* seq_scaling_matrix_present_flag */
        i_tmp = bs_read( p_bs, 1 );
        if( i_tmp )
        {
            for( int i = 0; i < ((3 != p_sps->i_chroma_idc) ? 8 : 12); i++ )
            {
                /* seq_scaling_list_present_flag[i] */
                i_tmp = bs_read( p_bs, 1 );
                if( !i_tmp )
                    continue;
                const int i_size_of_scaling_list = (i < 6 ) ? 16 : 64;
                /* scaling_list (...) */
                int i_lastscale = 8;
                int i_nextscale = 8;
                for( int j = 0; j < i_size_of_scaling_list; j++ )
                {
                    if( i_nextscale != 0 )
                    {
                        /* delta_scale */
                        i_tmp = bs_read_se( p_bs );
                        i_nextscale = ( i_lastscale + i_tmp + 256 ) % 256;
                        /* useDefaultScalingMatrixFlag = ... */
                    }
                    /* scalinglist[j] */
                    i_lastscale = ( i_nextscale == 0 ) ? i_lastscale : i_nextscale;
                }
            }
        }
    }

    /* Skip i_log2_max_frame_num */
    p_sps->i_log2_max_frame_num = bs_read_ue( p_bs );
    if( p_sps->i_log2_max_frame_num > 12)
        p_sps->i_log2_max_frame_num = 12;
    /* Read poc_type */
    p_sps->i_pic_order_cnt_type = bs_read_ue( p_bs );
    if( p_sps->i_pic_order_cnt_type == 0 )
    {
        /* skip i_log2_max_poc_lsb */
        p_sps->i_log2_max_pic_order_cnt_lsb = bs_read_ue( p_bs );
        if( p_sps->i_log2_max_pic_order_cnt_lsb > 12 )
            p_sps->i_log2_max_pic_order_cnt_lsb = 12;
    }
    else if( p_sps->i_pic_order_cnt_type == 1 )
    {
        int i_cycle;
        /* skip b_delta_pic_order_always_zero */
        p_sps->i_delta_pic_order_always_zero_flag = bs_read( p_bs, 1 );
        /* skip i_offset_for_non_ref_pic */
        bs_read_se( p_bs );
        /* skip i_offset_for_top_to_bottom_field */
        bs_read_se( p_bs );
        /* read i_num_ref_frames_in_poc_cycle */
        i_cycle = bs_read_ue( p_bs );
        if( i_cycle > 256 ) i_cycle = 256;
        while( i_cycle > 0 )
        {
            /* skip i_offset_for_ref_frame */
            bs_read_se(p_bs );
            i_cycle--;
        }
    }
    /* i_num_ref_frames */
    bs_read_ue( p_bs );
    /* b_gaps_in_frame_num_value_allowed */
    bs_skip( p_bs, 1 );

    /* Read size */
    p_sps->pic_width_in_mbs_minus1 = bs_read_ue( p_bs );
    p_sps->pic_height_in_map_units_minus1 = bs_read_ue( p_bs );

    /* b_frame_mbs_only */
    p_sps->frame_mbs_only_flag = bs_read( p_bs, 1 );
    if( !p_sps->frame_mbs_only_flag )
        bs_skip( p_bs, 1 );

    /* b_direct8x8_inference */
    bs_skip( p_bs, 1 );

    /* crop */
    if( bs_read1( p_bs ) ) /* frame_cropping_flag */
    {
        p_sps->frame_crop.left_offset = bs_read_ue( p_bs );
        p_sps->frame_crop.right_offset = bs_read_ue( p_bs );
        p_sps->frame_crop.right_offset = bs_read_ue( p_bs );
        p_sps->frame_crop.bottom_offset = bs_read_ue( p_bs );
    }

    /* vui */
    i_tmp = bs_read( p_bs, 1 );
    if( i_tmp )
    {
        p_sps->vui.b_valid = true;
        /* read the aspect ratio part if any */
        i_tmp = bs_read( p_bs, 1 );
        if( i_tmp )
        {
            static const struct { int w, h; } sar[17] =
            {
                { 0,   0 }, { 1,   1 }, { 12, 11 }, { 10, 11 },
                { 16, 11 }, { 40, 33 }, { 24, 11 }, { 20, 11 },
                { 32, 11 }, { 80, 33 }, { 18, 11 }, { 15, 11 },
                { 64, 33 }, { 160,99 }, {  4,  3 }, {  3,  2 },
                {  2,  1 },
            };
            int i_sar = bs_read( p_bs, 8 );
            int w, h;

            if( i_sar < 17 )
            {
                w = sar[i_sar].w;
                h = sar[i_sar].h;
            }
            else if( i_sar == 255 )
            {
                w = bs_read( p_bs, 16 );
                h = bs_read( p_bs, 16 );
            }
            else
            {
                w = 0;
                h = 0;
            }

            if( w != 0 && h != 0 )
            {
                p_sps->vui.i_sar_num = w;
                p_sps->vui.i_sar_den = h;
            }
            else
            {
                p_sps->vui.i_sar_num = 1;
                p_sps->vui.i_sar_den = 1;
            }
        }

        /* overscan */
        i_tmp = bs_read( p_bs, 1 );
        if ( i_tmp )
            bs_read( p_bs, 1 );

        /* video signal type */
        i_tmp = bs_read( p_bs, 1 );
        if( i_tmp )
        {
            bs_read( p_bs, 3 );
            p_sps->vui.colour.b_full_range = bs_read( p_bs, 1 );
            /* colour desc */
            i_tmp = bs_read( p_bs, 1 );
            if ( i_tmp )
            {
                p_sps->vui.colour.i_colour_primaries = bs_read( p_bs, 8 );
                p_sps->vui.colour.i_transfer_characteristics = bs_read( p_bs, 8 );
                p_sps->vui.colour.i_matrix_coefficients = bs_read( p_bs, 8 );
            }
            else
            {
                p_sps->vui.colour.i_colour_primaries = HXXX_PRIMARIES_UNSPECIFIED;
                p_sps->vui.colour.i_transfer_characteristics = HXXX_TRANSFER_UNSPECIFIED;
                p_sps->vui.colour.i_matrix_coefficients = HXXX_MATRIX_UNSPECIFIED;
            }
        }

        /* chroma loc info */
        i_tmp = bs_read( p_bs, 1 );
        if( i_tmp )
        {
            bs_read_ue( p_bs );
            bs_read_ue( p_bs );
        }

        /* timing info */
        p_sps->vui.b_timing_info_present_flag = bs_read( p_bs, 1 );
        if( p_sps->vui.b_timing_info_present_flag )
        {
            p_sps->vui.i_num_units_in_tick = bs_read( p_bs, 32 );
            p_sps->vui.i_time_scale = bs_read( p_bs, 32 );
            p_sps->vui.b_fixed_frame_rate = bs_read( p_bs, 1 );
        }

        /* Nal hrd & VC1 hrd parameters */
        p_sps->vui.b_hrd_parameters_present_flag = false;
        for ( int i=0; i<2; i++ )
        {
            i_tmp = bs_read( p_bs, 1 );
            if( i_tmp )
            {
                p_sps->vui.b_hrd_parameters_present_flag = true;
                uint32_t count = bs_read_ue( p_bs ) + 1;
                if( count > 31 )
                    return false;
                bs_read( p_bs, 4 );
                bs_read( p_bs, 4 );
                for( uint32_t i=0; i<count; i++ )
                {
                    if( bs_remain( p_bs ) < 23 )
                        return false;
                    bs_read_ue( p_bs );
                    bs_read_ue( p_bs );
                    bs_read( p_bs, 1 );
                }
                bs_read( p_bs, 5 );
                p_sps->vui.i_cpb_removal_delay_length_minus1 = bs_read( p_bs, 5 );
                p_sps->vui.i_dpb_output_delay_length_minus1 = bs_read( p_bs, 5 );
                bs_read( p_bs, 5 );
            }
        }

        if( p_sps->vui.b_hrd_parameters_present_flag )
            bs_read( p_bs, 1 );

        /* pic struct info */
        p_sps->vui.b_pic_struct_present_flag = bs_read( p_bs, 1 );

        /* + unparsed remains */
    }

    return true;
}
Example #7
0
/*****************************************************************************
 * ParseNALBlock: parses annexB type NALs
 * All p_frag blocks are required to start with 0 0 0 1 4-byte startcode 
 *****************************************************************************/
static block_t *ParseNALBlock( decoder_t *p_dec, block_t *p_frag )
{
    decoder_sys_t *p_sys = p_dec->p_sys;
    block_t *p_pic = NULL;

    const int i_nal_ref_idc = (p_frag->p_buffer[4] >> 5)&0x03;
    const int i_nal_type = p_frag->p_buffer[4]&0x1f;

#define OUTPUT \
    do {                                                      \
        if( !p_sys->b_header && p_sys->slice.i_frame_type != BLOCK_FLAG_TYPE_I) \
            break;                                            \
                                                              \
        if( p_sys->slice.i_frame_type == BLOCK_FLAG_TYPE_I && p_sys->p_sps && p_sys->p_pps && !p_sys->b_header ) \
        { \
            block_t *p_sps = block_Duplicate( p_sys->p_sps ); \
            block_t *p_pps = block_Duplicate( p_sys->p_pps ); \
            p_sps->i_dts = p_sys->p_frame->i_dts;           \
            p_sps->i_pts = p_sys->p_frame->i_pts;           \
            block_ChainAppend( &p_sps, p_pps );               \
            block_ChainAppend( &p_sps, p_sys->p_frame );      \
            p_sys->b_header = VLC_TRUE;                       \
            p_pic = block_ChainGather( p_sps );               \
        } else { \
            p_pic = block_ChainGather( p_sys->p_frame ); \
        } \
        p_pic->i_length = 0;    /* FIXME */                   \
        p_pic->i_flags |= p_sys->slice.i_frame_type;          \
            \
        p_sys->slice.i_frame_type = 0;                        \
        p_sys->p_frame = NULL;                                \
        p_sys->b_slice = VLC_FALSE;                           \
    } while(0)

    if( p_sys->b_slice && ( !p_sys->b_sps || !p_sys->b_pps ) )
    {
        block_ChainRelease( p_sys->p_frame );
        msg_Warn( p_dec, "waiting for SPS/PPS" );

        /* Reset context */
        p_sys->slice.i_frame_type = 0;
        p_sys->p_frame = NULL;
        p_sys->b_slice = VLC_FALSE;
    }

    if( ( !p_sys->b_sps || !p_sys->b_pps ) &&
        i_nal_type >= NAL_SLICE && i_nal_type <= NAL_SLICE_IDR )
    {
        p_sys->b_slice = VLC_TRUE;
        /* Fragment will be discarded later on */
    }
    else if( i_nal_type >= NAL_SLICE && i_nal_type <= NAL_SLICE_IDR )
    {
        uint8_t *dec;
        int i_dec, i_first_mb, i_slice_type;
        slice_t slice;
        vlc_bool_t b_pic;
        bs_t s;

        /* do not convert the whole frame */
        nal_get_decoded( &dec, &i_dec, &p_frag->p_buffer[5],
                         __MIN( p_frag->i_buffer - 5, 60 ) );
        bs_init( &s, dec, i_dec );

        /* first_mb_in_slice */
        i_first_mb = bs_read_ue( &s );

        /* slice_type */
        switch( (i_slice_type = bs_read_ue( &s )) )
        {
        case 0: case 5:
            slice.i_frame_type = BLOCK_FLAG_TYPE_P;
            break;
        case 1: case 6:
            slice.i_frame_type = BLOCK_FLAG_TYPE_B;
            break;
        case 2: case 7:
            slice.i_frame_type = BLOCK_FLAG_TYPE_I;
            break;
        case 3: case 8: /* SP */
            slice.i_frame_type = BLOCK_FLAG_TYPE_P;
            break;
        case 4: case 9:
            slice.i_frame_type = BLOCK_FLAG_TYPE_I;
            break;
        default:
            slice.i_frame_type = 0;
            break;
        }

        /* */
        slice.i_nal_type = i_nal_type;
        slice.i_nal_ref_idc = i_nal_ref_idc;

        slice.i_pic_parameter_set_id = bs_read_ue( &s );
        slice.i_frame_num = bs_read( &s, p_sys->i_log2_max_frame_num + 4 );

        slice.i_field_pic_flag = 0;
        slice.i_bottom_field_flag = -1;
        if( !p_sys->b_frame_mbs_only )
        {
            /* field_pic_flag */
            slice.i_field_pic_flag = bs_read( &s, 1 );
            if( slice.i_field_pic_flag )
                slice.i_bottom_field_flag = bs_read( &s, 1 );
        }

        slice.i_idr_pic_id = p_sys->slice.i_idr_pic_id;
        if( slice.i_nal_type == NAL_SLICE_IDR )
            slice.i_idr_pic_id = bs_read_ue( &s );

        slice.i_pic_order_cnt_lsb = -1;
        slice.i_delta_pic_order_cnt_bottom = -1;
        slice.i_delta_pic_order_cnt0 = 0;
        slice.i_delta_pic_order_cnt1 = 0;
        if( p_sys->i_pic_order_cnt_type == 0 )
        {
            slice.i_pic_order_cnt_lsb = bs_read( &s, p_sys->i_log2_max_pic_order_cnt_lsb + 4 );
            if( p_sys->i_pic_order_present_flag && !slice.i_field_pic_flag )
                slice.i_delta_pic_order_cnt_bottom = bs_read_se( &s );
        }
        else if( p_sys->i_pic_order_cnt_type == 1 && !p_sys->i_delta_pic_order_always_zero_flag )
        {
            slice.i_delta_pic_order_cnt0 = bs_read_se( &s );
            if( p_sys->i_pic_order_present_flag && !slice.i_field_pic_flag )
                slice.i_delta_pic_order_cnt1 = bs_read_se( &s );
        }

        /* Detection of the first VCL NAL unit of a primary coded picture
         * (cf. 7.4.1.2.4) */
        b_pic = VLC_FALSE;
        if( slice.i_frame_num != p_sys->slice.i_frame_num ||
            slice.i_pic_parameter_set_id != p_sys->slice.i_pic_parameter_set_id ||
            slice.i_field_pic_flag != p_sys->slice.i_field_pic_flag ||
            slice.i_nal_ref_idc != p_sys->slice.i_nal_ref_idc )
            b_pic = VLC_TRUE;
        if( slice.i_bottom_field_flag != -1 && p_sys->slice.i_bottom_field_flag != -1 && slice.i_bottom_field_flag != p_sys->slice.i_bottom_field_flag )
            b_pic = VLC_TRUE;
        if( p_sys->i_pic_order_cnt_type == 0 &&
            ( slice.i_pic_order_cnt_lsb != p_sys->slice.i_pic_order_cnt_lsb ||
              slice.i_delta_pic_order_cnt_bottom != p_sys->slice.i_delta_pic_order_cnt_bottom ) )
            b_pic = VLC_TRUE;
        else if( p_sys->i_pic_order_cnt_type == 1 &&
                 ( slice.i_delta_pic_order_cnt0 != p_sys->slice.i_delta_pic_order_cnt0 ||
                   slice.i_delta_pic_order_cnt1 != p_sys->slice.i_delta_pic_order_cnt1 ) )
            b_pic = VLC_TRUE;
        if( ( slice.i_nal_type == NAL_SLICE_IDR || p_sys->slice.i_nal_type == NAL_SLICE_IDR ) &&
            ( slice.i_nal_type != p_sys->slice.i_nal_type || slice.i_idr_pic_id != p_sys->slice.i_idr_pic_id ) )
                b_pic = VLC_TRUE;

        /* */
        p_sys->slice = slice;

        if( b_pic && p_sys->b_slice )
            OUTPUT;

        p_sys->b_slice = VLC_TRUE;

        free( dec );
    }
    else if( i_nal_type == NAL_SPS )
    {
        uint8_t *dec;
        int     i_dec;
        bs_t s;
        int i_tmp;

        if( !p_sys->b_sps ) msg_Dbg( p_dec, "found NAL_SPS" );

        p_sys->b_sps = VLC_TRUE;

        nal_get_decoded( &dec, &i_dec, &p_frag->p_buffer[5],
                         p_frag->i_buffer - 5 );

        bs_init( &s, dec, i_dec );
        /* Skip profile(8), constraint_set012, reserver(5), level(8) */
        bs_skip( &s, 8 + 1+1+1 + 5 + 8 );
        /* sps id */
        bs_read_ue( &s );
        /* Skip i_log2_max_frame_num */
        p_sys->i_log2_max_frame_num = bs_read_ue( &s );
        if( p_sys->i_log2_max_frame_num > 12)
            p_sys->i_log2_max_frame_num = 12;
        /* Read poc_type */
        p_sys->i_pic_order_cnt_type = bs_read_ue( &s );
        if( p_sys->i_pic_order_cnt_type == 0 )
        {
            /* skip i_log2_max_poc_lsb */
            p_sys->i_log2_max_pic_order_cnt_lsb = bs_read_ue( &s );
            if( p_sys->i_log2_max_pic_order_cnt_lsb > 12 )
                p_sys->i_log2_max_pic_order_cnt_lsb = 12;
        }
        else if( p_sys->i_pic_order_cnt_type == 1 )
        {
            int i_cycle;
            /* skip b_delta_pic_order_always_zero */
            p_sys->i_delta_pic_order_always_zero_flag = bs_read( &s, 1 );
            /* skip i_offset_for_non_ref_pic */
            bs_read_se( &s );
            /* skip i_offset_for_top_to_bottom_field */
            bs_read_se( &s );
            /* read i_num_ref_frames_in_poc_cycle */
            i_cycle = bs_read_ue( &s );
            if( i_cycle > 256 ) i_cycle = 256;
            while( i_cycle > 0 )
            {
                /* skip i_offset_for_ref_frame */
                bs_read_se(&s );
            }
        }
        /* i_num_ref_frames */
        bs_read_ue( &s );
        /* b_gaps_in_frame_num_value_allowed */
        bs_skip( &s, 1 );

        /* Read size */
        p_dec->fmt_out.video.i_width  = 16 * ( bs_read_ue( &s ) + 1 );
        p_dec->fmt_out.video.i_height = 16 * ( bs_read_ue( &s ) + 1 );

        /* b_frame_mbs_only */
        p_sys->b_frame_mbs_only = bs_read( &s, 1 );
        if( p_sys->b_frame_mbs_only == 0 )
        {
            bs_skip( &s, 1 );
        }
        /* b_direct8x8_inference */
        bs_skip( &s, 1 );

        /* crop */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            /* left */
            bs_read_ue( &s );
            /* right */
            bs_read_ue( &s );
            /* top */
            bs_read_ue( &s );
            /* bottom */
            bs_read_ue( &s );
        }

        /* vui */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            /* read the aspect ratio part if any FIXME check it */
            i_tmp = bs_read( &s, 1 );
            if( i_tmp )
            {
                static const struct { int w, h; } sar[14] =
                {
                    { 0,   0 }, { 1,   1 }, { 12, 11 }, { 10, 11 },
                    { 16, 11 }, { 40, 33 }, { 24, 11 }, { 20, 11 },
                    { 32, 11 }, { 80, 33 }, { 18, 11 }, { 15, 11 },
                    { 64, 33 }, { 160,99 },
                };
                int i_sar = bs_read( &s, 8 );
                int w, h;

                if( i_sar < 14 )
                {
                    w = sar[i_sar].w;
                    h = sar[i_sar].h;
                }
                else
                {
                    w = bs_read( &s, 16 );
                    h = bs_read( &s, 16 );
                }
                if( h != 0 )
                    p_dec->fmt_out.video.i_aspect = VOUT_ASPECT_FACTOR * w /
                        h * p_dec->fmt_out.video.i_width /
                        p_dec->fmt_out.video.i_height;
                else
                    p_dec->fmt_out.video.i_aspect = VOUT_ASPECT_FACTOR;
            }
        }

        free( dec );

        if( p_sys->b_slice ) OUTPUT;

        /* We have a new SPS */
        if( p_sys->p_sps ) block_Release( p_sys->p_sps );
        p_sys->p_sps = p_frag;

        /* Do not append the SPS because we will insert it on keyframes */
        return p_pic;
    }
    else if( i_nal_type == NAL_PPS )
    {
        bs_t s;

        bs_init( &s, &p_frag->p_buffer[5], p_frag->i_buffer - 5 );
        bs_read_ue( &s ); // pps id
        bs_read_ue( &s ); // sps id
        bs_skip( &s, 1 ); // entropy coding mode flag
        p_sys->i_pic_order_present_flag = bs_read( &s, 1 );

        if( !p_sys->b_pps ) msg_Dbg( p_dec, "found NAL_PPS" );
        p_sys->b_pps = VLC_TRUE;

        /* TODO */

        if( p_sys->b_slice ) OUTPUT;

        /* We have a new PPS */
        if( p_sys->p_pps ) block_Release( p_sys->p_pps );
        p_sys->p_pps = p_frag;

        /* Do not append the PPS because we will insert it on keyframes */
        return p_pic;
    }
    else if( i_nal_type == NAL_AU_DELIMITER ||
             i_nal_type == NAL_SEI ||
             ( i_nal_type >= 13 && i_nal_type <= 18 ) )
    {
        if( p_sys->b_slice ) OUTPUT;
    }

#undef OUTPUT

    /* Append the block */
    block_ChainAppend( &p_sys->p_frame, p_frag );

    return p_pic;
}
Example #8
0
File: h264.c Project: 5UN5H1N3/vlc
static void PutSPS( decoder_t *p_dec, block_t *p_frag )
{
    decoder_sys_t *p_sys = p_dec->p_sys;

    uint8_t *pb_dec = NULL;
    int     i_dec = 0;
    bs_t s;
    int i_tmp;
    int i_sps_id;

    CreateDecodedNAL( &pb_dec, &i_dec, &p_frag->p_buffer[5],
                     p_frag->i_buffer - 5 );

    bs_init( &s, pb_dec, i_dec );
    int i_profile_idc = bs_read( &s, 8 );
    p_dec->fmt_out.i_profile = i_profile_idc;
    /* Skip constraint_set0123, reserved(4) */
    bs_skip( &s, 1+1+1+1 + 4 );
    p_dec->fmt_out.i_level = bs_read( &s, 8 );
    /* sps id */
    i_sps_id = bs_read_ue( &s );
    if( i_sps_id >= SPS_MAX || i_sps_id < 0 )
    {
        msg_Warn( p_dec, "invalid SPS (sps_id=%d)", i_sps_id );
        free( pb_dec );
        block_Release( p_frag );
        return;
    }

    if( i_profile_idc == 100 || i_profile_idc == 110 ||
        i_profile_idc == 122 || i_profile_idc == 244 ||
        i_profile_idc ==  44 || i_profile_idc ==  83 ||
        i_profile_idc ==  86 )
    {
        /* chroma_format_idc */
        const int i_chroma_format_idc = bs_read_ue( &s );
        if( i_chroma_format_idc == 3 )
            bs_skip( &s, 1 ); /* separate_colour_plane_flag */
        /* bit_depth_luma_minus8 */
        bs_read_ue( &s );
        /* bit_depth_chroma_minus8 */
        bs_read_ue( &s );
        /* qpprime_y_zero_transform_bypass_flag */
        bs_skip( &s, 1 );
        /* seq_scaling_matrix_present_flag */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            for( int i = 0; i < ((3 != i_chroma_format_idc) ? 8 : 12); i++ )
            {
                /* seq_scaling_list_present_flag[i] */
                i_tmp = bs_read( &s, 1 );
                if( !i_tmp )
                    continue;
                const int i_size_of_scaling_list = (i < 6 ) ? 16 : 64;
                /* scaling_list (...) */
                int i_lastscale = 8;
                int i_nextscale = 8;
                for( int j = 0; j < i_size_of_scaling_list; j++ )
                {
                    if( i_nextscale != 0 )
                    {
                        /* delta_scale */
                        i_tmp = bs_read_se( &s );
                        i_nextscale = ( i_lastscale + i_tmp + 256 ) % 256;
                        /* useDefaultScalingMatrixFlag = ... */
                    }
                    /* scalinglist[j] */
                    i_lastscale = ( i_nextscale == 0 ) ? i_lastscale : i_nextscale;
                }
            }
        }
    }

    /* Skip i_log2_max_frame_num */
    p_sys->i_log2_max_frame_num = bs_read_ue( &s );
    if( p_sys->i_log2_max_frame_num > 12)
        p_sys->i_log2_max_frame_num = 12;
    /* Read poc_type */
    p_sys->i_pic_order_cnt_type = bs_read_ue( &s );
    if( p_sys->i_pic_order_cnt_type == 0 )
    {
        /* skip i_log2_max_poc_lsb */
        p_sys->i_log2_max_pic_order_cnt_lsb = bs_read_ue( &s );
        if( p_sys->i_log2_max_pic_order_cnt_lsb > 12 )
            p_sys->i_log2_max_pic_order_cnt_lsb = 12;
    }
    else if( p_sys->i_pic_order_cnt_type == 1 )
    {
        int i_cycle;
        /* skip b_delta_pic_order_always_zero */
        p_sys->i_delta_pic_order_always_zero_flag = bs_read( &s, 1 );
        /* skip i_offset_for_non_ref_pic */
        bs_read_se( &s );
        /* skip i_offset_for_top_to_bottom_field */
        bs_read_se( &s );
        /* read i_num_ref_frames_in_poc_cycle */
        i_cycle = bs_read_ue( &s );
        if( i_cycle > 256 ) i_cycle = 256;
        while( i_cycle > 0 )
        {
            /* skip i_offset_for_ref_frame */
            bs_read_se(&s );
            i_cycle--;
        }
    }
    /* i_num_ref_frames */
    bs_read_ue( &s );
    /* b_gaps_in_frame_num_value_allowed */
    bs_skip( &s, 1 );

    /* Read size */
    p_dec->fmt_out.video.i_width  = 16 * ( bs_read_ue( &s ) + 1 );
    p_dec->fmt_out.video.i_height = 16 * ( bs_read_ue( &s ) + 1 );

    /* b_frame_mbs_only */
    p_sys->b_frame_mbs_only = bs_read( &s, 1 );
    p_dec->fmt_out.video.i_height *=  ( 2 - p_sys->b_frame_mbs_only );
    if( p_sys->b_frame_mbs_only == 0 )
    {
        bs_skip( &s, 1 );
    }
    /* b_direct8x8_inference */
    bs_skip( &s, 1 );

    /* crop */
    i_tmp = bs_read( &s, 1 );
    if( i_tmp )
    {
        /* left */
        bs_read_ue( &s );
        /* right */
        bs_read_ue( &s );
        /* top */
        bs_read_ue( &s );
        /* bottom */
        bs_read_ue( &s );
    }

    /* vui */
    i_tmp = bs_read( &s, 1 );
    if( i_tmp )
    {
        /* read the aspect ratio part if any */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            static const struct { int w, h; } sar[17] =
            {
                { 0,   0 }, { 1,   1 }, { 12, 11 }, { 10, 11 },
                { 16, 11 }, { 40, 33 }, { 24, 11 }, { 20, 11 },
                { 32, 11 }, { 80, 33 }, { 18, 11 }, { 15, 11 },
                { 64, 33 }, { 160,99 }, {  4,  3 }, {  3,  2 },
                {  2,  1 },
            };
            int i_sar = bs_read( &s, 8 );
            int w, h;

            if( i_sar < 17 )
            {
                w = sar[i_sar].w;
                h = sar[i_sar].h;
            }
            else if( i_sar == 255 )
            {
                w = bs_read( &s, 16 );
                h = bs_read( &s, 16 );
            }
            else
            {
                w = 0;
                h = 0;
            }

            if( w != 0 && h != 0 )
            {
                p_dec->fmt_out.video.i_sar_num = w;
                p_dec->fmt_out.video.i_sar_den = h;
            }
            else
            {
                p_dec->fmt_out.video.i_sar_num = 1;
                p_dec->fmt_out.video.i_sar_den = 1;
            }
        }
    }

    free( pb_dec );

    /* We have a new SPS */
    if( !p_sys->b_sps )
        msg_Dbg( p_dec, "found NAL_SPS (sps_id=%d)", i_sps_id );
    p_sys->b_sps = true;

    if( p_sys->pp_sps[i_sps_id] )
        block_Release( p_sys->pp_sps[i_sps_id] );
    p_sys->pp_sps[i_sps_id] = p_frag;
}
Example #9
0
File: h264.c Project: 5UN5H1N3/vlc
static void ParseSlice( decoder_t *p_dec, bool *pb_new_picture, slice_t *p_slice,
                        int i_nal_ref_idc, int i_nal_type, const block_t *p_frag )
{
    decoder_sys_t *p_sys = p_dec->p_sys;
    uint8_t *pb_dec;
    int i_dec;
    int i_slice_type;
    slice_t slice;
    bs_t s;

    /* do not convert the whole frame */
    CreateDecodedNAL( &pb_dec, &i_dec, &p_frag->p_buffer[5],
                     __MIN( p_frag->i_buffer - 5, 60 ) );
    bs_init( &s, pb_dec, i_dec );

    /* first_mb_in_slice */
    /* int i_first_mb = */ bs_read_ue( &s );

    /* slice_type */
    switch( (i_slice_type = bs_read_ue( &s )) )
    {
    case 0: case 5:
        slice.i_frame_type = BLOCK_FLAG_TYPE_P;
        break;
    case 1: case 6:
        slice.i_frame_type = BLOCK_FLAG_TYPE_B;
        break;
    case 2: case 7:
        slice.i_frame_type = BLOCK_FLAG_TYPE_I;
        break;
    case 3: case 8: /* SP */
        slice.i_frame_type = BLOCK_FLAG_TYPE_P;
        break;
    case 4: case 9:
        slice.i_frame_type = BLOCK_FLAG_TYPE_I;
        break;
    default:
        slice.i_frame_type = 0;
        break;
    }

    /* */
    slice.i_nal_type = i_nal_type;
    slice.i_nal_ref_idc = i_nal_ref_idc;

    slice.i_pic_parameter_set_id = bs_read_ue( &s );
    slice.i_frame_num = bs_read( &s, p_sys->i_log2_max_frame_num + 4 );

    slice.i_field_pic_flag = 0;
    slice.i_bottom_field_flag = -1;
    if( !p_sys->b_frame_mbs_only )
    {
        /* field_pic_flag */
        slice.i_field_pic_flag = bs_read( &s, 1 );
        if( slice.i_field_pic_flag )
            slice.i_bottom_field_flag = bs_read( &s, 1 );
    }

    slice.i_idr_pic_id = p_sys->slice.i_idr_pic_id;
    if( slice.i_nal_type == NAL_SLICE_IDR )
        slice.i_idr_pic_id = bs_read_ue( &s );

    slice.i_pic_order_cnt_lsb = -1;
    slice.i_delta_pic_order_cnt_bottom = -1;
    slice.i_delta_pic_order_cnt0 = 0;
    slice.i_delta_pic_order_cnt1 = 0;
    if( p_sys->i_pic_order_cnt_type == 0 )
    {
        slice.i_pic_order_cnt_lsb = bs_read( &s, p_sys->i_log2_max_pic_order_cnt_lsb + 4 );
        if( p_sys->i_pic_order_present_flag && !slice.i_field_pic_flag )
            slice.i_delta_pic_order_cnt_bottom = bs_read_se( &s );
    }
    else if( (p_sys->i_pic_order_cnt_type == 1) &&
             (!p_sys->i_delta_pic_order_always_zero_flag) )
    {
        slice.i_delta_pic_order_cnt0 = bs_read_se( &s );
        if( p_sys->i_pic_order_present_flag && !slice.i_field_pic_flag )
            slice.i_delta_pic_order_cnt1 = bs_read_se( &s );
    }
    free( pb_dec );

    /* Detection of the first VCL NAL unit of a primary coded picture
     * (cf. 7.4.1.2.4) */
    bool b_pic = false;
    if( slice.i_frame_num != p_sys->slice.i_frame_num ||
        slice.i_pic_parameter_set_id != p_sys->slice.i_pic_parameter_set_id ||
        slice.i_field_pic_flag != p_sys->slice.i_field_pic_flag ||
        slice.i_nal_ref_idc != p_sys->slice.i_nal_ref_idc )
        b_pic = true;
    if( (slice.i_bottom_field_flag != -1) &&
        (p_sys->slice.i_bottom_field_flag != -1) &&
        (slice.i_bottom_field_flag != p_sys->slice.i_bottom_field_flag) )
        b_pic = true;
    if( p_sys->i_pic_order_cnt_type == 0 &&
        ( slice.i_pic_order_cnt_lsb != p_sys->slice.i_pic_order_cnt_lsb ||
          slice.i_delta_pic_order_cnt_bottom != p_sys->slice.i_delta_pic_order_cnt_bottom ) )
        b_pic = true;
    else if( p_sys->i_pic_order_cnt_type == 1 &&
             ( slice.i_delta_pic_order_cnt0 != p_sys->slice.i_delta_pic_order_cnt0 ||
               slice.i_delta_pic_order_cnt1 != p_sys->slice.i_delta_pic_order_cnt1 ) )
        b_pic = true;
    if( ( slice.i_nal_type == NAL_SLICE_IDR || p_sys->slice.i_nal_type == NAL_SLICE_IDR ) &&
        ( slice.i_nal_type != p_sys->slice.i_nal_type || slice.i_idr_pic_id != p_sys->slice.i_idr_pic_id ) )
            b_pic = true;

    /* */
    *pb_new_picture = b_pic;
    *p_slice = slice;
}
Example #10
0
File: h264.c Project: sdelmas/SDesk
static block_t *ParseNALBlock( decoder_t *p_dec, block_t *p_frag )
{
    decoder_sys_t *p_sys = p_dec->p_sys;
    block_t *p_pic = NULL;

    const int i_nal_ref_idc = (p_frag->p_buffer[3] >> 5)&0x03;
    const int i_nal_type = p_frag->p_buffer[3]&0x1f;

    if( p_sys->b_slice && !p_sys->b_sps )
    {
        block_ChainRelease( p_sys->p_frame );
        msg_Warn( p_dec, "waiting for SPS" );

        /* Reset context */
        p_sys->p_frame = NULL;
        p_sys->b_slice = VLC_FALSE;
    }

    if( !p_sys->b_sps &&
            i_nal_type >= NAL_SLICE && i_nal_type <= NAL_SLICE_IDR )
    {
        p_sys->b_slice = VLC_TRUE;
        /* Fragment will be discarded later on */
    }
    else if( i_nal_type >= NAL_SLICE && i_nal_type <= NAL_SLICE_IDR )
    {
        uint8_t *dec;
        int i_dec, i_first_mb, i_slice_type, i_frame_num, i_pic_flags = 0;
        vlc_bool_t b_pic = VLC_FALSE;
        bs_t s;

        /* do not convert the whole frame */
        nal_get_decoded( &dec, &i_dec, &p_frag->p_buffer[4],
                         __MIN( p_frag->i_buffer - 4, 60 ) );
        bs_init( &s, dec, i_dec );

        /* first_mb_in_slice */
        i_first_mb = bs_read_ue( &s );

        /* slice_type */
        switch( (i_slice_type = bs_read_ue( &s )) )
        {
        case 0:
        case 5:
            i_pic_flags = BLOCK_FLAG_TYPE_P;
            break;
        case 1:
        case 6:
            i_pic_flags = BLOCK_FLAG_TYPE_B;
            break;
        case 2:
        case 7:
            i_pic_flags = BLOCK_FLAG_TYPE_I;
            break;
        case 3:
        case 8: /* SP */
            i_pic_flags = BLOCK_FLAG_TYPE_P;
            break;
        case 4:
        case 9:
            i_pic_flags = BLOCK_FLAG_TYPE_I;
            break;
        }

        /* pic_parameter_set_id */
        bs_read_ue( &s );
        /* frame_num */
        i_frame_num = bs_read( &s, p_sys->i_log2_max_frame_num + 4 );

        /* Detection of the first VCL NAL unit of a primary coded picture
         * (cf. 7.4.1.2.4) */
        if( i_frame_num != p_sys->i_frame_num ||
                ( (i_nal_ref_idc != p_sys->i_nal_ref_idc) &&
                  (!i_nal_ref_idc || !p_sys->i_nal_ref_idc) ) )
        {
            b_pic = VLC_TRUE;
        }
        p_sys->i_frame_num = i_frame_num;
        p_sys->i_nal_ref_idc = i_nal_ref_idc;

        if( !p_sys->b_frame_mbs_only )
        {
            /* field_pic_flag */
            if( bs_read( &s, 1 ) )
            {
                /* bottom_field_flag */
                bs_read( &s, 1 );
            }
        }

        if( i_nal_type == NAL_SLICE_IDR )
        {
            /* id_pic_id */
            int i_idr_pic_id = bs_read_ue( &s );
            if( p_sys->i_nal_type != i_nal_type ) b_pic = VLC_TRUE;
            if( p_sys->i_idr_pic_id != i_idr_pic_id ) b_pic = VLC_TRUE;
            p_sys->i_idr_pic_id = i_idr_pic_id;
        }
        p_sys->i_nal_type = i_nal_type;

        if( b_pic && p_sys->b_slice )
        {
            p_pic = block_ChainGather( p_sys->p_frame );
            p_pic->i_dts = p_sys->i_dts;
            p_pic->i_pts = p_sys->i_pts;
            p_pic->i_length = 0;    /* FIXME */
            p_pic->i_flags = p_sys->i_flags;

            /* Reset context */
            p_sys->p_frame = NULL;
            p_sys->b_slice = VLC_FALSE;
        }

        p_sys->b_slice = VLC_TRUE;
        p_sys->i_flags = i_pic_flags;
        p_sys->i_dts   = p_frag->i_dts;
        p_sys->i_pts   = p_frag->i_pts;

        free( dec );
    }
    else if( i_nal_type == NAL_SPS )
    {
        uint8_t *dec;
        int     i_dec;
        bs_t s;
        int i_tmp;

        msg_Dbg( p_dec, "found NAL_SPS" );

        p_sys->b_sps = VLC_TRUE;

        nal_get_decoded( &dec, &i_dec, &p_frag->p_buffer[4],
                         p_frag->i_buffer - 4 );

        bs_init( &s, dec, i_dec );
        /* Skip profile(8), constraint_set012, reserver(5), level(8) */
        bs_skip( &s, 8 + 1+1+1 + 5 + 8 );
        /* sps id */
        bs_read_ue( &s );
        /* Skip i_log2_max_frame_num */
        p_sys->i_log2_max_frame_num = bs_read_ue( &s );
        /* Read poc_type */
        i_tmp = bs_read_ue( &s );
        if( i_tmp == 0 )
        {
            /* skip i_log2_max_poc_lsb */
            bs_read_ue( &s );
        }
        else if( i_tmp == 1 )
        {
            int i_cycle;
            /* skip b_delta_pic_order_always_zero */
            bs_skip( &s, 1 );
            /* skip i_offset_for_non_ref_pic */
            bs_read_se( &s );
            /* skip i_offset_for_top_to_bottom_field */
            bs_read_se( &s );
            /* read i_num_ref_frames_in_poc_cycle */
            i_cycle = bs_read_ue( &s );
            if( i_cycle > 256 ) i_cycle = 256;
            while( i_cycle > 0 )
            {
                /* skip i_offset_for_ref_frame */
                bs_read_se(&s );
            }
        }
        /* i_num_ref_frames */
        bs_read_ue( &s );
        /* b_gaps_in_frame_num_value_allowed */
        bs_skip( &s, 1 );

        /* Read size */
        p_dec->fmt_out.video.i_width  = 16 * ( bs_read_ue( &s ) + 1 );
        p_dec->fmt_out.video.i_height = 16 * ( bs_read_ue( &s ) + 1 );

        /* b_frame_mbs_only */
        p_sys->b_frame_mbs_only = bs_read( &s, 1 );
        if( p_sys->b_frame_mbs_only == 0 )
        {
            bs_skip( &s, 1 );
        }
        /* b_direct8x8_inference */
        bs_skip( &s, 1 );

        /* crop */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            /* left */
            bs_read_ue( &s );
            /* right */
            bs_read_ue( &s );
            /* top */
            bs_read_ue( &s );
            /* bottom */
            bs_read_ue( &s );
        }

        /* vui */
        i_tmp = bs_read( &s, 1 );
        if( i_tmp )
        {
            /* read the aspect ratio part if any FIXME check it */
            i_tmp = bs_read( &s, 1 );
            if( i_tmp )
            {
                static const struct {
                    int w, h;
                } sar[14] =
                {
                    { 0,   0 }, { 1,   1 }, { 12, 11 }, { 10, 11 },
                    { 16, 11 }, { 40, 33 }, { 24, 11 }, { 20, 11 },
                    { 32, 11 }, { 80, 33 }, { 18, 11 }, { 15, 11 },
                    { 64, 33 }, { 160,99 },
                };
                int i_sar = bs_read( &s, 8 );
                int w, h;

                if( i_sar < 14 )
                {
                    w = sar[i_sar].w;
                    h = sar[i_sar].h;
                }
                else
                {
                    w = bs_read( &s, 16 );
                    h = bs_read( &s, 16 );
                }
                p_dec->fmt_out.video.i_aspect =
                    VOUT_ASPECT_FACTOR * w / h * p_dec->fmt_out.video.i_width /
                    p_dec->fmt_out.video.i_height;
            }
        }

        free( dec );
    }
    else if( i_nal_type == NAL_PPS )
    {
        bs_t s;
        bs_init( &s, &p_frag->p_buffer[4], p_frag->i_buffer - 4 );

        /* TODO */
        msg_Dbg( p_dec, "found NAL_PPS" );
    }

    /* Append the block */
    block_ChainAppend( &p_sys->p_frame, p_frag );

    return p_pic;
}
bool 
h264MediaStream::ParseSqs(const buf_share_ptr SqsNode)
{
	assert(SqsNode);

	if (StreamSps == NULL)
		StreamSps = new h264_sps_t;
	uint8_t *pb_dec = NULL;
	int     i_dec = 0;
	bs_t s;
	int i_sps_id;
	i_dec = SqsNode->GetSizeValue(); 
	int nal_hrd_parameters_present_flag, vcl_hrd_parameters_present_flag;
	pb_dec = const_cast<uint8_t *>(SqsNode->GetBuffer());

	//转化00 00 03为00 00


	uint8_t *p_nal = new uint8_t[i_dec];
	int pcount = 0;
	for (int tmp = 1; tmp < i_dec ; tmp++)
	{
		if (tmp < i_dec - 3 && *(pb_dec + tmp) == 0x00 && 
			*(pb_dec + tmp + 1) == 0x00 && *(pb_dec + tmp + 2) == 0x03)
		{
			p_nal[pcount++] = 0x00;
			p_nal[pcount++] = 0x00;
			//printf("count = %d %2X\n",tmp, *(p_nal + tmp));
			tmp += 2;
			continue;
		}
		p_nal[pcount++] = *(pb_dec + tmp);
	}
	pb_dec = p_nal;

	//以下内容根据H264协议解读,属于直接复制粘贴代码 同parseslice

	bs_init( &s, pb_dec, i_dec );
	// profile(8)
	StreamSps->profile_idc = bs_read( &s, 8);

	/* constraint_set012, reserver(5), level(8) */
	bs_skip( &s, 1+1+1 + 5 + 8 );
	/* sps id */
	i_sps_id = bs_read_ue( &s );
	if( i_sps_id >= 32/*SPS_MAX*/ )
	{
		printf("invalid SPS (sps_id=%d)", i_sps_id );
		delete pb_dec;
		return false;
	}

	StreamSps->scaling_matrix_present = 0;
	if(StreamSps->profile_idc >= 100)		//high profile
	{ 
		if(bs_read_ue(&s) == 3)			//chroma_format_idc
			bs_read(&s, 1);				//residual_color_transform_flag
		bs_read_ue(&s);					//bit_depth_luma_minus8
		bs_read_ue(&s);					//bit_depth_chroma_minus8
		StreamSps->transform_bypass = bs_read(&s, 1);
		bs_skip(&s, 1); //decode_scaling_matrices(h, sps, NULL, 1, sps->scaling_matrix4, sps->scaling_matrix8);
	}

	/* Skip i_log2_max_frame_num */
	StreamSps->log2_max_frame_num = bs_read_ue( &s );
	if( StreamSps->log2_max_frame_num > 12)
		StreamSps->log2_max_frame_num = 12;
	/* Read poc_type */
	StreamSps->poc_type/*->i_pic_order_cnt_type*/ = bs_read_ue( &s );
	if( StreamSps->poc_type == 0 )
	{
		/* skip i_log2_max_poc_lsb */
		StreamSps->log2_max_poc_lsb/*->i_log2_max_pic_order_cnt_lsb*/ = bs_read_ue( &s );
		if( StreamSps->log2_max_poc_lsb > 12 )
			StreamSps->log2_max_poc_lsb = 12;
	}
	else if( StreamSps->poc_type/*p_sys->i_pic_order_cnt_type*/ == 1 )
	{
		int i_cycle;
		/* skip b_delta_pic_order_always_zero */
		StreamSps->delta_pic_order_always_zero_flag/*->i_delta_pic_order_always_zero_flag*/ = bs_read( &s, 1 );
		/* skip i_offset_for_non_ref_pic */
		bs_read_se( &s );
		/* skip i_offset_for_top_to_bottom_field */
		bs_read_se( &s );
		/* read i_num_ref_frames_in_poc_cycle */
		i_cycle = bs_read_ue( &s );
		if( i_cycle > 256 ) i_cycle = 256;
		while( i_cycle > 0 )
		{
			/* skip i_offset_for_ref_frame */
			bs_read_se(&s );
			i_cycle--;
		}
	}
	/* i_num_ref_frames */
	bs_read_ue( &s );
	/* b_gaps_in_frame_num_value_allowed */
	bs_skip( &s, 1 );

	/* Read size */
	StreamSps->mb_width/*->fmt_out.video.i_width*/  = 16 * ( bs_read_ue( &s ) + 1 );
	StreamSps->mb_height/*fmt_out.video.i_height*/ = 16 * ( bs_read_ue( &s ) + 1 );

	/* b_frame_mbs_only */
	StreamSps->frame_mbs_only_flag/*->b_frame_mbs_only*/ = bs_read( &s, 1 );
	if( StreamSps->frame_mbs_only_flag == 0 )
	{
		bs_skip( &s, 1 );
	}
	/* b_direct8x8_inference */
	bs_skip( &s, 1 );

	/* crop */
	StreamSps->crop = bs_read( &s, 1 );
	if( StreamSps->crop )
	{
		/* left */
		bs_read_ue( &s );
		/* right */
		bs_read_ue( &s );
		/* top */
		bs_read_ue( &s );
		/* bottom */
		bs_read_ue( &s );
	}

	/* vui */
	StreamSps->vui_parameters_present_flag = bs_read( &s, 1 );
	if( StreamSps->vui_parameters_present_flag )
	{
		int aspect_ratio_info_present_flag = bs_read( &s, 1 );
		if( aspect_ratio_info_present_flag )
		{
			static const struct { int num, den; } sar[17] =
			{
				{ 0,   0 }, { 1,   1 }, { 12, 11 }, { 10, 11 },
				{ 16, 11 }, { 40, 33 }, { 24, 11 }, { 20, 11 },
				{ 32, 11 }, { 80, 33 }, { 18, 11 }, { 15, 11 },
				{ 64, 33 }, { 160,99 }, {  4,  3 }, {  3,  2 },
				{  2,  1 },
			};

			int i_sar = bs_read( &s, 8 );

			if( i_sar < 17 )
			{
				StreamSps->sar.num = sar[i_sar].num;
				StreamSps->sar.den = sar[i_sar].den;
			}
			else if( i_sar == 255 )
			{
				StreamSps->sar.num = bs_read( &s, 16 );
				StreamSps->sar.den = bs_read( &s, 16 );
			}
			else
			{
				StreamSps->sar.num = 0;
				StreamSps->sar.den = 0;
			}

			//if( den != 0 )
			//	p_dec->fmt_out.video.i_aspect = (int64_t)VOUT_ASPECT_FACTOR *
			//	( num * p_dec->fmt_out.video.i_width ) /
			//	( den * p_dec->fmt_out.video.i_height);
			//else
			//	p_dec->fmt_out.video.i_aspect = VOUT_ASPECT_FACTOR;
		}
		else
		{
			StreamSps->sar.num = 0;
			StreamSps->sar.den = 0;
		}

		if(bs_read(&s, 1))		/* overscan_info_present_flag */
		{
			bs_read(&s, 1);     /* overscan_appropriate_flag */
		}

		if(bs_read(&s, 1))		/* video_signal_type_present_flag */
		{      
			bs_read(&s, 3);		/* video_format */
			bs_read(&s, 1);     /* video_full_range_flag */

			if(bs_read(&s, 1))  /* colour_description_present_flag */
			{
				bs_read(&s, 8);	/* colour_primaries */
				bs_read(&s, 8); /* transfer_characteristics */
				bs_read(&s, 8); /* matrix_coefficients */
			}
		}

		if(bs_read(&s, 1))		/* chroma_location_info_present_flag */
		{
			bs_read_ue(&s);		/* chroma_sample_location_type_top_field */
			bs_read_ue(&s);		/* chroma_sample_location_type_bottom_field */
		}

		StreamSps->timing_info_present_flag = bs_read(&s, 1);
		if(StreamSps->timing_info_present_flag)
		{
			StreamSps->num_units_in_tick = bs_read(&s, 32);
			StreamSps->time_scale = bs_read(&s, 32);
			StreamSps->fixed_frame_rate_flag = bs_read(&s, 1);
		}

		nal_hrd_parameters_present_flag = bs_read(&s, 1);
		if(nal_hrd_parameters_present_flag)
			h264_decode_hrd_parameters(s, StreamSps);
		vcl_hrd_parameters_present_flag = bs_read(&s, 1);
		if(vcl_hrd_parameters_present_flag)
			h264_decode_hrd_parameters(s, StreamSps);
		if(nal_hrd_parameters_present_flag || vcl_hrd_parameters_present_flag)
			bs_read(&s, 1);     /* low_delay_hrd_flag */
		bs_read(&s, 1);         /* pic_struct_present_flag */

		StreamSps->bitstream_restriction_flag = bs_read(&s, 1);
		if(StreamSps->bitstream_restriction_flag)
		{
			unsigned int num_reorder_frames;
			bs_read(&s, 1);     /* motion_vectors_over_pic_boundaries_flag */
			bs_read_ue(&s); /* max_bytes_per_pic_denom */
			bs_read_ue(&s); /* max_bits_per_mb_denom */
			bs_read_ue(&s); /* log2_max_mv_length_horizontal */
			bs_read_ue(&s); /* log2_max_mv_length_vertical */
			num_reorder_frames= bs_read_ue(&s);
			bs_read_ue(&s); /*max_dec_frame_buffering*/

			if(num_reorder_frames > 16 /*max_dec_frame_buffering || max_dec_frame_buffering > 16*/){
				printf("illegal num_reorder_frames %d\n", num_reorder_frames);
				delete pb_dec;
				return true;
			}

			StreamSps->num_reorder_frames= num_reorder_frames;
		}
	}
	delete pb_dec;
	return true;
}
void 
h264MediaStream::ParseSlice(uint8_t* p_nal,  int n_nal_size, int i_nal_type)
{	
	
	if(CurSlice == NULL)
		CurSlice = new h264_slice_t;
	//转化00 00 03为00 00
	int icount = 0;
	uint8_t p_slice[64] = {0};
	int parcount = (n_nal_size>64?64:n_nal_size);
	for (int t = 0; t < parcount; t++)
	{
		if (t < parcount-2 && p_nal[t] == 0x00 && p_nal[t + 1] == 0x00 && p_nal[t + 2] == 0x03)
		{
			p_slice[icount++] = 0x00;
			p_slice[icount++] = 0x00;
			t += 2;
			continue;
		}
		p_slice[icount++] = p_nal[t];
	}
	
	


	bs_t s;
	bs_init(&s, p_slice, icount);

	bs_read_ue( &s );	// first_mb_in_slice
	CurSlice->i_slice_type = bs_read_ue( &s );	// slice type

	int i_pic_parameter_set_id = bs_read_ue( &s );
	CurSlice->i_frame_num = bs_read( &s, StreamSps->log2_max_frame_num + 4 );

	int i_field_pic_flag = 0;
	int i_bottom_field_flag = -1;
	if( !StreamSps->frame_mbs_only_flag)
	{
		/* field_pic_flag */
		i_field_pic_flag = bs_read( &s, 1 );
		if( i_field_pic_flag )
			i_bottom_field_flag = bs_read( &s, 1 );
	}

	int i_idr_pic_id;
	if( i_nal_type == 5/*NAL_SLICE_IDR*/ )
		i_idr_pic_id = bs_read_ue( &s );

	int i_delta_pic_order_cnt_bottom = -1;
	int i_delta_pic_order_cnt0 = 0;
	int i_delta_pic_order_cnt1 = 0;

	CurSlice->i_pic_order_cnt_lsb = 0;

	if( StreamSps->poc_type == 0 )
	{
		CurSlice->i_pic_order_cnt_lsb = bs_read( &s, StreamSps->log2_max_poc_lsb + 4 );
		//if( g_pic_order_present_flag && !i_field_pic_flag )
		//	i_delta_pic_order_cnt_bottom = bs_read_se( &s );
	}
	else if( (StreamSps->poc_type == 1) &&
		(!StreamSps->delta_pic_order_always_zero_flag) )
	{
		i_delta_pic_order_cnt0 = bs_read_se( &s );
		//if( g_pic_order_present_flag && !i_field_pic_flag )
		//	i_delta_pic_order_cnt1 = bs_read_se( &s );
	}
}