static int decode_frame_packing_arrangement(H264SEIFramePacking *h, GetBitContext *gb) { h->frame_packing_arrangement_id = get_ue_golomb_long(gb); h->frame_packing_arrangement_cancel_flag = get_bits1(gb); h->present = !h->frame_packing_arrangement_cancel_flag; if (h->present) { h->frame_packing_arrangement_type = get_bits(gb, 7); h->quincunx_sampling_flag = get_bits1(gb); h->content_interpretation_type = get_bits(gb, 6); // the following skips: spatial_flipping_flag, frame0_flipped_flag, // field_views_flag, current_frame_is_frame0_flag, // frame0_self_contained_flag, frame1_self_contained_flag skip_bits(gb, 6); if (!h->quincunx_sampling_flag && h->frame_packing_arrangement_type != 5) skip_bits(gb, 16); // frame[01]_grid_position_[xy] skip_bits(gb, 8); // frame_packing_arrangement_reserved_byte h->frame_packing_arrangement_repetition_period = get_ue_golomb_long(gb); } skip_bits1(gb); // frame_packing_arrangement_extension_flag return 0; }
static int active_parameter_sets(HEVCContext *s) { GetBitContext *gb = &s->HEVClc->gb; int num_sps_ids_minus1; int i; unsigned active_seq_parameter_set_id; get_bits(gb, 4); // active_video_parameter_set_id get_bits(gb, 1); // self_contained_cvs_flag get_bits(gb, 1); // num_sps_ids_minus1 num_sps_ids_minus1 = get_ue_golomb_long(gb); // num_sps_ids_minus1 if (num_sps_ids_minus1 < 0 || num_sps_ids_minus1 > 15) { av_log(s->avctx, AV_LOG_ERROR, "num_sps_ids_minus1 %d invalid\n", num_sps_ids_minus1); return AVERROR_INVALIDDATA; } active_seq_parameter_set_id = get_ue_golomb_long(gb); if (active_seq_parameter_set_id >= MAX_SPS_COUNT) { av_log(s->avctx, AV_LOG_ERROR, "active_parameter_set_id %d invalid\n", active_seq_parameter_set_id); return AVERROR_INVALIDDATA; } s->active_seq_parameter_set_id = active_seq_parameter_set_id; for (i = 1; i <= num_sps_ids_minus1; i++) get_ue_golomb_long(gb); // active_seq_parameter_set_id[i] return 0; }
static int decode_nal_sei_frame_packing_arrangement(HEVCContext *s) { GetBitContext *gb = &s->HEVClc->gb; get_ue_golomb_long(gb); // frame_packing_arrangement_id s->sei_frame_packing_present = !get_bits1(gb); if (s->sei_frame_packing_present) { s->frame_packing_arrangement_type = get_bits(gb, 7); s->quincunx_subsampling = get_bits1(gb); s->content_interpretation_type = get_bits(gb, 6); // the following skips spatial_flipping_flag frame0_flipped_flag // field_views_flag current_frame_is_frame0_flag // frame0_self_contained_flag frame1_self_contained_flag skip_bits(gb, 6); if (!s->quincunx_subsampling && s->frame_packing_arrangement_type != 5) skip_bits(gb, 16); // frame[01]_grid_position_[xy] skip_bits(gb, 8); // frame_packing_arrangement_reserved_byte skip_bits1(gb); // frame_packing_arrangement_persistance_flag } skip_bits1(gb); // upsampled_aspect_ratio_flag return 0; }
int ff_h264_decode_ref_pic_list_reordering(H264SliceContext *sl, void *logctx) { int list, index; sl->nb_ref_modifications[0] = 0; sl->nb_ref_modifications[1] = 0; for (list = 0; list < sl->list_count; list++) { if (!get_bits1(&sl->gb)) // ref_pic_list_modification_flag_l[01] continue; for (index = 0; ; index++) { unsigned int op = get_ue_golomb_31(&sl->gb); if (op == 3) break; if (index >= sl->ref_count[list]) { av_log(logctx, AV_LOG_ERROR, "reference count overflow\n"); return AVERROR_INVALIDDATA; } else if (op > 2) { av_log(logctx, AV_LOG_ERROR, "illegal modification_of_pic_nums_idc %u\n", op); return AVERROR_INVALIDDATA; } sl->ref_modifications[list][index].val = get_ue_golomb_long(&sl->gb); sl->ref_modifications[list][index].op = op; sl->nb_ref_modifications[list]++; } } return 0; }
int ff_h264_decode_ref_pic_marking(H264SliceContext *sl, GetBitContext *gb, const H2645NAL *nal, void *logctx) { int i; MMCO *mmco = sl->mmco; int nb_mmco = 0; if (nal->type == H264_NAL_IDR_SLICE) { // FIXME fields skip_bits1(gb); // broken_link if (get_bits1(gb)) { mmco[0].opcode = MMCO_LONG; mmco[0].long_arg = 0; nb_mmco = 1; } sl->explicit_ref_marking = 1; } else { sl->explicit_ref_marking = get_bits1(gb); if (sl->explicit_ref_marking) { for (i = 0; i < MAX_MMCO_COUNT; i++) { MMCOOpcode opcode = get_ue_golomb_31(gb); mmco[i].opcode = opcode; if (opcode == MMCO_SHORT2UNUSED || opcode == MMCO_SHORT2LONG) { mmco[i].short_pic_num = (sl->curr_pic_num - get_ue_golomb_long(gb) - 1) & (sl->max_pic_num - 1); } if (opcode == MMCO_SHORT2LONG || opcode == MMCO_LONG2UNUSED || opcode == MMCO_LONG || opcode == MMCO_SET_MAX_LONG) { unsigned int long_arg = get_ue_golomb_31(gb); if (long_arg >= 32 || (long_arg >= 16 && !(opcode == MMCO_SET_MAX_LONG && long_arg == 16) && !(opcode == MMCO_LONG2UNUSED && FIELD_PICTURE(sl)))) { av_log(logctx, AV_LOG_ERROR, "illegal long ref in memory management control " "operation %d\n", opcode); return -1; } mmco[i].long_arg = long_arg; } if (opcode > (unsigned) MMCO_LONG) { av_log(logctx, AV_LOG_ERROR, "illegal memory management control operation %d\n", opcode); return -1; } if (opcode == MMCO_END) break; } nb_mmco = i; } } sl->nb_mmco = nb_mmco; return 0; }
static int decode_recovery_point(H264SEIRecoveryPoint *h, GetBitContext *gb) { h->recovery_frame_cnt = get_ue_golomb_long(gb); /* 1b exact_match_flag, * 1b broken_link_flag, * 2b changing_slice_group_idc */ skip_bits(gb, 4); return 0; }
static inline int decode_hrd_parameters(H264Context *h, SPS *sps){ MpegEncContext * const s = &h->s; int cpb_count, i; cpb_count = get_ue_golomb_31(&s->gb) + 1; if(cpb_count > 32U){ av_log(h->s.avctx, AV_LOG_ERROR, "cpb_count %d invalid\n", cpb_count); return -1; } get_bits(&s->gb, 4); /* bit_rate_scale */ get_bits(&s->gb, 4); /* cpb_size_scale */ for(i=0; i<cpb_count; i++){ get_ue_golomb_long(&s->gb); /* bit_rate_value_minus1 */ get_ue_golomb_long(&s->gb); /* cpb_size_value_minus1 */ get_bits1(&s->gb); /* cbr_flag */ } sps->initial_cpb_removal_delay_length = get_bits(&s->gb, 5) + 1; sps->cpb_removal_delay_length = get_bits(&s->gb, 5) + 1; sps->dpb_output_delay_length = get_bits(&s->gb, 5) + 1; sps->time_offset_length = get_bits(&s->gb, 5); sps->cpb_cnt = cpb_count; return 0; }
static int decode_display_orientation(H264SEIDisplayOrientation *h, GetBitContext *gb) { h->present = !get_bits1(gb); if (h->present) { h->hflip = get_bits1(gb); // hor_flip h->vflip = get_bits1(gb); // ver_flip h->anticlockwise_rotation = get_bits(gb, 16); get_ue_golomb_long(gb); // display_orientation_repetition_period skip_bits1(gb); // display_orientation_extension_flag } return 0; }
static int h264_find_frame_end(H264Context *h, const uint8_t *buf, int buf_size) { int i, j; uint32_t state; ParseContext *pc = &h->parse_context; int next_avc= h->is_avc ? 0 : buf_size; // mb_addr= pc->mb_addr - 1; state = pc->state; if (state > 13) state = 7; if (h->is_avc && !h->nal_length_size) av_log(h->avctx, AV_LOG_ERROR, "AVC-parser: nal length size invalid\n"); for (i = 0; i < buf_size; i++) { if (i >= next_avc) { int nalsize = 0; i = next_avc; for (j = 0; j < h->nal_length_size; j++) nalsize = (nalsize << 8) | buf[i++]; if (nalsize <= 0 || nalsize > buf_size - i) { av_log(h->avctx, AV_LOG_ERROR, "AVC-parser: nal size %d remaining %d\n", nalsize, buf_size - i); return buf_size; } next_avc = i + nalsize; state = 5; } if (state == 7) { i += h->h264dsp.startcode_find_candidate(buf + i, next_avc - i); if (i < next_avc) state = 2; } else if (state <= 2) { if (buf[i] == 1) state ^= 5; // 2->7, 1->4, 0->5 else if (buf[i]) state = 7; else state >>= 1; // 2->1, 1->0, 0->0 } else if (state <= 5) { int nalu_type = buf[i] & 0x1F; if (nalu_type == NAL_SEI || nalu_type == NAL_SPS || nalu_type == NAL_PPS || nalu_type == NAL_AUD) { if (pc->frame_start_found) { i++; goto found; } } else if (nalu_type == NAL_SLICE || nalu_type == NAL_DPA || nalu_type == NAL_IDR_SLICE) { state += 8; continue; } state = 7; } else { h->parse_history[h->parse_history_count++]= buf[i]; if (h->parse_history_count>5) { unsigned int mb, last_mb= h->parse_last_mb; GetBitContext gb; init_get_bits(&gb, h->parse_history, 8*h->parse_history_count); h->parse_history_count=0; mb= get_ue_golomb_long(&gb); h->parse_last_mb= mb; if (pc->frame_start_found) { if (mb <= last_mb) goto found; } else pc->frame_start_found = 1; state = 7; } } }
static int ff_h264_find_frame_end(H264Context *h, const uint8_t *buf, int buf_size) { int i, j; uint32_t state; ParseContext *pc = &(h->s.parse_context); int next_avc= h->is_avc ? 0 : buf_size; //printf("first %02X%02X%02X%02X\n", buf[0], buf[1],buf[2],buf[3]); // mb_addr= pc->mb_addr - 1; state= pc->state; if(state>13) state= 7; if(h->is_avc && !h->nal_length_size) av_log(h->s.avctx, AV_LOG_ERROR, "AVC-parser: nal length size invalid\n"); for(i=0; i<buf_size; i++){ if(i >= next_avc) { int nalsize = 0; i = next_avc; for(j = 0; j < h->nal_length_size; j++) nalsize = (nalsize << 8) | buf[i++]; if(nalsize <= 0 || nalsize > buf_size - i){ av_log(h->s.avctx, AV_LOG_ERROR, "AVC-parser: nal size %d remaining %d\n", nalsize, buf_size - i); return buf_size; } next_avc= i + nalsize; state= 5; } if(state==7){ #if HAVE_FAST_UNALIGNED /* we check i<buf_size instead of i+3/7 because its simpler * and there should be FF_INPUT_BUFFER_PADDING_SIZE bytes at the end */ # if HAVE_FAST_64BIT while(i<next_avc && !((~*(const uint64_t*)(buf+i) & (*(const uint64_t*)(buf+i) - 0x0101010101010101ULL)) & 0x8080808080808080ULL)) i+=8; # else while(i<next_avc && !((~*(const uint32_t*)(buf+i) & (*(const uint32_t*)(buf+i) - 0x01010101U)) & 0x80808080U)) i+=4; # endif #endif for(; i<next_avc; i++){ if(!buf[i]){ state=2; break; } } }else if(state<=2){ if(buf[i]==1) state^= 5; //2->7, 1->4, 0->5 else if(buf[i]) state = 7; else state>>=1; //2->1, 1->0, 0->0 }else if(state<=5){ int v= buf[i] & 0x1F; if(v==6 || v==7 || v==8 || v==9){ if(pc->frame_start_found){ i++; goto found; } }else if(v==1 || v==2 || v==5){ state+=8; continue; } state= 7; }else{ h->parse_history[h->parse_history_count++]= buf[i]; if(h->parse_history_count>3){ unsigned int mb, last_mb= h->parse_last_mb; GetBitContext gb; init_get_bits(&gb, h->parse_history, 8*h->parse_history_count); h->parse_history_count=0; mb= get_ue_golomb_long(&gb); last_mb= h->parse_last_mb; h->parse_last_mb= mb; if(pc->frame_start_found){ if(mb <= last_mb) goto found; }else pc->frame_start_found = 1; state= 7; } } }
int ff_h264_decode_ref_pic_marking(H264Context *h, GetBitContext *gb, int first_slice) { int i, ret; MMCO mmco_temp[MAX_MMCO_COUNT], *mmco = mmco_temp; int mmco_index = 0; if (h->nal_unit_type == NAL_IDR_SLICE) { // FIXME fields skip_bits1(gb); // broken_link if (get_bits1(gb)) { mmco[0].opcode = MMCO_LONG; mmco[0].long_arg = 0; mmco_index = 1; } } else { if (get_bits1(gb)) { // adaptive_ref_pic_marking_mode_flag for (i = 0; i < MAX_MMCO_COUNT; i++) { MMCOOpcode opcode = get_ue_golomb_31(gb); mmco[i].opcode = opcode; if (opcode == MMCO_SHORT2UNUSED || opcode == MMCO_SHORT2LONG) { mmco[i].short_pic_num = (h->curr_pic_num - get_ue_golomb_long(gb) - 1) & (h->max_pic_num - 1); #if 0 if (mmco[i].short_pic_num >= h->short_ref_count || !h->short_ref[mmco[i].short_pic_num]) { av_log(s->avctx, AV_LOG_ERROR, "illegal short ref in memory management control " "operation %d\n", mmco); return -1; } #endif } if (opcode == MMCO_SHORT2LONG || opcode == MMCO_LONG2UNUSED || opcode == MMCO_LONG || opcode == MMCO_SET_MAX_LONG) { unsigned int long_arg = get_ue_golomb_31(gb); if (long_arg >= 32 || (long_arg >= 16 && !(opcode == MMCO_SET_MAX_LONG && long_arg == 16) && !(opcode == MMCO_LONG2UNUSED && FIELD_PICTURE(h)))) { av_log(h->avctx, AV_LOG_ERROR, "illegal long ref in memory management control " "operation %d\n", opcode); return -1; } mmco[i].long_arg = long_arg; } if (opcode > (unsigned) MMCO_LONG) { av_log(h->avctx, AV_LOG_ERROR, "illegal memory management control operation %d\n", opcode); return -1; } if (opcode == MMCO_END) break; } mmco_index = i; } else { if (first_slice) { ret = ff_generate_sliding_window_mmcos(h, first_slice); if (ret < 0 && h->avctx->err_recognition & AV_EF_EXPLODE) return ret; } mmco_index = -1; } } if (first_slice && mmco_index != -1) { memcpy(h->mmco, mmco_temp, sizeof(h->mmco)); h->mmco_index = mmco_index; } else if (!first_slice && mmco_index >= 0 && (mmco_index != h->mmco_index || check_opcodes(h->mmco, mmco_temp, mmco_index))) { av_log(h->avctx, AV_LOG_ERROR, "Inconsistent MMCO state between slices [%d, %d]\n", mmco_index, h->mmco_index); return AVERROR_INVALIDDATA; } return 0; }
int ff_h264_decode_ref_pic_list_reordering(H264Context *h, H264SliceContext *sl) { int list, index, pic_structure; print_short_term(h); print_long_term(h); h264_initialise_ref_list(h, sl); for (list = 0; list < sl->list_count; list++) { if (get_bits1(&sl->gb)) { // ref_pic_list_modification_flag_l[01] int pred = h->curr_pic_num; for (index = 0; ; index++) { unsigned int modification_of_pic_nums_idc = get_ue_golomb_31(&sl->gb); unsigned int pic_id; int i; H264Picture *ref = NULL; if (modification_of_pic_nums_idc == 3) break; if (index >= sl->ref_count[list]) { av_log(h->avctx, AV_LOG_ERROR, "reference count overflow\n"); return -1; } switch (modification_of_pic_nums_idc) { case 0: case 1: { const unsigned int abs_diff_pic_num = get_ue_golomb_long(&sl->gb) + 1; int frame_num; if (abs_diff_pic_num > h->max_pic_num) { av_log(h->avctx, AV_LOG_ERROR, "abs_diff_pic_num overflow\n"); return AVERROR_INVALIDDATA; } if (modification_of_pic_nums_idc == 0) pred -= abs_diff_pic_num; else pred += abs_diff_pic_num; pred &= h->max_pic_num - 1; frame_num = pic_num_extract(h, pred, &pic_structure); for (i = h->short_ref_count - 1; i >= 0; i--) { ref = h->short_ref[i]; assert(ref->reference); assert(!ref->long_ref); if (ref->frame_num == frame_num && (ref->reference & pic_structure)) break; } if (i >= 0) ref->pic_id = pred; break; } case 2: { int long_idx; pic_id = get_ue_golomb(&sl->gb); // long_term_pic_idx long_idx = pic_num_extract(h, pic_id, &pic_structure); if (long_idx > 31U) { av_log(h->avctx, AV_LOG_ERROR, "long_term_pic_idx overflow\n"); return AVERROR_INVALIDDATA; } ref = h->long_ref[long_idx]; assert(!(ref && !ref->reference)); if (ref && (ref->reference & pic_structure) && !mismatches_ref(h, ref)) { ref->pic_id = pic_id; assert(ref->long_ref); i = 0; } else { i = -1; } break; } default: av_log(h->avctx, AV_LOG_ERROR, "illegal modification_of_pic_nums_idc %u\n", modification_of_pic_nums_idc); return AVERROR_INVALIDDATA; } if (i < 0) { av_log(h->avctx, AV_LOG_ERROR, "reference picture missing during reorder\n"); memset(&sl->ref_list[list][index], 0, sizeof(sl->ref_list[0][0])); // FIXME } else { for (i = index; i + 1 < sl->ref_count[list]; i++) { if (sl->ref_list[list][i].parent && ref->long_ref == sl->ref_list[list][i].parent->long_ref && ref->pic_id == sl->ref_list[list][i].pic_id) break; } for (; i > index; i--) { sl->ref_list[list][i] = sl->ref_list[list][i - 1]; } ref_from_h264pic(&sl->ref_list[list][index], ref); if (FIELD_PICTURE(h)) { pic_as_field(&sl->ref_list[list][index], pic_structure); } } } } } for (list = 0; list < sl->list_count; list++) { for (index = 0; index < sl->ref_count[list]; index++) { if ( !sl->ref_list[list][index].parent || (!FIELD_PICTURE(h) && (sl->ref_list[list][index].reference&3) != 3)) { int i; av_log(h->avctx, AV_LOG_ERROR, "Missing reference picture, default is %d\n", h->default_ref[list].poc); for (i = 0; i < FF_ARRAY_ELEMS(h->last_pocs); i++) h->last_pocs[i] = INT_MIN; if (h->default_ref[list].parent && !(!FIELD_PICTURE(h) && (h->default_ref[list].reference&3) != 3)) sl->ref_list[list][index] = h->default_ref[list]; else return -1; } av_assert0(av_buffer_get_ref_count(sl->ref_list[list][index].parent->f->buf[0]) > 0); } } return 0; }
int main(void) { int i, ret = 0; uint8_t *temp; PutBitContext pb; BitstreamContext bc; temp = av_malloc(SIZE); if (!temp) return 2; init_put_bits(&pb, temp, SIZE); for (i = 0; i < COUNT; i++) set_ue_golomb(&pb, i); flush_put_bits(&pb); bitstream_init8(&bc, temp, SIZE); for (i = 0; i < COUNT; i++) { int j, s = bitstream_peek(&bc, 25); j = get_ue_golomb(&bc); if (j != i) { fprintf(stderr, "get_ue_golomb: expected %d, got %d. bits: %7x\n", i, j, s); ret = 1; } } #define EXTEND(i) (i << 3 | i & 7) init_put_bits(&pb, temp, SIZE); for (i = 0; i < COUNT; i++) set_ue_golomb(&pb, EXTEND(i)); flush_put_bits(&pb); bitstream_init8(&bc, temp, SIZE); for (i = 0; i < COUNT; i++) { int j, s = bitstream_peek(&bc, 32); j = get_ue_golomb_long(&bc); if (j != EXTEND(i)) { fprintf(stderr, "get_ue_golomb_long: expected %d, got %d. " "bits: %8x\n", EXTEND(i), j, s); ret = 1; } } init_put_bits(&pb, temp, SIZE); for (i = 0; i < COUNT; i++) set_se_golomb(&pb, i - COUNT / 2); flush_put_bits(&pb); bitstream_init8(&bc, temp, SIZE); for (i = 0; i < COUNT; i++) { int j, s = bitstream_peek(&bc, 25); j = get_se_golomb(&bc); if (j != i - COUNT / 2) { fprintf(stderr, "get_se_golomb: expected %d, got %d. bits: %7x\n", i - COUNT / 2, j, s); ret = 1; } } av_free(temp); return ret; }