Merge commit 'f42485dbce614b3f63182845da43db690b427b7c'
authorMichael Niedermayer <michaelni@gmx.at>
Sat, 21 Mar 2015 16:13:24 +0000 (17:13 +0100)
committerMichael Niedermayer <michaelni@gmx.at>
Sat, 21 Mar 2015 16:13:24 +0000 (17:13 +0100)
* commit 'f42485dbce614b3f63182845da43db690b427b7c':
  h264: use a separate GetBitContext for slice data

Conflicts:
libavcodec/h264.c
libavcodec/h264_cavlc.c
libavcodec/h264_parser.c
libavcodec/h264_slice.c

Merged-by: Michael Niedermayer <michaelni@gmx.at>
1  2 
libavcodec/h264.c
libavcodec/h264.h
libavcodec/h264_cavlc.c
libavcodec/h264_parser.c
libavcodec/h264_refs.c
libavcodec/h264_slice.c

@@@ -1010,19 -1007,9 +1010,19 @@@ int ff_pred_weight_table(H264Context *h
  
      sl->use_weight             = 0;
      sl->use_weight_chroma      = 0;
-     sl->luma_log2_weight_denom = get_ue_golomb(&h->gb);
+     sl->luma_log2_weight_denom = get_ue_golomb(&sl->gb);
      if (h->sps.chroma_format_idc)
-         sl->chroma_log2_weight_denom = get_ue_golomb(&h->gb);
+         sl->chroma_log2_weight_denom = get_ue_golomb(&sl->gb);
 +
 +    if (sl->luma_log2_weight_denom > 7U) {
 +        av_log(h->avctx, AV_LOG_ERROR, "luma_log2_weight_denom %d is out of range\n", sl->luma_log2_weight_denom);
 +        sl->luma_log2_weight_denom = 0;
 +    }
 +    if (sl->chroma_log2_weight_denom > 7U) {
 +        av_log(h->avctx, AV_LOG_ERROR, "chroma_log2_weight_denom %d is out of range\n", sl->chroma_log2_weight_denom);
 +        sl->chroma_log2_weight_denom = 0;
 +    }
 +
      luma_def   = 1 << sl->luma_log2_weight_denom;
      chroma_def = 1 << sl->chroma_log2_weight_denom;
  
@@@ -1303,27 -1266,19 +1303,27 @@@ int ff_set_ref_count(H264Context *h, H2
      ref_count[1] = h->pps.ref_count[1];
  
      if (sl->slice_type_nos != AV_PICTURE_TYPE_I) {
 +        unsigned max[2];
 +        max[0] = max[1] = h->picture_structure == PICT_FRAME ? 15 : 31;
 +
          if (sl->slice_type_nos == AV_PICTURE_TYPE_B)
-             sl->direct_spatial_mv_pred = get_bits1(&h->gb);
-         num_ref_idx_active_override_flag = get_bits1(&h->gb);
+             sl->direct_spatial_mv_pred = get_bits1(&sl->gb);
+         num_ref_idx_active_override_flag = get_bits1(&sl->gb);
  
          if (num_ref_idx_active_override_flag) {
-             ref_count[0] = get_ue_golomb(&h->gb) + 1;
+             ref_count[0] = get_ue_golomb(&sl->gb) + 1;
 -            if (ref_count[0] < 1)
 -                return AVERROR_INVALIDDATA;
              if (sl->slice_type_nos == AV_PICTURE_TYPE_B) {
-                 ref_count[1] = get_ue_golomb(&h->gb) + 1;
+                 ref_count[1] = get_ue_golomb(&sl->gb) + 1;
 -                if (ref_count[1] < 1)
 -                    return AVERROR_INVALIDDATA;
 -            }
 +            } else
 +                // full range is spec-ok in this case, even for frames
 +                ref_count[1] = 1;
 +        }
 +
 +        if (ref_count[0]-1 > max[0] || ref_count[1]-1 > max[1]){
 +            av_log(h->avctx, AV_LOG_ERROR, "reference overflow %u > %u or %u > %u\n", ref_count[0]-1, max[0], ref_count[1]-1, max[1]);
 +            sl->ref_count[0] = sl->ref_count[1] = 0;
 +            sl->list_count   = 0;
 +            return AVERROR_INVALIDDATA;
          }
  
          if (sl->slice_type_nos == AV_PICTURE_TYPE_B)
@@@ -1564,12 -1526,9 +1564,12 @@@ again
                      ret = -1;
                      goto end;
                  }
 -                idr(h); // FIXME ensure we don't lose some frames if there is reordering
 +                if(!idr_cleared)
 +                    idr(h); // FIXME ensure we don't lose some frames if there is reordering
 +                idr_cleared = 1;
 +                h->has_recovery_point = 1;
              case NAL_SLICE:
-                 init_get_bits(&hx->gb, ptr, bit_length);
+                 init_get_bits(&sl->gb, ptr, bit_length);
  
                  if ((err = ff_h264_decode_slice_header(hx, sl, h)))
                      break;
Simple merge
@@@ -718,7 -710,7 +718,7 @@@ int ff_h264_decode_mb_cavlc(H264Contex
                  down the code */
      if (sl->slice_type_nos != AV_PICTURE_TYPE_I) {
          if (sl->mb_skip_run == -1)
-             sl->mb_skip_run = get_ue_golomb_long(&h->gb);
 -            sl->mb_skip_run = get_ue_golomb(&sl->gb);
++            sl->mb_skip_run = get_ue_golomb_long(&sl->gb);
  
          if (sl->mb_skip_run--) {
              if (FRAME_MBAFF(h) && (sl->mb_y & 1) == 0) {
@@@ -863,9 -852,9 +863,9 @@@ decode_intra_mb
                  sl->ref_cache[1][scan8[12]] = PART_NOT_AVAILABLE;
              }
          }else{
 -            assert(sl->slice_type_nos == AV_PICTURE_TYPE_P); //FIXME SP correct ?
 +            av_assert2(sl->slice_type_nos == AV_PICTURE_TYPE_P); //FIXME SP correct ?
              for(i=0; i<4; i++){
-                 sl->sub_mb_type[i]= get_ue_golomb_31(&h->gb);
+                 sl->sub_mb_type[i]= get_ue_golomb_31(&sl->gb);
                  if(sl->sub_mb_type[i] >=4){
                      av_log(h->avctx, AV_LOG_ERROR, "P sub_mb_type %u out of range at %d %d\n", sl->sub_mb_type[i], sl->mb_x, sl->mb_y);
                      return -1;
              for (list = 0; list < sl->list_count; list++) {
                      unsigned int val;
                      if(IS_DIR(mb_type, 0, list)){
 -                        int rc = sl->ref_count[list] << MB_MBAFF(h);
 -                        if (rc == 1) {
 +                        if(local_ref_count[list]==1){
                              val= 0;
 -                        } else if (rc == 2) {
 +                        } else if(local_ref_count[list]==2){
-                             val= get_bits1(&h->gb)^1;
+                             val= get_bits1(&sl->gb)^1;
                          }else{
-                             val= get_ue_golomb_31(&h->gb);
+                             val= get_ue_golomb_31(&sl->gb);
 -                            if (val >= rc) {
 +                            if (val >= local_ref_count[list]){
                                  av_log(h->avctx, AV_LOG_ERROR, "ref %u overflow\n", val);
                                  return -1;
                              }
                      for(i=0; i<2; i++){
                          unsigned int val;
                          if(IS_DIR(mb_type, i, list)){
 -                            int rc = sl->ref_count[list] << MB_MBAFF(h);
 -                            if (rc == 1) {
 +                            if(local_ref_count[list] == 1) {
                                  val= 0;
 -                            } else if (rc == 2) {
 +                            } else if(local_ref_count[list] == 2) {
-                                 val= get_bits1(&h->gb)^1;
+                                 val= get_bits1(&sl->gb)^1;
                              }else{
-                                 val= get_ue_golomb_31(&h->gb);
+                                 val= get_ue_golomb_31(&sl->gb);
 -                                if (val >= rc) {
 +                                if (val >= local_ref_count[list]){
                                      av_log(h->avctx, AV_LOG_ERROR, "ref %u overflow\n", val);
                                      return -1;
                                  }
                      for(i=0; i<2; i++){
                          unsigned int val;
                          if(IS_DIR(mb_type, i, list)){ //FIXME optimize
 -                            int rc = sl->ref_count[list] << MB_MBAFF(h);
 -                            if (rc == 1) {
 +                            if(local_ref_count[list]==1){
                                  val= 0;
 -                            } else if (rc == 2) {
 +                            } else if(local_ref_count[list]==2){
-                                 val= get_bits1(&h->gb)^1;
+                                 val= get_bits1(&sl->gb)^1;
                              }else{
-                                 val= get_ue_golomb_31(&h->gb);
+                                 val= get_ue_golomb_31(&sl->gb);
 -                                if (val >= rc) {
 +                                if (val >= local_ref_count[list]){
                                      av_log(h->avctx, AV_LOG_ERROR, "ref %u overflow\n", val);
                                      return -1;
                                  }
@@@ -215,7 -184,8 +215,8 @@@ static inline int parse_nal_units(AVCod
  {
      H264ParseContext *p = s->priv_data;
      H264Context      *h = &p->h;
 -    const uint8_t *buf_end = buf + buf_size;
+     H264SliceContext *sl = &h->slice_ctx[0];
 +    int buf_index, next_avc;
      unsigned int pps_id;
      unsigned int slice_type;
      int state = -1, got_reset = 0;
              h->prev_poc_lsb          = 0;
          /* fall through */
          case NAL_SLICE:
-             get_ue_golomb_long(&h->gb);  // skip first_mb_in_slice
-             slice_type   = get_ue_golomb_31(&h->gb);
+             init_get_bits(&sl->gb, ptr, 8 * dst_length);
 -            get_ue_golomb(&sl->gb);  // skip first_mb_in_slice
++            get_ue_golomb_long(&sl->gb);  // skip first_mb_in_slice
+             slice_type   = get_ue_golomb_31(&sl->gb);
              s->pict_type = golomb_to_pict_type[slice_type % 5];
              if (h->sei_recovery_frame_cnt >= 0) {
                  /* key frame, since recovery_frame_cnt is set */
                  return -1;
              }
              h->sps       = *h->sps_buffers[h->pps.sps_id];
-             h->frame_num = get_bits(&h->gb, h->sps.log2_max_frame_num);
+             h->frame_num = get_bits(&sl->gb, h->sps.log2_max_frame_num);
  
 +            if(h->sps.ref_frame_count <= 1 && h->pps.ref_count[0] <= 1 && s->pict_type == AV_PICTURE_TYPE_I)
 +                s->key_frame = 1;
 +
              s->coded_width  = 16 * h->sps.mb_width;
              s->coded_height = 16 * h->sps.mb_height;
              s->width        = s->coded_width  - (h->sps.crop_right + h->sps.crop_left);
Simple merge
@@@ -1296,7 -1186,7 +1296,7 @@@ int ff_h264_decode_slice_header(H264Con
      h->qpel_put = h->h264qpel.put_h264_qpel_pixels_tab;
      h->qpel_avg = h->h264qpel.avg_h264_qpel_pixels_tab;
  
-     first_mb_in_slice = get_ue_golomb_long(&h->gb);
 -    first_mb_in_slice = get_ue_golomb(&sl->gb);
++    first_mb_in_slice = get_ue_golomb_long(&sl->gb);
  
      if (first_mb_in_slice == 0) { // FIXME better field boundary detection
          if (h0->current_slice && h->cur_pic_ptr && FIELD_PICTURE(h)) {
          }
      }
  
 -    if (h == h0 && h->dequant_coeff_pps != pps_id) {
 +    if (first_slice && h->dequant_coeff_pps != pps_id) {
          h->dequant_coeff_pps = pps_id;
 -        h264_init_dequant_tables(h);
 +        ff_h264_init_dequant_tables(h);
      }
  
-     frame_num = get_bits(&h->gb, h->sps.log2_max_frame_num);
 -    h->frame_num = get_bits(&sl->gb, h->sps.log2_max_frame_num);
++    frame_num = get_bits(&sl->gb, h->sps.log2_max_frame_num);
 +    if (!first_slice) {
 +        if (h0->frame_num != frame_num) {
 +            av_log(h->avctx, AV_LOG_ERROR, "Frame num change from %d to %d\n",
 +                   h0->frame_num, frame_num);
 +            return AVERROR_INVALIDDATA;
 +        }
 +    }
  
      h->mb_mbaff        = 0;
      h->mb_aff_frame    = 0;
      last_pic_structure = h0->picture_structure;
      last_pic_droppable = h0->droppable;
 -    h->droppable       = h->nal_ref_idc == 0;
 +    droppable          = h->nal_ref_idc == 0;
      if (h->sps.frame_mbs_only_flag) {
 -        h->picture_structure = PICT_FRAME;
 +        picture_structure = PICT_FRAME;
      } else {
-         field_pic_flag = get_bits1(&h->gb);
 +        if (!h->sps.direct_8x8_inference_flag && slice_type == AV_PICTURE_TYPE_B) {
 +            av_log(h->avctx, AV_LOG_ERROR, "This stream was generated by a broken encoder, invalid 8x8 inference\n");
 +            return -1;
 +        }
+         field_pic_flag = get_bits1(&sl->gb);
 +
          if (field_pic_flag) {
-             bottom_field_flag = get_bits1(&h->gb);
+             bottom_field_flag = get_bits1(&sl->gb);
 -            h->picture_structure = PICT_TOP_FIELD + bottom_field_flag;
 +            picture_structure = PICT_TOP_FIELD + bottom_field_flag;
          } else {
 -            h->picture_structure = PICT_FRAME;
 +            picture_structure = PICT_FRAME;
              h->mb_aff_frame      = h->sps.mb_aff;
          }
      }
@@@ -2406,19 -2188,9 +2406,19 @@@ static int decode_slice(struct AVCodecC
                       avctx->codec_id != AV_CODEC_ID_H264 ||
                       (CONFIG_GRAY && (h->flags & CODEC_FLAG_GRAY));
  
 +    if (!(h->avctx->active_thread_type & FF_THREAD_SLICE) && h->picture_structure == PICT_FRAME && h->er.error_status_table) {
 +        const int start_i  = av_clip(sl->resync_mb_x + sl->resync_mb_y * h->mb_width, 0, h->mb_num - 1);
 +        if (start_i) {
 +            int prev_status = h->er.error_status_table[h->er.mb_index2xy[start_i - 1]];
 +            prev_status &= ~ VP_START;
 +            if (prev_status != (ER_MV_END | ER_DC_END | ER_AC_END))
 +                h->er.error_occurred = 1;
 +        }
 +    }
 +
      if (h->pps.cabac) {
          /* realign */
-         align_get_bits(&h->gb);
+         align_get_bits(&sl->gb);
  
          /* init cabac */
          ff_init_cabac_decoder(&sl->cabac,
                  }
                  if (sl->mb_y >= h->mb_height) {
                      tprintf(h->avctx, "slice end %d %d\n",
-                             get_bits_count(&h->gb), h->gb.size_in_bits);
+                             get_bits_count(&sl->gb), sl->gb.size_in_bits);
  
-                     if (   get_bits_left(&h->gb) == 0
-                         || get_bits_left(&h->gb) > 0 && !(h->avctx->err_recognition & AV_EF_AGGRESSIVE)) {
 -                    if (get_bits_left(&sl->gb) == 0) {
++                    if (   get_bits_left(&sl->gb) == 0
++                        || get_bits_left(&sl->gb) > 0 && !(h->avctx->err_recognition & AV_EF_AGGRESSIVE)) {
                          er_add_slice(h, sl, sl->resync_mb_x, sl->resync_mb_y,
                                       sl->mb_x - 1, sl->mb_y, ER_MB_END);