[SCM] libav/master: Imported Upstream version 0.8.8

siretart at users.alioth.debian.org siretart at users.alioth.debian.org
Fri Jul 12 20:00:46 UTC 2013


The following commit has been merged in the master branch:
commit 9a88bd4bbd77c5b55809b1c77f264a81ba2523e1
Author: Reinhard Tartler <siretart at tauware.de>
Date:   Fri Jul 12 21:27:38 2013 +0200

    Imported Upstream version 0.8.8

diff --git a/Changelog b/Changelog
index 9295452..2cbf41d 100644
--- a/Changelog
+++ b/Changelog
@@ -1,6 +1,39 @@
 Entries are sorted chronologically from oldest to youngest within each release,
 releases are sorted from youngest to oldest.
 
+
+version 0.8.8:
+
+- kmvc: Clip pixel position to valid range
+- kmvc: use fixed sized arrays in the context
+- indeo: use a typedef for the mc function pointer
+- lavc: check for overflow in init_get_bits
+- mjpegdec: properly report unsupported disabled features
+- jpegls: return meaningful errors
+- jpegls: factorize return paths
+- jpegls: check the scan offset
+- wavpack: validate samples size parsed in wavpack_decode_block
+- ljpeg: use the correct number of components in yuv
+- mjpeg: Validate sampling factors
+- mjpegdec: validate parameters in mjpeg_decode_scan_progressive_ac
+- wavpack: check packet size early
+- wavpack: return meaningful errors
+- apetag: use int64_t for filesize
+- tiff: do not overread the source buffer
+- Prepare for 0.8.8 Release
+- smacker: fix an off by one in huff.length computation
+- smacker: check the return value of smacker_decode_tree
+- smacker: pad the extradata allocation
+- smacker: check frame size validity
+- vmdav: convert to bytestream2
+- 4xm: don't rely on get_buffer() initializing the frame.
+- 4xm: check the return value of read_huffman_tables().
+- 4xm: use the correct logging context
+- 4xm: reject frames not compatible with the declared version
+- 4xm: check bitstream_size boundary before using it
+- 4xm: do not overread the source buffer in decode_p_block
+
+
 version 0.8.7:
 
 - avfiltergraph: check for sws opts being non-NULL before using them
diff --git a/RELEASE b/RELEASE
index 1e9b46b..6201b5f 100644
--- a/RELEASE
+++ b/RELEASE
@@ -1 +1 @@
-0.8.7
+0.8.8
diff --git a/VERSION b/VERSION
index 1e9b46b..6201b5f 100644
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-0.8.7
+0.8.8
diff --git a/libavcodec/4xm.c b/libavcodec/4xm.c
index 0d4f036..77d15d5 100644
--- a/libavcodec/4xm.c
+++ b/libavcodec/4xm.c
@@ -343,6 +343,10 @@ static void decode_p_block(FourXContext *f, uint16_t *dst, uint16_t *src, int lo
         decode_p_block(f, dst             , src             , log2w, log2h, stride);
         decode_p_block(f, dst + (1<<log2w), src + (1<<log2w), log2w, log2h, stride);
     }else if(code == 3 && f->version<2){
+        if (start > src || src > end) {
+            av_log(f->avctx, AV_LOG_ERROR, "mv out of pic\n");
+            return;
+        }
         mcdc(dst, src, log2w, h, stride, 1, 0);
     }else if(code == 4){
         src += f->mv[bytestream2_get_byte(&f->g)];
@@ -352,6 +356,10 @@ static void decode_p_block(FourXContext *f, uint16_t *dst, uint16_t *src, int lo
         }
         mcdc(dst, src, log2w, h, stride, 1, bytestream2_get_le16(&f->g2));
     }else if(code == 5){
+        if (start > src || src > end) {
+            av_log(f->avctx, AV_LOG_ERROR, "mv out of pic\n");
+            return;
+        }
         mcdc(dst, src, log2w, h, stride, 0, bytestream2_get_le16(&f->g2));
     }else if(code == 6){
         if(log2w){
@@ -633,8 +641,8 @@ static int decode_i2_frame(FourXContext *f, const uint8_t *buf, int length){
             color[0]= bytestream2_get_le16u(&g3);
             color[1]= bytestream2_get_le16u(&g3);
 
-            if(color[0]&0x8000) av_log(NULL, AV_LOG_ERROR, "unk bit 1\n");
-            if(color[1]&0x8000) av_log(NULL, AV_LOG_ERROR, "unk bit 2\n");
+            if(color[0]&0x8000) av_log(f->avctx, AV_LOG_ERROR, "unk bit 1\n");
+            if(color[1]&0x8000) av_log(f->avctx, AV_LOG_ERROR, "unk bit 2\n");
 
             color[2]= mix(color[0], color[1]);
             color[3]= mix(color[1], color[0]);
@@ -663,6 +671,9 @@ static int decode_i_frame(FourXContext *f, const uint8_t *buf, int length){
     unsigned int prestream_size;
     const uint8_t *prestream;
 
+    if (bitstream_size > (1 << 26))
+        return AVERROR_INVALIDDATA;
+
     if (length < bitstream_size + 12) {
         av_log(f->avctx, AV_LOG_ERROR, "packet size too small\n");
         return AVERROR_INVALIDDATA;
@@ -673,13 +684,16 @@ static int decode_i_frame(FourXContext *f, const uint8_t *buf, int length){
     prestream      = buf + bitstream_size + 12;
 
     if(prestream_size + bitstream_size + 12 != length
-       || bitstream_size > (1<<26)
        || prestream_size > (1<<26)){
         av_log(f->avctx, AV_LOG_ERROR, "size mismatch %d %d %d\n", prestream_size, bitstream_size, length);
         return -1;
     }
 
-    prestream= read_huffman_tables(f, prestream);
+    prestream = read_huffman_tables(f, prestream);
+    if (!prestream) {
+        av_log(f->avctx, AV_LOG_ERROR, "Error reading Huffman tables.\n");
+        return AVERROR_INVALIDDATA;
+    }
 
     init_get_bits(&f->gb, buf + 4, 8*bitstream_size);
 
@@ -765,6 +779,9 @@ static int decode_frame(AVCodecContext *avctx,
                 av_log(f->avctx, AV_LOG_ERROR, "cframe id mismatch %d %d\n", id, avctx->frame_number);
             }
 
+            if (f->version <= 1)
+                return AVERROR_INVALIDDATA;
+
             cfrm->size= cfrm->id= 0;
             frame_4cc= AV_RL32("pfrm");
         }else
@@ -807,6 +824,7 @@ static int decode_frame(AVCodecContext *avctx,
                 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
                 return -1;
             }
+            memset(f->last_picture.data[0], 0, avctx->height * FFABS(f->last_picture.linesize[0]));
         }
 
         p->pict_type= AV_PICTURE_TYPE_P;
diff --git a/libavcodec/dv.c b/libavcodec/dv.c
index 03a05b3..6f74e7b 100644
--- a/libavcodec/dv.c
+++ b/libavcodec/dv.c
@@ -372,11 +372,6 @@ typedef struct BlockInfo {
 static const int vs_total_ac_bits = (100 * 4 + 68*2) * 5;
 static const int mb_area_start[5] = { 1, 6, 21, 43, 64 };
 
-static inline int put_bits_left(PutBitContext* s)
-{
-    return (s->buf_end - s->buf) * 8 - put_bits_count(s);
-}
-
 /* decode AC coefficients */
 static void dv_decode_ac(GetBitContext *gb, BlockInfo *mb, DCTELEM *block)
 {
diff --git a/libavcodec/get_bits.h b/libavcodec/get_bits.h
index 64393bc..dc348c7 100644
--- a/libavcodec/get_bits.h
+++ b/libavcodec/get_bits.h
@@ -344,20 +344,27 @@ static inline int check_marker(GetBitContext *s, const char *msg)
 }
 
 /**
- * Inititalize GetBitContext.
- * @param buffer bitstream buffer, must be FF_INPUT_BUFFER_PADDING_SIZE bytes larger than the actual read bits
- * because some optimized bitstream readers read 32 or 64 bit at once and could read over the end
+ * Initialize GetBitContext.
+ * @param buffer bitstream buffer, must be FF_INPUT_BUFFER_PADDING_SIZE bytes
+ *        larger than the actual read bits because some optimized bitstream
+ *        readers read 32 or 64 bit at once and could read over the end
  * @param bit_size the size of the buffer in bits
+ * @return 0 on success, AVERROR_INVALIDDATA if the buffer_size would overflow.
  */
-static inline void init_get_bits(GetBitContext *s, const uint8_t *buffer,
-                                 int bit_size)
+static inline int init_get_bits(GetBitContext *s, const uint8_t *buffer,
+                                int bit_size)
 {
-    int buffer_size = (bit_size+7)>>3;
-    if (buffer_size < 0 || bit_size < 0) {
+    int buffer_size;
+    int ret = 0;
+
+    if (bit_size > INT_MAX - 7 || bit_size <= 0) {
         buffer_size = bit_size = 0;
         buffer = NULL;
+        ret = AVERROR_INVALIDDATA;
     }
 
+    buffer_size = (bit_size + 7) >> 3;
+
     s->buffer       = buffer;
     s->size_in_bits = bit_size;
 #if !UNCHECKED_BITSTREAM_READER
@@ -365,6 +372,7 @@ static inline void init_get_bits(GetBitContext *s, const uint8_t *buffer,
 #endif
     s->buffer_end   = buffer + buffer_size;
     s->index        = 0;
+    return ret;
 }
 
 static inline void align_get_bits(GetBitContext *s)
diff --git a/libavcodec/ivi_common.c b/libavcodec/ivi_common.c
index 00205ae..c907e2a 100644
--- a/libavcodec/ivi_common.c
+++ b/libavcodec/ivi_common.c
@@ -39,6 +39,9 @@ extern const IVIHuffDesc ff_ivi_blk_huff_desc[8]; ///< static block huffman tabl
 VLC ff_ivi_mb_vlc_tabs [8];
 VLC ff_ivi_blk_vlc_tabs[8];
 
+typedef void (*ivi_mc_func) (int16_t *buf, const int16_t *ref_buf,
+                             uint32_t pitch, int mc_type);
+
 /**
  *  Reverse "nbits" bits of the value "val" and return the result
  *  in the least significant bits.
@@ -74,7 +77,7 @@ int ff_ivi_create_huff_from_desc(const IVIHuffDesc *cb, VLC *vlc, int flag)
 
             bits[pos] = i + cb->xbits[i] + not_last_row;
             if (bits[pos] > IVI_VLC_BITS)
-                return -1; /* invalid descriptor */
+                return AVERROR_INVALIDDATA; /* invalid descriptor */
 
             codewords[pos] = inv_bits((prefix | j), bits[pos]);
             if (!bits[pos])
@@ -343,8 +346,7 @@ int ff_ivi_decode_blocks(GetBitContext *gb, IVIBandDesc *band, IVITile *tile)
     uint32_t    cbp, sym, lo, hi, quant, buf_offs, q;
     IVIMbInfo   *mb;
     RVMapDesc   *rvmap = band->rv_map;
-    void (*mc_with_delta_func)(int16_t *buf, const int16_t *ref_buf, uint32_t pitch, int mc_type);
-    void (*mc_no_delta_func)  (int16_t *buf, const int16_t *ref_buf, uint32_t pitch, int mc_type);
+    ivi_mc_func mc_with_delta_func, mc_no_delta_func;
     const uint16_t  *base_tab;
     const uint8_t   *scale_tab;
 
@@ -433,7 +435,7 @@ int ff_ivi_decode_blocks(GetBitContext *gb, IVIBandDesc *band, IVITile *tile)
                     } else {
                         if (sym >= 256U) {
                             av_log(NULL, AV_LOG_ERROR, "Invalid sym encountered: %d.\n", sym);
-                            return -1;
+                            return AVERROR_INVALIDDATA;
                         }
                         run = rvmap->runtab[sym];
                         val = rvmap->valtab[sym];
@@ -456,7 +458,7 @@ int ff_ivi_decode_blocks(GetBitContext *gb, IVIBandDesc *band, IVITile *tile)
                 }// while
 
                 if (scan_pos >= num_coeffs && sym != rvmap->eob_sym)
-                    return -1; /* corrupt block data */
+                    return AVERROR_INVALIDDATA; /* corrupt block data */
 
                 /* undoing DC coeff prediction for intra-blocks */
                 if (is_intra && band->is_2d_trans) {
@@ -514,8 +516,7 @@ static int ivi_process_empty_tile(AVCodecContext *avctx, IVIBandDesc *band,
     IVIMbInfo       *mb, *ref_mb;
     const int16_t   *src;
     int16_t         *dst;
-    void (*mc_no_delta_func)(int16_t *buf, const int16_t *ref_buf, uint32_t pitch,
-                             int mc_type);
+    ivi_mc_func     mc_no_delta_func;
 
     if (tile->num_MBs != IVI_MBs_PER_TILE(tile->width, tile->height, band->mb_size)) {
         av_log(avctx, AV_LOG_ERROR, "Allocated tile size %d mismatches "
@@ -550,7 +551,7 @@ static int ivi_process_empty_tile(AVCodecContext *avctx, IVIBandDesc *band,
             if (band->inherit_qdelta && ref_mb)
                 mb->q_delta = ref_mb->q_delta;
 
-            if (band->inherit_mv) {
+            if (band->inherit_mv && ref_mb) {
                 /* motion vector inheritance */
                 if (mv_scale) {
                     mb->mv_x = ivi_scale_mv(ref_mb->mv_x, mv_scale);
@@ -737,8 +738,16 @@ static int decode_band(IVI45DecContext *ctx, int plane_num,
                 break;
 
             result = ff_ivi_decode_blocks(&ctx->gb, band, tile);
-            if (result < 0 || ((get_bits_count(&ctx->gb) - pos) >> 3) != tile->data_size) {
-                av_log(avctx, AV_LOG_ERROR, "Corrupted tile data encountered!\n");
+            if (result < 0) {
+                av_log(avctx, AV_LOG_ERROR,
+                       "Corrupted tile data encountered!\n");
+                break;
+            }
+
+            if (((get_bits_count(&ctx->gb) - pos) >> 3) != tile->data_size) {
+                av_log(avctx, AV_LOG_ERROR,
+                       "Tile data_size mismatch!\n");
+                result = AVERROR_INVALIDDATA;
                 break;
             }
 
@@ -786,14 +795,14 @@ int ff_ivi_decode_frame(AVCodecContext *avctx, void *data, int *data_size,
     if (result) {
         av_log(avctx, AV_LOG_ERROR,
                "Error while decoding picture header: %d\n", result);
-        return -1;
+        return result;
     }
     if (ctx->gop_invalid)
         return AVERROR_INVALIDDATA;
 
     if (ctx->gop_flags & IVI5_IS_PROTECTED) {
         av_log(avctx, AV_LOG_ERROR, "Password-protected clip!\n");
-        return -1;
+        return AVERROR_PATCHWELCOME;
     }
 
     ctx->switch_buffers(ctx);
@@ -804,10 +813,10 @@ int ff_ivi_decode_frame(AVCodecContext *avctx, void *data, int *data_size,
         for (p = 0; p < 3; p++) {
             for (b = 0; b < ctx->planes[p].num_bands; b++) {
                 result = decode_band(ctx, p, &ctx->planes[p].bands[b], avctx);
-                if (result) {
+                if (result < 0) {
                     av_log(avctx, AV_LOG_ERROR,
                            "Error while decoding band: %d, plane: %d\n", b, p);
-                    return -1;
+                    return result;
                 }
             }
         }
diff --git a/libavcodec/jpeglsdec.c b/libavcodec/jpeglsdec.c
index a4cfe4f..d234d73 100644
--- a/libavcodec/jpeglsdec.c
+++ b/libavcodec/jpeglsdec.c
@@ -71,13 +71,13 @@ int ff_jpegls_decode_lse(MJpegDecodeContext *s)
     case 2:
     case 3:
         av_log(s->avctx, AV_LOG_ERROR, "palette not supported\n");
-        return -1;
+        return AVERROR(ENOSYS);
     case 4:
         av_log(s->avctx, AV_LOG_ERROR, "oversize image not supported\n");
-        return -1;
+        return AVERROR(ENOSYS);
     default:
         av_log(s->avctx, AV_LOG_ERROR, "invalid id %d\n", id);
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
 //    av_log(s->avctx, AV_LOG_DEBUG, "ID=%i, T=%i,%i,%i\n", id, s->t1, s->t2, s->t3);
 
@@ -260,7 +260,7 @@ int ff_jpegls_decode_picture(MJpegDecodeContext *s, int near, int point_transfor
     int i, t = 0;
     uint8_t *zero, *last, *cur;
     JLSState *state;
-    int off = 0, stride = 1, width, shift;
+    int off = 0, stride = 1, width, shift, ret = 0;
 
     zero = av_mallocz(s->picture_ptr->linesize[0]);
     last = zero;
@@ -286,6 +286,10 @@ int ff_jpegls_decode_picture(MJpegDecodeContext *s, int near, int point_transfor
 //    av_log(s->avctx, AV_LOG_DEBUG, "JPEG-LS params: %ix%i NEAR=%i MV=%i T(%i,%i,%i) RESET=%i, LIMIT=%i, qbpp=%i, RANGE=%i\n",s->width,s->height,state->near,state->maxval,state->T1,state->T2,state->T3,state->reset,state->limit,state->qbpp, state->range);
 //    av_log(s->avctx, AV_LOG_DEBUG, "JPEG params: ILV=%i Pt=%i BPP=%i, scan = %i\n", ilv, point_transform, s->bits, s->cur_scan);
     if(ilv == 0) { /* separate planes */
+        if (s->cur_scan > s->nb_components) {
+            ret = AVERROR_INVALIDDATA;
+            goto end;
+        }
         off = s->cur_scan - 1;
         stride = (s->nb_components > 1) ? 3 : 1;
         width = s->width * stride;
@@ -324,11 +328,10 @@ int ff_jpegls_decode_picture(MJpegDecodeContext *s, int near, int point_transfor
             last = cur;
             cur += s->picture_ptr->linesize[0];
         }
-    } else if(ilv == 2) { /* sample interleaving */
+    } else if (ilv == 2) { /* sample interleaving */
         av_log(s->avctx, AV_LOG_ERROR, "Sample interleaved images are not supported.\n");
-        av_free(state);
-        av_free(zero);
-        return -1;
+        ret = AVERROR_PATCHWELCOME;
+        goto end;
     }
 
     if(shift){ /* we need to do point transform or normalize samples */
@@ -356,10 +359,12 @@ int ff_jpegls_decode_picture(MJpegDecodeContext *s, int near, int point_transfor
             }
         }
     }
+
+end:
     av_free(state);
     av_free(zero);
 
-    return 0;
+    return ret;
 }
 
 
diff --git a/libavcodec/kmvc.c b/libavcodec/kmvc.c
index a6bb13b..4ed7811 100644
--- a/libavcodec/kmvc.c
+++ b/libavcodec/kmvc.c
@@ -29,6 +29,8 @@
 
 #include "avcodec.h"
 #include "bytestream.h"
+#include "internal.h"
+#include "libavutil/common.h"
 
 #define KMVC_KEYFRAME 0x80
 #define KMVC_PALETTE  0x40
@@ -46,7 +48,7 @@ typedef struct KmvcContext {
     int palsize;
     uint32_t pal[MAX_PALSIZE];
     uint8_t *cur, *prev;
-    uint8_t *frm0, *frm1;
+    uint8_t frm0[320 * 200], frm1[320 * 200];
     GetByteContext g;
 } KmvcContext;
 
@@ -55,7 +57,7 @@ typedef struct BitBuf {
     int bitbuf;
 } BitBuf;
 
-#define BLK(data, x, y)  data[(x) + (y) * 320]
+#define BLK(data, x, y)  data[av_clip((x) + (y) * 320, 0, 320 * 200 -1)]
 
 #define kmvc_init_getbits(bb, g)  bb.bits = 7; bb.bitbuf = bytestream2_get_byte(g);
 
@@ -367,8 +369,6 @@ static av_cold int decode_init(AVCodecContext * avctx)
         return -1;
     }
 
-    c->frm0 = av_mallocz(320 * 200);
-    c->frm1 = av_mallocz(320 * 200);
     c->cur = c->frm0;
     c->prev = c->frm1;
 
@@ -401,30 +401,12 @@ static av_cold int decode_init(AVCodecContext * avctx)
     return 0;
 }
 
-
-
-/*
- * Uninit kmvc decoder
- */
-static av_cold int decode_end(AVCodecContext * avctx)
-{
-    KmvcContext *const c = avctx->priv_data;
-
-    av_freep(&c->frm0);
-    av_freep(&c->frm1);
-    if (c->pic.data[0])
-        avctx->release_buffer(avctx, &c->pic);
-
-    return 0;
-}
-
 AVCodec ff_kmvc_decoder = {
     .name           = "kmvc",
     .type           = AVMEDIA_TYPE_VIDEO,
     .id             = CODEC_ID_KMVC,
     .priv_data_size = sizeof(KmvcContext),
     .init           = decode_init,
-    .close          = decode_end,
     .decode         = decode_frame,
     .capabilities   = CODEC_CAP_DR1,
     .long_name = NULL_IF_CONFIG_SMALL("Karl Morton's video codec"),
diff --git a/libavcodec/mjpegdec.c b/libavcodec/mjpegdec.c
index 542de98..5256a8e 100644
--- a/libavcodec/mjpegdec.c
+++ b/libavcodec/mjpegdec.c
@@ -266,6 +266,13 @@ int ff_mjpeg_decode_sof(MJpegDecodeContext *s)
         s->quant_index[i] = get_bits(&s->gb, 8);
         if (s->quant_index[i] >= 4)
             return -1;
+        if (!s->h_count[i] || !s->v_count[i]) {
+            av_log(s->avctx, AV_LOG_ERROR,
+                   "Invalid sampling factor in component %d %d:%d\n",
+                   i, s->h_count[i], s->v_count[i]);
+            return AVERROR_INVALIDDATA;
+        }
+
         av_log(s->avctx, AV_LOG_DEBUG, "component %d %d:%d id: %d quant:%d\n",
                i, s->h_count[i], s->v_count[i],
                s->component_id[i], s->quant_index[i]);
@@ -711,10 +718,9 @@ static int ljpeg_decode_rgb_scan(MJpegDecodeContext *s, int predictor,
 }
 
 static int ljpeg_decode_yuv_scan(MJpegDecodeContext *s, int predictor,
-                                 int point_transform)
+                                 int point_transform, int nb_components)
 {
     int i, mb_x, mb_y;
-    const int nb_components = 3;
 
     for (mb_y = 0; mb_y < s->mb_height; mb_y++) {
         for (mb_x = 0; mb_x < s->mb_width; mb_x++) {
@@ -957,6 +963,11 @@ static int mjpeg_decode_scan_progressive_ac(MJpegDecodeContext *s, int ss,
     int16_t *quant_matrix = s->quant_matrixes[s->quant_index[c]];
     GetBitContext mb_bitmask_gb;
 
+    if (ss < 0  || ss >= 64 ||
+        se < ss || se >= 64 ||
+        Ah < 0  || Al < 0)
+        return AVERROR_INVALIDDATA;
+
     if (mb_bitmask)
         init_get_bits(&mb_bitmask_gb, mb_bitmask, s->mb_width * s->mb_height);
 
@@ -1108,7 +1119,8 @@ int ff_mjpeg_decode_sos(MJpegDecodeContext *s, const uint8_t *mb_bitmask,
                 if (ljpeg_decode_rgb_scan(s, predictor, point_transform) < 0)
                     return -1;
             } else {
-                if (ljpeg_decode_yuv_scan(s, predictor, point_transform) < 0)
+                if (ljpeg_decode_yuv_scan(s, predictor, point_transform,
+                                          nb_components))
                     return -1;
             }
         }
@@ -1489,6 +1501,12 @@ int ff_mjpeg_decode_frame(AVCodecContext *avctx, void *data, int *data_size,
             else if (start_code == COM)
                 mjpeg_decode_com(s);
 
+            if (!CONFIG_JPEGLS_DECODER &&
+                (start_code == SOF48 || start_code == LSE)) {
+                av_log(avctx, AV_LOG_ERROR, "JPEG-LS support not enabled.\n");
+                return AVERROR(ENOSYS);
+            }
+
             switch (start_code) {
             case SOI:
                 s->restart_interval = 0;
diff --git a/libavcodec/put_bits.h b/libavcodec/put_bits.h
index 6e81267..905461a 100644
--- a/libavcodec/put_bits.h
+++ b/libavcodec/put_bits.h
@@ -73,6 +73,14 @@ static inline int put_bits_count(PutBitContext *s)
 }
 
 /**
+ * @return the number of bits available in the bitstream.
+ */
+static inline int put_bits_left(PutBitContext* s)
+{
+    return (s->buf_end - s->buf_ptr) * 8 - 32 + s->bit_left;
+}
+
+/**
  * Pad the end of the output stream with zeros.
  */
 static inline void flush_put_bits(PutBitContext *s)
diff --git a/libavcodec/smacker.c b/libavcodec/smacker.c
index 3928d8f..e9192ff 100644
--- a/libavcodec/smacker.c
+++ b/libavcodec/smacker.c
@@ -252,7 +252,7 @@ static int smacker_decode_header_tree(SmackVContext *smk, GetBitContext *gb, int
     ctx.recode2 = tmp2.values;
     ctx.last = last;
 
-    huff.length = ((size + 3) >> 2) + 3;
+    huff.length = ((size + 3) >> 2) + 4;
     huff.maxlength = 0;
     huff.current = 0;
     huff.values = av_mallocz(huff.length * sizeof(int));
@@ -648,7 +648,16 @@ static int smka_decode_frame(AVCodecContext *avctx, void *data,
         h[i].lengths = av_mallocz(256 * sizeof(int));
         h[i].values = av_mallocz(256 * sizeof(int));
         skip_bits1(&gb);
-        smacker_decode_tree(&gb, &h[i], 0, 0);
+        if (smacker_decode_tree(&gb, &h[i], 0, 0) < 0) {
+            for (; i >= 0; i--) {
+                if (vlc[i].table)
+                    ff_free_vlc(&vlc[i]);
+                av_free(h[i].bits);
+                av_free(h[i].lengths);
+                av_free(h[i].values);
+            }
+            return AVERROR_INVALIDDATA;
+        }
         skip_bits1(&gb);
         if(h[i].current > 1) {
             res = init_vlc(&vlc[i], SMKTREE_BITS, h[i].length,
diff --git a/libavcodec/tiff.c b/libavcodec/tiff.c
index a0db1f1..8a1db12 100644
--- a/libavcodec/tiff.c
+++ b/libavcodec/tiff.c
@@ -186,10 +186,13 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t* dst, int stride, const uin
             break;
         case TIFF_PACKBITS:
             for(pixels = 0; pixels < width;){
+                if (ssrc + size - src < 2)
+                    return AVERROR_INVALIDDATA;
                 code = (int8_t)*src++;
                 if(code >= 0){
                     code++;
-                    if(pixels + code > width){
+                    if (pixels + code > width ||
+                        ssrc + size - src < code) {
                         av_log(s->avctx, AV_LOG_ERROR, "Copy went out of bounds\n");
                         return -1;
                     }
diff --git a/libavcodec/vmdav.c b/libavcodec/vmdav.c
index 570c362..4659971 100644
--- a/libavcodec/vmdav.c
+++ b/libavcodec/vmdav.c
@@ -45,6 +45,7 @@
 
 #include "libavutil/intreadwrite.h"
 #include "avcodec.h"
+#include "bytestream.h"
 
 #define VMD_HEADER_SIZE 0x330
 #define PALETTE_COUNT 256
@@ -75,8 +76,6 @@ typedef struct VmdVideoContext {
 static void lz_unpack(const unsigned char *src, int src_len,
                       unsigned char *dest, int dest_len)
 {
-    const unsigned char *s;
-    unsigned int s_len;
     unsigned char *d;
     unsigned char *d_end;
     unsigned char queue[QUEUE_SIZE];
@@ -87,18 +86,17 @@ static void lz_unpack(const unsigned char *src, int src_len,
     unsigned int speclen;
     unsigned char tag;
     unsigned int i, j;
+    GetByteContext gb;
 
-    s = src;
-    s_len = src_len;
+    bytestream2_init(&gb, src, src_len);
     d = dest;
     d_end = d + dest_len;
-    dataleft = AV_RL32(s);
-    s += 4; s_len -= 4;
+    dataleft = bytestream2_get_le32(&gb);
     memset(queue, 0x20, QUEUE_SIZE);
-    if (s_len < 4)
+    if (bytestream2_get_bytes_left(&gb) < 4)
         return;
-    if (AV_RL32(s) == 0x56781234) {
-        s += 4; s_len -= 4;
+    if (bytestream2_peek_le32(&gb) == 0x56781234) {
+        bytestream2_get_le32(&gb);
         qpos = 0x111;
         speclen = 0xF + 3;
     } else {
@@ -106,40 +104,32 @@ static void lz_unpack(const unsigned char *src, int src_len,
         speclen = 100;  /* no speclen */
     }
 
-    while (dataleft > 0 && s_len > 0) {
-        tag = *s++; s_len--;
+    while (dataleft > 0 && bytestream2_get_bytes_left(&gb) > 0) {
+        tag = bytestream2_get_byteu(&gb);
         if ((tag == 0xFF) && (dataleft > 8)) {
-            if (d + 8 > d_end || s_len < 8)
+            if (d + 8 > d_end || bytestream2_get_bytes_left(&gb) < 8)
                 return;
             for (i = 0; i < 8; i++) {
-                queue[qpos++] = *d++ = *s++;
+                queue[qpos++] = *d++ = bytestream2_get_byteu(&gb);
                 qpos &= QUEUE_MASK;
             }
-            s_len -= 8;
             dataleft -= 8;
         } else {
             for (i = 0; i < 8; i++) {
                 if (dataleft == 0)
                     break;
                 if (tag & 0x01) {
-                    if (d + 1 > d_end || s_len < 1)
+                    if (d + 1 > d_end || bytestream2_get_bytes_left(&gb) < 1)
                         return;
-                    queue[qpos++] = *d++ = *s++;
+                    queue[qpos++] = *d++ = bytestream2_get_byte(&gb);
                     qpos &= QUEUE_MASK;
                     dataleft--;
-                    s_len--;
                 } else {
-                    if (s_len < 2)
-                        return;
-                    chainofs = *s++;
-                    chainofs |= ((*s & 0xF0) << 4);
-                    chainlen = (*s++ & 0x0F) + 3;
-                    s_len -= 2;
+                    chainofs = bytestream2_get_byte(&gb);
+                    chainofs |= ((bytestream2_peek_byte(&gb) & 0xF0) << 4);
+                    chainlen = (bytestream2_get_byte(&gb) & 0x0F) + 3;
                     if (chainlen == speclen) {
-                        if (s_len < 1)
-                            return;
-                        chainlen = *s++ + 0xF + 3;
-                        s_len--;
+                        chainlen = bytestream2_get_byte(&gb) + 0xF + 3;
                     }
                     if (d + chainlen > d_end)
                         return;
@@ -159,49 +149,44 @@ static void lz_unpack(const unsigned char *src, int src_len,
 static int rle_unpack(const unsigned char *src, unsigned char *dest,
     int src_count, int src_size, int dest_len)
 {
-    const unsigned char *ps;
     unsigned char *pd;
     int i, l;
     unsigned char *dest_end = dest + dest_len;
+    GetByteContext gb;
 
-    ps = src;
+    bytestream2_init(&gb, src, src_size);
     pd = dest;
     if (src_count & 1) {
-        if (src_size < 1)
+        if (bytestream2_get_bytes_left(&gb) < 1)
             return 0;
-        *pd++ = *ps++;
-        src_size--;
+        *pd++ = bytestream2_get_byteu(&gb);
     }
 
     src_count >>= 1;
     i = 0;
     do {
-        if (src_size < 1)
+        if (bytestream2_get_bytes_left(&gb) < 1)
             break;
-        l = *ps++;
-        src_size--;
+        l = bytestream2_get_byteu(&gb);
         if (l & 0x80) {
             l = (l & 0x7F) * 2;
-            if (pd + l > dest_end || src_size < l)
-                return ps - src;
-            memcpy(pd, ps, l);
-            ps += l;
-            src_size -= l;
+            if (pd + l > dest_end || bytestream2_get_bytes_left(&gb) < l)
+                return bytestream2_tell(&gb);
+            bytestream2_get_buffer(&gb, pd, l);
             pd += l;
         } else {
-            if (pd + i > dest_end || src_size < 2)
-                return ps - src;
+            if (pd + i > dest_end || bytestream2_get_bytes_left(&gb) < 2)
+                return bytestream2_tell(&gb);
             for (i = 0; i < l; i++) {
-                *pd++ = ps[0];
-                *pd++ = ps[1];
+                *pd++ = bytestream2_get_byteu(&gb);
+                *pd++ = bytestream2_get_byteu(&gb);
             }
-            ps += 2;
-            src_size -= 2;
+            bytestream2_skip(&gb, 2);
         }
         i += l;
     } while (i < src_count);
 
-    return ps - src;
+    return bytestream2_tell(&gb);
 }
 
 static void vmd_decode(VmdVideoContext *s)
@@ -210,11 +195,8 @@ static void vmd_decode(VmdVideoContext *s)
     unsigned int *palette32;
     unsigned char r, g, b;
 
-    /* point to the start of the encoded data */
-    const unsigned char *p = s->buf + 16;
+    GetByteContext gb;
 
-    const unsigned char *pb;
-    unsigned int pb_size;
     unsigned char meth;
     unsigned char *dp;   /* pointer to current frame */
     unsigned char *pp;   /* pointer to previous frame */
@@ -259,30 +241,31 @@ static void vmd_decode(VmdVideoContext *s)
     }
 
     /* check if there is a new palette */
+    bytestream2_init(&gb, s->buf + 16, s->size - 16);
     if (s->buf[15] & 0x02) {
-        p += 2;
+        bytestream2_skip(&gb, 2);
         palette32 = (unsigned int *)s->palette;
-        for (i = 0; i < PALETTE_COUNT; i++) {
-            r = *p++ * 4;
-            g = *p++ * 4;
-            b = *p++ * 4;
-            palette32[i] = (r << 16) | (g << 8) | (b);
+        if (bytestream2_get_bytes_left(&gb) >= PALETTE_COUNT * 3) {
+            for (i = 0; i < PALETTE_COUNT; i++) {
+                r = bytestream2_get_byteu(&gb) * 4;
+                g = bytestream2_get_byteu(&gb) * 4;
+                b = bytestream2_get_byteu(&gb) * 4;
+                palette32[i] = (r << 16) | (g << 8) | (b);
+            }
         }
         s->size -= (256 * 3 + 2);
     }
     if (s->size > 0) {
         /* originally UnpackFrame in VAG's code */
-        pb = p;
-        pb_size = s->buf + s->size - pb;
-        if (pb_size < 1)
+        bytestream2_init(&gb, gb.buffer, s->buf + s->size - gb.buffer);
+        if (bytestream2_get_bytes_left(&gb) < 1)
             return;
-        meth = *pb++; pb_size--;
+        meth = bytestream2_get_byteu(&gb);
         if (meth & 0x80) {
-            lz_unpack(pb, pb_size,
+            lz_unpack(gb.buffer, bytestream2_get_bytes_left(&gb),
                       s->unpack_buffer, s->unpack_buffer_size);
             meth &= 0x7F;
-            pb = s->unpack_buffer;
-            pb_size = s->unpack_buffer_size;
+            bytestream2_init(&gb, s->unpack_buffer, s->unpack_buffer_size);
         }
 
         dp = &s->frame.data[0][frame_y * s->frame.linesize[0] + frame_x];
@@ -292,17 +275,12 @@ static void vmd_decode(VmdVideoContext *s)
             for (i = 0; i < frame_height; i++) {
                 ofs = 0;
                 do {
-                    if (pb_size < 1)
-                        return;
-                    len = *pb++;
-                    pb_size--;
+                    len = bytestream2_get_byte(&gb);
                     if (len & 0x80) {
                         len = (len & 0x7F) + 1;
-                        if (ofs + len > frame_width || pb_size < len)
+                        if (ofs + len > frame_width || bytestream2_get_bytes_left(&gb) < len)
                             return;
-                        memcpy(&dp[ofs], pb, len);
-                        pb += len;
-                        pb_size -= len;
+                        bytestream2_get_buffer(&gb, &dp[ofs], len);
                         ofs += len;
                     } else {
                         /* interframe pixel copy */
@@ -324,11 +302,7 @@ static void vmd_decode(VmdVideoContext *s)
 
         case 2:
             for (i = 0; i < frame_height; i++) {
-                if (pb_size < frame_width)
-                    return;
-                memcpy(dp, pb, frame_width);
-                pb += frame_width;
-                pb_size -= frame_width;
+                bytestream2_get_buffer(&gb, dp, frame_width);
                 dp += s->frame.linesize[0];
                 pp += s->prev_frame.linesize[0];
             }
@@ -338,24 +312,16 @@ static void vmd_decode(VmdVideoContext *s)
             for (i = 0; i < frame_height; i++) {
                 ofs = 0;
                 do {
-                    if (pb_size < 1)
-                        return;
-                    len = *pb++;
-                    pb_size--;
+                    len = bytestream2_get_byte(&gb);
                     if (len & 0x80) {
                         len = (len & 0x7F) + 1;
-                        if (pb_size < 1)
-                            return;
-                        if (*pb++ == 0xFF)
-                            len = rle_unpack(pb, &dp[ofs], len, pb_size, frame_width - ofs);
-                        else {
-                            if (pb_size < len)
-                                return;
-                            memcpy(&dp[ofs], pb, len);
-                        }
-                        pb += len;
-                        pb_size -= 1 + len;
-                        ofs += len;
+                        if (bytestream2_get_byte(&gb) == 0xFF)
+                            len = rle_unpack(gb.buffer, &dp[ofs],
+                                             len, bytestream2_get_bytes_left(&gb),
+                                             frame_width - ofs);
+                        else
+                            bytestream2_get_buffer(&gb, &dp[ofs], len);
+                        bytestream2_skip(&gb, len);
                     } else {
                         /* interframe pixel copy */
                         if (ofs + len + 1 > frame_width || !s->prev_frame.data[0])
diff --git a/libavcodec/wavpack.c b/libavcodec/wavpack.c
index 1098873..31377e7 100644
--- a/libavcodec/wavpack.c
+++ b/libavcodec/wavpack.c
@@ -773,13 +773,13 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
 
     if (block_no >= wc->fdec_num && wv_alloc_frame_context(wc) < 0) {
         av_log(avctx, AV_LOG_ERROR, "Error creating frame decode context\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
 
     s = wc->fdec[block_no];
     if (!s) {
         av_log(avctx, AV_LOG_ERROR, "Context for block %d is not present\n", block_no);
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
 
     memset(s->decorr, 0, MAX_TERMS * sizeof(Decorr));
@@ -790,6 +790,9 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
 
     if (!wc->mkv_mode) {
         s->samples = AV_RL32(buf); buf += 4;
+        if (s->samples != wc->samples)
+            return AVERROR_INVALIDDATA;
+
         if (!s->samples) {
             *got_frame_ptr = 0;
             return 0;
@@ -1018,7 +1021,7 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
         case WP_ID_CHANINFO:
             if (size <= 1) {
                 av_log(avctx, AV_LOG_ERROR, "Insufficient channel information\n");
-                return -1;
+                return AVERROR_INVALIDDATA;
             }
             chan = *buf++;
             switch (size - 2) {
@@ -1037,10 +1040,11 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
                 chmask = avctx->channel_layout;
             }
             if (chan != avctx->channels) {
-                av_log(avctx, AV_LOG_ERROR, "Block reports total %d channels, "
-                       "decoder believes it's %d channels\n", chan,
-                       avctx->channels);
-                return -1;
+                av_log(avctx, AV_LOG_ERROR,
+                       "Block reports total %d channels, "
+                       "decoder believes it's %d channels\n",
+                       chan, avctx->channels);
+                return AVERROR_INVALIDDATA;
             }
             if (!avctx->channel_layout)
                 avctx->channel_layout = chmask;
@@ -1055,31 +1059,31 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
 
     if (!got_terms) {
         av_log(avctx, AV_LOG_ERROR, "No block with decorrelation terms\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (!got_weights) {
         av_log(avctx, AV_LOG_ERROR, "No block with decorrelation weights\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (!got_samples) {
         av_log(avctx, AV_LOG_ERROR, "No block with decorrelation samples\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (!got_entropy) {
         av_log(avctx, AV_LOG_ERROR, "No block with entropy info\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (s->hybrid && !got_hybrid) {
         av_log(avctx, AV_LOG_ERROR, "Hybrid config not found\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (!got_bs) {
         av_log(avctx, AV_LOG_ERROR, "Packed samples not found\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (!got_float && avctx->sample_fmt == AV_SAMPLE_FMT_FLT) {
         av_log(avctx, AV_LOG_ERROR, "Float information not found\n");
-        return -1;
+        return AVERROR_INVALIDDATA;
     }
     if (s->got_extra_bits && avctx->sample_fmt != AV_SAMPLE_FMT_FLT) {
         const int size   = get_bits_left(&s->gb_extra_bits);
@@ -1099,7 +1103,7 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
             samplecount = wv_unpack_stereo(s, &s->gb, samples, AV_SAMPLE_FMT_FLT);
 
         if (samplecount < 0)
-            return -1;
+            return samplecount;
 
         samplecount >>= 1;
     } else {
@@ -1113,7 +1117,7 @@ static int wavpack_decode_block(AVCodecContext *avctx, int block_no,
             samplecount = wv_unpack_mono(s, &s->gb, samples, AV_SAMPLE_FMT_FLT);
 
         if (samplecount < 0)
-            return -1;
+            return samplecount;
 
         if (s->stereo && avctx->sample_fmt == AV_SAMPLE_FMT_S16) {
             int16_t *dst = (int16_t*)samples + 1;
@@ -1168,6 +1172,9 @@ static int wavpack_decode_frame(AVCodecContext *avctx, void *data,
     int frame_size, ret, frame_flags;
     int samplecount = 0;
 
+    if (avpkt->size < 12 + s->multichannel * 4)
+        return AVERROR_INVALIDDATA;
+
     s->block     = 0;
     s->ch_offset = 0;
 
@@ -1187,7 +1194,7 @@ static int wavpack_decode_frame(AVCodecContext *avctx, void *data,
     if (s->samples <= 0) {
         av_log(avctx, AV_LOG_ERROR, "Invalid number of samples: %d\n",
                s->samples);
-        return AVERROR(EINVAL);
+        return AVERROR_INVALIDDATA;
     }
 
     if (frame_flags & 0x80) {
@@ -1221,13 +1228,13 @@ static int wavpack_decode_frame(AVCodecContext *avctx, void *data,
             av_log(avctx, AV_LOG_ERROR, "Block %d has invalid size (size %d "
                    "vs. %d bytes left)\n", s->block, frame_size, buf_size);
             wavpack_decode_flush(avctx);
-            return -1;
+            return AVERROR_INVALIDDATA;
         }
         if ((samplecount = wavpack_decode_block(avctx, s->block,
                                                 s->frame.data[0], got_frame_ptr,
                                                 buf, frame_size)) < 0) {
             wavpack_decode_flush(avctx);
-            return -1;
+            return samplecount;
         }
         s->block++;
         buf += frame_size; buf_size -= frame_size;
diff --git a/libavcodec/wmaprodec.c b/libavcodec/wmaprodec.c
index 1b7797c..902c4e3 100644
--- a/libavcodec/wmaprodec.c
+++ b/libavcodec/wmaprodec.c
@@ -106,6 +106,7 @@
 
 #define WMAPRO_BLOCK_MIN_BITS  6                                           ///< log2 of min block size
 #define WMAPRO_BLOCK_MAX_BITS 12                                           ///< log2 of max block size
+#define WMAPRO_BLOCK_MIN_SIZE (1 << WMAPRO_BLOCK_MIN_BITS)                 ///< minimum block size
 #define WMAPRO_BLOCK_MAX_SIZE (1 << WMAPRO_BLOCK_MAX_BITS)                 ///< maximum block size
 #define WMAPRO_BLOCK_SIZES    (WMAPRO_BLOCK_MAX_BITS - WMAPRO_BLOCK_MIN_BITS + 1) ///< possible block sizes
 
@@ -335,6 +336,12 @@ static av_cold int decode_init(AVCodecContext *avctx)
         return AVERROR_INVALIDDATA;
     }
 
+    if (s->min_samples_per_subframe < WMAPRO_BLOCK_MIN_SIZE) {
+        av_log(avctx, AV_LOG_ERROR, "Invalid minimum block size %i\n",
+               s->max_num_subframes);
+        return AVERROR_INVALIDDATA;
+    }
+
     if (s->avctx->sample_rate <= 0) {
         av_log(avctx, AV_LOG_ERROR, "invalid sample rate\n");
         return AVERROR_INVALIDDATA;
@@ -428,7 +435,8 @@ static av_cold int decode_init(AVCodecContext *avctx)
             for (x = 0; x < num_possible_block_sizes; x++) {
                 int v = 0;
                 while (s->sfb_offsets[x][v + 1] << x < offset)
-                    ++v;
+                    if (++v >= MAX_BANDS)
+                        return AVERROR_INVALIDDATA;
                 s->sf_offsets[i][x][b] = v;
             }
         }
@@ -720,6 +728,7 @@ static int decode_channel_transform(WMAProDecodeCtx* s)
                     if (get_bits1(&s->gb)) {
                         av_log_ask_for_sample(s->avctx,
                                               "unsupported channel transform type\n");
+                        return AVERROR_PATCHWELCOME;
                     }
                 } else {
                     chgroup->transform = 1;
@@ -1122,11 +1131,12 @@ static int decode_subframe(WMAProDecodeCtx *s)
     cur_subwoofer_cutoff = s->subwoofer_cutoffs[s->table_idx];
 
     /** configure the decoder for the current subframe */
+    offset += s->samples_per_frame >> 1;
+
     for (i = 0; i < s->channels_for_cur_subframe; i++) {
         int c = s->channel_indexes_for_cur_subframe[i];
 
-        s->channel[c].coeffs = &s->channel[c].out[(s->samples_per_frame >> 1)
-                                                  + offset];
+        s->channel[c].coeffs = &s->channel[c].out[offset];
     }
 
     s->subframe_len = subframe_len;
@@ -1177,7 +1187,7 @@ static int decode_subframe(WMAProDecodeCtx *s)
             for (i = 0; i < s->channels_for_cur_subframe; i++) {
                 int c = s->channel_indexes_for_cur_subframe[i];
                 int num_vec_coeffs = get_bits(&s->gb, num_bits) << 2;
-                if (num_vec_coeffs > WMAPRO_BLOCK_MAX_SIZE) {
+                if (num_vec_coeffs + offset > FF_ARRAY_ELEMS(s->channel[c].out)) {
                     av_log(s->avctx, AV_LOG_ERROR, "num_vec_coeffs %d is too large\n", num_vec_coeffs);
                     return AVERROR_INVALIDDATA;
                 }
@@ -1466,6 +1476,14 @@ static void save_bits(WMAProDecodeCtx *s, GetBitContext* gb, int len,
         return;
     }
 
+    if (len > put_bits_left(&s->pb)) {
+        av_log(s->avctx, AV_LOG_ERROR,
+               "Cannot append %d bits, only %d bits available.\n",
+               len, put_bits_left(&s->pb));
+        s->packet_loss = 1;
+        return;
+    }
+
     s->num_saved_bits += len;
     if (!append) {
         avpriv_copy_bits(&s->pb, gb->buffer + (get_bits_count(gb) >> 3),
diff --git a/libavformat/apetag.c b/libavformat/apetag.c
index 257ed48..2390bfa 100644
--- a/libavformat/apetag.c
+++ b/libavformat/apetag.c
@@ -65,7 +65,7 @@ static int ape_tag_read_field(AVFormatContext *s)
 void ff_ape_parse_tag(AVFormatContext *s)
 {
     AVIOContext *pb = s->pb;
-    int file_size = avio_size(pb);
+    int64_t file_size = avio_size(pb);
     uint32_t val, fields, tag_bytes;
     uint8_t buf[8];
     int i;
diff --git a/libavformat/smacker.c b/libavformat/smacker.c
index 6df8b8b..d6bb213 100644
--- a/libavformat/smacker.c
+++ b/libavformat/smacker.c
@@ -203,7 +203,8 @@ static int smacker_read_header(AVFormatContext *s, AVFormatParameters *ap)
 
 
     /* load trees to extradata, they will be unpacked by decoder */
-    st->codec->extradata = av_malloc(smk->treesize + 16);
+    st->codec->extradata = av_mallocz(smk->treesize + 16 +
+                                      FF_INPUT_BUFFER_PADDING_SIZE);
     st->codec->extradata_size = smk->treesize + 16;
     if(!st->codec->extradata){
         av_log(s, AV_LOG_ERROR, "Cannot allocate %i bytes of extradata\n", smk->treesize + 16);
@@ -296,10 +297,14 @@ static int smacker_read_packet(AVFormatContext *s, AVPacket *pkt)
         /* if audio chunks are present, put them to stack and retrieve later */
         for(i = 0; i < 7; i++) {
             if(flags & 1) {
-                int size;
+                uint32_t size;
                 uint8_t *tmpbuf;
 
                 size = avio_rl32(s->pb) - 4;
+                if (!size || size > frame_size) {
+                    av_log(s, AV_LOG_ERROR, "Invalid audio part size\n");
+                    return AVERROR_INVALIDDATA;
+                }
                 frame_size -= size;
                 frame_size -= 4;
                 smk->curstream++;

-- 
Libav/FFmpeg packaging



More information about the pkg-multimedia-commits mailing list