X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavcodec%2Fcavsdec.c;h=9c3825df3846d4e2ef2e915bdf94a0af918db2b7;hb=e83717e63eab1f1b78dc0990e5b8e927097fca29;hp=c7fff67c06c660ce31e11b7d3aea8cf8b5b725a7;hpb=ef71ef5f30ddf1cd61e46628a04608892caf76d2;p=ffmpeg diff --git a/libavcodec/cavsdec.c b/libavcodec/cavsdec.c index c7fff67c06c..9c3825df384 100644 --- a/libavcodec/cavsdec.c +++ b/libavcodec/cavsdec.c @@ -591,14 +591,21 @@ static int decode_residual_block(AVSContext *h, GetBitContext *gb, } -static inline void decode_residual_chroma(AVSContext *h) +static inline int decode_residual_chroma(AVSContext *h) { - if (h->cbp & (1 << 4)) - decode_residual_block(h, &h->gb, chroma_dec, 0, + if (h->cbp & (1 << 4)) { + int ret = decode_residual_block(h, &h->gb, chroma_dec, 0, ff_cavs_chroma_qp[h->qp], h->cu, h->c_stride); - if (h->cbp & (1 << 5)) - decode_residual_block(h, &h->gb, chroma_dec, 0, + if (ret < 0) + return ret; + } + if (h->cbp & (1 << 5)) { + int ret = decode_residual_block(h, &h->gb, chroma_dec, 0, ff_cavs_chroma_qp[h->qp], h->cv, h->c_stride); + if (ret < 0) + return ret; + } + return 0; } static inline int decode_residual_inter(AVSContext *h) @@ -649,6 +656,7 @@ static int decode_mb_i(AVSContext *h, int cbp_code) uint8_t top[18]; uint8_t *left = NULL; uint8_t *d; + int ret; ff_cavs_init_mb(h); @@ -668,7 +676,7 @@ static int decode_mb_i(AVSContext *h, int cbp_code) } h->pred_mode_Y[pos] = predpred; } - pred_mode_uv = get_ue_golomb(gb); + pred_mode_uv = get_ue_golomb_31(gb); if (pred_mode_uv > 6) { av_log(h->avctx, AV_LOG_ERROR, "illegal intra chroma pred mode\n"); return AVERROR_INVALIDDATA; @@ -692,8 +700,11 @@ static int decode_mb_i(AVSContext *h, int cbp_code) ff_cavs_load_intra_pred_luma(h, top, &left, block); h->intra_pred_l[h->pred_mode_Y[scan3x3[block]]] (d, top, left, h->l_stride); - if (h->cbp & (1<qp, d, h->l_stride); + if (h->cbp & (1<qp, d, h->l_stride); + if (ret < 0) + return ret; + } } /* chroma intra prediction */ @@ -703,7 +714,9 @@ static int decode_mb_i(AVSContext *h, int cbp_code) h->intra_pred_c[pred_mode_uv](h->cv, &h->top_border_v[h->mbx * 10], h->left_border_v, h->c_stride); - decode_residual_chroma(h); + ret = decode_residual_chroma(h); + if (ret < 0) + return ret; ff_cavs_filter(h, I_8X8); set_mv_intra(h); return 0; @@ -1088,11 +1101,20 @@ static int decode_pic(AVSContext *h) do { if (check_for_slice(h)) skip_count = -1; - if (h->skip_mode_flag && (skip_count < 0)) + if (h->skip_mode_flag && (skip_count < 0)) { + if (get_bits_left(&h->gb) < 1) { + ret = AVERROR_INVALIDDATA; + break; + } skip_count = get_ue_golomb(&h->gb); + } if (h->skip_mode_flag && skip_count--) { decode_mb_p(h, P_SKIP); } else { + if (get_bits_left(&h->gb) < 1) { + ret = AVERROR_INVALIDDATA; + break; + } mb_type = get_ue_golomb(&h->gb) + P_SKIP + h->skip_mode_flag; if (mb_type > P_8X8) ret = decode_mb_i(h, mb_type - P_8X8 - 1); @@ -1106,11 +1128,20 @@ static int decode_pic(AVSContext *h) do { if (check_for_slice(h)) skip_count = -1; - if (h->skip_mode_flag && (skip_count < 0)) + if (h->skip_mode_flag && (skip_count < 0)) { + if (get_bits_left(&h->gb) < 1) { + ret = AVERROR_INVALIDDATA; + break; + } skip_count = get_ue_golomb(&h->gb); + } if (h->skip_mode_flag && skip_count--) { ret = decode_mb_b(h, B_SKIP); } else { + if (get_bits_left(&h->gb) < 1) { + ret = AVERROR_INVALIDDATA; + break; + } mb_type = get_ue_golomb(&h->gb) + B_SKIP + h->skip_mode_flag; if (mb_type > B_8X8) ret = decode_mb_i(h, mb_type - B_8X8 - 1); @@ -1202,6 +1233,7 @@ static int cavs_decode_frame(AVCodecContext *avctx, void *data, int *got_frame, int input_size, ret; const uint8_t *buf_end; const uint8_t *buf_ptr; + int frame_start = 0; if (buf_size == 0) { if (!h->low_delay && h->DPB[0].f->data[0]) { @@ -1235,6 +1267,9 @@ static int cavs_decode_frame(AVCodecContext *avctx, void *data, int *got_frame, h->got_keyframe = 1; } case PIC_PB_START_CODE: + if (frame_start > 1) + return AVERROR_INVALIDDATA; + frame_start ++; if (*got_frame) av_frame_unref(data); *got_frame = 0;