Browse Source

yop: simplify/sanitize the decoding loop

Do not overwrite linesize set by get_buffer().

The last frame in the FATE test is not decoded anymore, since the file
is cut and a part of it is missing.
tags/n1.1
Anton Khirnov 12 years ago
parent
commit
c6303f8d70
2 changed files with 19 additions and 34 deletions
  1. +19
    -33
      libavcodec/yop.c
  2. +0
    -1
      tests/ref/fate/yop

+ 19
- 33
libavcodec/yop.c View File

@@ -36,7 +36,6 @@ typedef struct YopDecContext {
int num_pal_colors; int num_pal_colors;
int first_color[2]; int first_color[2];
int frame_data_length; int frame_data_length;
int row_pos;


uint8_t *low_nibble; uint8_t *low_nibble;
uint8_t *srcptr; uint8_t *srcptr;
@@ -173,27 +172,12 @@ static uint8_t yop_get_next_nibble(YopDecContext *s)
return ret; return ret;
} }


/**
* Take s->dstptr to the next macroblock in sequence.
*/
static void yop_next_macroblock(YopDecContext *s)
{
// If we are advancing to the next row of macroblocks
if (s->row_pos == s->frame.linesize[0] - 2) {
s->dstptr += s->frame.linesize[0];
s->row_pos = 0;
}else {
s->row_pos += 2;
}
s->dstptr += 2;
}

static int yop_decode_frame(AVCodecContext *avctx, void *data, int *got_frame, static int yop_decode_frame(AVCodecContext *avctx, void *data, int *got_frame,
AVPacket *avpkt) AVPacket *avpkt)
{ {
YopDecContext *s = avctx->priv_data; YopDecContext *s = avctx->priv_data;
int tag, firstcolor, is_odd_frame; int tag, firstcolor, is_odd_frame;
int ret, i;
int ret, i, x, y;
uint32_t *palette; uint32_t *palette;


if (s->frame.data[0]) if (s->frame.data[0])
@@ -205,12 +189,9 @@ static int yop_decode_frame(AVCodecContext *avctx, void *data, int *got_frame,
return ret; return ret;
} }


s->frame.linesize[0] = avctx->width;

s->dstbuf = s->frame.data[0]; s->dstbuf = s->frame.data[0];
s->dstptr = s->frame.data[0]; s->dstptr = s->frame.data[0];
s->srcptr = avpkt->data + 4; s->srcptr = avpkt->data + 4;
s->row_pos = 0;
s->low_nibble = NULL; s->low_nibble = NULL;


is_odd_frame = avpkt->data[0]; is_odd_frame = avpkt->data[0];
@@ -224,23 +205,28 @@ static int yop_decode_frame(AVCodecContext *avctx, void *data, int *got_frame,


s->frame.palette_has_changed = 1; s->frame.palette_has_changed = 1;


while (s->dstptr - s->dstbuf <
avctx->width * avctx->height &&
s->srcptr - avpkt->data < avpkt->size) {

tag = yop_get_next_nibble(s);
for (y = 0; y < avctx->height; y += 2) {
for (x = 0; x < avctx->width; x += 2) {
if (s->srcptr - avpkt->data >= avpkt->size) {
av_log(avctx, AV_LOG_ERROR, "Packet too small.\n");
return AVERROR_INVALIDDATA;
}


if (tag != 0xf) {
yop_paint_block(s, tag);
}else {
tag = yop_get_next_nibble(s); tag = yop_get_next_nibble(s);
ret = yop_copy_previous_block(s, tag);
if (ret < 0) {
avctx->release_buffer(avctx, &s->frame);
return ret;

if (tag != 0xf) {
yop_paint_block(s, tag);
} else {
tag = yop_get_next_nibble(s);
ret = yop_copy_previous_block(s, tag);
if (ret < 0) {
avctx->release_buffer(avctx, &s->frame);
return ret;
}
} }
s->dstptr += 2;
} }
yop_next_macroblock(s);
s->dstptr += 2*s->frame.linesize[0] - x;
} }


*got_frame = 1; *got_frame = 1;


+ 0
- 1
tests/ref/fate/yop View File

@@ -5,4 +5,3 @@
0, 3, 3, 1, 302760, 0xc34b20bd 0, 3, 3, 1, 302760, 0xc34b20bd
0, 4, 4, 1, 302760, 0x461d29a1 0, 4, 4, 1, 302760, 0x461d29a1
0, 5, 5, 1, 302760, 0x45abca02 0, 5, 5, 1, 302760, 0x45abca02
0, 6, 6, 1, 302760, 0xb05448b9

Loading…
Cancel
Save