[FFmpeg-soc] [soc]: r379 - rv40/rv40.c
kostya
subversion at mplayerhq.hu
Thu Jul 12 07:56:15 CEST 2007
Author: kostya
Date: Thu Jul 12 07:56:15 2007
New Revision: 379
Log:
Save history for intra_types. Now bitstream is parsed correctly
Modified:
rv40/rv40.c
Modified: rv40/rv40.c
==============================================================================
--- rv40/rv40.c (original)
+++ rv40/rv40.c Thu Jul 12 07:56:15 2007
@@ -38,7 +38,9 @@
typedef struct RV40DecContext{
MpegEncContext s;
int mb_bits; ///< bits needed to read MB offet in slice header
- int intra_types[16]; ///< block types
+ int *intra_types_hist; ///< old block types, used for prediction
+ int *intra_types; ///< block types
+ int intra_types_stride; ///< stride for block types data
int block_start; ///< start of slice in blocks
int ptype; ///< picture type
int quant; ///< quantizer
@@ -469,11 +471,8 @@ static int rv40_parse_slice_header(RV40D
/**
* Decode 4x4 intra types array
- *
- * This function expects old array passed as reference, filled with -1 is absent
- * XXX: Corner cases may be not handled
*/
-static int rv40_decode_intra_types(RV40DecContext *r, GetBitContext *gb, int dst[16])
+static int rv40_decode_intra_types(RV40DecContext *r, GetBitContext *gb, int *dst)
{
MpegEncContext *s = &r->s;
int i, j, k, v;
@@ -481,7 +480,7 @@ static int rv40_decode_intra_types(RV40D
int pattern;
int *ptr;
- for(i = 0; i < 4; i++){
+ for(i = 0; i < 4; i++, dst += r->intra_types_stride){
if(!i && s->first_slice_line){
pattern = get_vlc2(gb, aic_top_vlc.table, AIC_TOP_BITS, 1);
dst[0] = (pattern >> 2) & 2;
@@ -490,7 +489,7 @@ static int rv40_decode_intra_types(RV40D
dst[3] = (pattern << 1) & 2;
continue;
}
- ptr = dst + i*4;
+ ptr = dst;
for(j = 0; j < 4; j++){
/* Coefficients are read using VLC chosen by prediction pattern
* First one (used for retrieving a pair of coefficients) is
@@ -498,9 +497,9 @@ static int rv40_decode_intra_types(RV40D
* Second one (used for retrieving only one coefficient) is
* top + 10 * left
*/
- A = i ? ptr[-3] : dst[j+1]; // it won't be used for the last coefficient in a row
- B = i ? ptr[-4] : dst[j];
- C = j ? ptr[-1] : ptr[3];
+ A = ptr[-r->intra_types_stride + 1]; // it won't be used for the last coefficient in a row
+ B = ptr[-r->intra_types_stride];
+ C = ptr[-1];
pattern = A + (B << 4) + (C << 8);
for(k = 0; k < MODE2_PATTERNS_NUM; k++)
if(pattern == rv40_aic_table_index[k])
@@ -533,7 +532,7 @@ static int rv40_decode_intra_types(RV40D
return 0;
}
-static int rv40_decode_macroblock(RV40DecContext *r)
+static int rv40_decode_macroblock(RV40DecContext *r, int *intra_types)
{
MpegEncContext *s = &r->s;
GetBitContext *gb = &s->gb;
@@ -558,7 +557,7 @@ static int rv40_decode_macroblock(RV40De
break;
}
if(!is16){
- rv40_decode_intra_types(r, gb, r->intra_types);
+ rv40_decode_intra_types(r, gb, intra_types);
chroma_vlc = 0;
luma_vlc = 1;
}else{
@@ -566,7 +565,7 @@ static int rv40_decode_macroblock(RV40De
if(x==3)
av_log(NULL,0,"Got type 3 for Intra16x16\n");
for(i = 0; i < 16; i++)
- r->intra_types[i] = x;
+ intra_types[(i & 3) + (i>>2) * r->intra_types_stride] = x;
chroma_vlc = 0;
luma_vlc = 2;
}
@@ -623,7 +622,7 @@ static int rv40_decode_slice(RV40DecCont
s->mb_x = r->block_start % s->mb_width;
s->mb_y = r->block_start / s->mb_width;
}
- memset(r->intra_types, -1, 16 * sizeof(int));
+ memset(r->intra_types, -1, r->intra_types_stride * 4 * 2 * sizeof(int));
s->first_slice_line = 1;
s->resync_mb_x= s->mb_x;
ff_init_block_index(s);
@@ -632,12 +631,15 @@ static int rv40_decode_slice(RV40DecCont
ff_update_block_index(s);
s->dsp.clear_blocks(s->block[0]);
- rv40_decode_macroblock(r);
+ rv40_decode_macroblock(r, r->intra_types + (s->mb_x + 1) * 4);
ff_draw_horiz_band(s, s->mb_y * 16, 16);
if (++s->mb_x == s->mb_width) {
s->mb_x = 0;
s->mb_y++;
ff_init_block_index(s);
+
+ memmove(r->intra_types_hist, r->intra_types, r->intra_types_stride * 4 * sizeof(int));
+ memset(r->intra_types, -1, r->intra_types_stride * 4 * sizeof(int));
}
if(s->mb_x == s->resync_mb_x)
s->first_slice_line=0;
@@ -678,6 +680,10 @@ static int rv40_decode_init(AVCodecConte
if (MPV_common_init(s) < 0)
return -1;
+ r->intra_types_stride = (s->mb_width + 1) * 4;
+ r->intra_types_hist = av_malloc(r->intra_types_stride * 4 * 2 * sizeof(int));
+ r->intra_types = r->intra_types_hist + r->intra_types_stride * 4;
+
if(!tables_done){
rv40_init_tables();
tables_done = 1;
@@ -742,6 +748,10 @@ static int rv40_decode_end(AVCodecContex
RV40DecContext *r = avctx->priv_data;
MPV_common_end(&r->s);
+
+ av_freep(&r->intra_types_hist);
+ r->intra_types = NULL;
+
return 0;
}
More information about the FFmpeg-soc
mailing list