Merge remote-tracking branch 'qatar/release/0.8' into release/0.10

* qatar/release/0.8:
  swfdec: do better validation of tag length
  Changelog for 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
  indeo: check for reference when inheriting mvs
  indeo: use proper error code
  indeo: Properly forward the error codes
  wmapro: error out on impossible scale factor offsets
  wmapro: check the min_samples_per_subframe
  wmapro: return early on unsupported condition
  wmapro: check num_vec_coeffs against the actual available buffer

Conflicts:
	Changelog
	libavformat/swfdec.c

Merged-by: Michael Niedermayer <michaelni@gmx.at>
This commit is contained in:
Michael Niedermayer 2013-07-29 04:05:13 +02:00
commit 62d9d4d9d4
6 changed files with 102 additions and 50 deletions

View File

@ -5,7 +5,34 @@ version next:
version 0.10.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
- avfiltergraph: check for sws opts being non-NULL before using them
- bmv: check for len being valid in bmv_decode_frame()
- dfa: check for invalid access in decode_wdlt()

View File

@ -342,25 +342,33 @@ 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;
s->size_in_bits_plus8 = bit_size + 8;
s->buffer_end = buffer + buffer_size;
s->index = 0;
return ret;
}
static inline void align_get_bits(GetBitContext *s)

View File

@ -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])
@ -345,8 +348,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;
@ -435,7 +437,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];
@ -458,7 +460,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) {
@ -516,8 +518,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 "
@ -739,8 +740,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;
}
@ -788,14 +797,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);
@ -806,10 +815,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;
}
}
}

View File

@ -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;
@ -403,30 +403,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"),

View File

@ -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;
}

View File

@ -91,6 +91,10 @@ static int swf_read_packet(AVFormatContext *s, AVPacket *pkt)
tag = get_swf_tag(pb, &len);
if (tag < 0)
return tag;
if (len < 0) {
av_log(s, AV_LOG_ERROR, "invalid tag length: %d\n", len);
return AVERROR_INVALIDDATA;
}
if (tag == TAG_VIDEOSTREAM) {
int ch_id = avio_rl16(pb);
len -= 2;
@ -150,7 +154,10 @@ static int swf_read_packet(AVFormatContext *s, AVPacket *pkt)
st = s->streams[i];
if (st->codec->codec_type == AVMEDIA_TYPE_VIDEO && st->id == ch_id) {
frame = avio_rl16(pb);
if ((res = av_get_packet(pb, pkt, len-2)) < 0)
len -= 2;
if (len <= 0)
goto skip;
if ((res = av_get_packet(pb, pkt, len)) < 0)
return res;
pkt->pos = pos;
pkt->pts = frame;
@ -164,9 +171,14 @@ static int swf_read_packet(AVFormatContext *s, AVPacket *pkt)
if (st->codec->codec_type == AVMEDIA_TYPE_AUDIO && st->id == -1) {
if (st->codec->codec_id == CODEC_ID_MP3) {
avio_skip(pb, 4);
if ((res = av_get_packet(pb, pkt, len-4)) < 0)
len -= 4;
if (len <= 0)
goto skip;
if ((res = av_get_packet(pb, pkt, len)) < 0)
return res;
} else { // ADPCM, PCM
if (len <= 0)
goto skip;
if ((res = av_get_packet(pb, pkt, len)) < 0)
return res;
}
@ -193,7 +205,10 @@ static int swf_read_packet(AVFormatContext *s, AVPacket *pkt)
st = vst;
}
avio_rl16(pb); /* BITMAP_ID */
if ((res = av_new_packet(pkt, len-2)) < 0)
len -= 2;
if (len < 4)
goto skip;
if ((res = av_new_packet(pkt, len)) < 0)
return res;
avio_read(pb, pkt->data, 4);
if (AV_RB32(pkt->data) == 0xffd8ffd9 ||
@ -210,6 +225,7 @@ static int swf_read_packet(AVFormatContext *s, AVPacket *pkt)
return pkt->size;
}
skip:
len = FFMAX(0, len);
avio_skip(pb, len);
}
}