Commit a7137a04 authored by Michael Niedermayer's avatar Michael Niedermayer

mpeg4 dc prediction simplification

dc cliping fix

Originally committed as revision 3107 to svn://svn.ffmpeg.org/ffmpeg/trunk
parent 4c263142
...@@ -76,7 +76,7 @@ static void mpeg4_encode_visual_object_header(MpegEncContext * s); ...@@ -76,7 +76,7 @@ static void mpeg4_encode_visual_object_header(MpegEncContext * s);
static void mpeg4_encode_vol_header(MpegEncContext * s, int vo_number, int vol_number); static void mpeg4_encode_vol_header(MpegEncContext * s, int vo_number, int vol_number);
#endif //CONFIG_ENCODERS #endif //CONFIG_ENCODERS
static void mpeg4_decode_sprite_trajectory(MpegEncContext * s, GetBitContext *gb); static void mpeg4_decode_sprite_trajectory(MpegEncContext * s, GetBitContext *gb);
static inline int ff_mpeg4_pred_dc(MpegEncContext * s, int n, uint16_t **dc_val_ptr, int *dir_ptr); static inline int ff_mpeg4_pred_dc(MpegEncContext * s, int n, int level, int *dir_ptr, int encoding);
#ifdef CONFIG_ENCODERS #ifdef CONFIG_ENCODERS
static uint8_t uni_DCtab_lum_len[512]; static uint8_t uni_DCtab_lum_len[512];
...@@ -1073,15 +1073,7 @@ void mpeg4_encode_mb(MpegEncContext * s, ...@@ -1073,15 +1073,7 @@ void mpeg4_encode_mb(MpegEncContext * s,
int i; int i;
for(i=0; i<6; i++){ for(i=0; i<6; i++){
const int level= block[i][0]; dc_diff[i]= ff_mpeg4_pred_dc(s, i, block[i][0], &dir[i], 1);
uint16_t *dc_ptr;
dc_diff[i]= level - ff_mpeg4_pred_dc(s, i, &dc_ptr, &dir[i]);
if (i < 4) {
*dc_ptr = level * s->y_dc_scale;
} else {
*dc_ptr = level * s->c_dc_scale;
}
} }
if(s->flags & CODEC_FLAG_AC_PRED){ if(s->flags & CODEC_FLAG_AC_PRED){
...@@ -2382,14 +2374,14 @@ void ff_set_qscale(MpegEncContext * s, int qscale) ...@@ -2382,14 +2374,14 @@ void ff_set_qscale(MpegEncContext * s, int qscale)
/** /**
* predicts the dc. * predicts the dc.
* encoding quantized level -> quantized diff
* decoding quantized diff -> quantized level
* @param n block index (0-3 are luma, 4-5 are chroma) * @param n block index (0-3 are luma, 4-5 are chroma)
* @param dc_val_ptr a pointer to the dc_val entry for the current MB will be stored here
* @param dir_ptr pointer to an integer where the prediction direction will be stored * @param dir_ptr pointer to an integer where the prediction direction will be stored
* @return the quantized predicted dc
*/ */
static inline int ff_mpeg4_pred_dc(MpegEncContext * s, int n, uint16_t **dc_val_ptr, int *dir_ptr) static inline int ff_mpeg4_pred_dc(MpegEncContext * s, int n, int level, int *dir_ptr, int encoding)
{ {
int a, b, c, wrap, pred, scale; int a, b, c, wrap, pred, scale, ret;
uint16_t *dc_val; uint16_t *dc_val;
/* find prediction */ /* find prediction */
...@@ -2431,10 +2423,27 @@ static inline int ff_mpeg4_pred_dc(MpegEncContext * s, int n, uint16_t **dc_val_ ...@@ -2431,10 +2423,27 @@ static inline int ff_mpeg4_pred_dc(MpegEncContext * s, int n, uint16_t **dc_val_
/* we assume pred is positive */ /* we assume pred is positive */
pred = FASTDIV((pred + (scale >> 1)), scale); pred = FASTDIV((pred + (scale >> 1)), scale);
/* prepare address for prediction update */ if(encoding){
*dc_val_ptr = &dc_val[0]; ret = level - pred;
}else{
level += pred;
ret= level;
if(s->error_resilience>=3){
if(level<0){
av_log(s->avctx, AV_LOG_ERROR, "dc<0 at %dx%d\n", s->mb_x, s->mb_y);
return -1;
}
if(level*scale > 2048 + scale){
av_log(s->avctx, AV_LOG_ERROR, "dc overflow at %dx%d\n", s->mb_x, s->mb_y);
return -1;
}
}
}
level *=scale;
if(level&(~2047)) level= level<0 ? 0 : 2047;
dc_val[0]= level;
return pred; return ret;
} }
/** /**
...@@ -4537,8 +4546,7 @@ not_coded: ...@@ -4537,8 +4546,7 @@ not_coded:
*/ */
static inline int mpeg4_decode_dc(MpegEncContext * s, int n, int *dir_ptr) static inline int mpeg4_decode_dc(MpegEncContext * s, int n, int *dir_ptr)
{ {
int level, pred, code; int level, code;
uint16_t *dc_val;
if (n < 4) if (n < 4)
code = get_vlc2(&s->gb, dc_lum.table, DC_VLC_BITS, 1); code = get_vlc2(&s->gb, dc_lum.table, DC_VLC_BITS, 1);
...@@ -4573,30 +4581,8 @@ static inline int mpeg4_decode_dc(MpegEncContext * s, int n, int *dir_ptr) ...@@ -4573,30 +4581,8 @@ static inline int mpeg4_decode_dc(MpegEncContext * s, int n, int *dir_ptr)
} }
} }
} }
pred = ff_mpeg4_pred_dc(s, n, &dc_val, dir_ptr);
level += pred;
if (level < 0){
if(s->error_resilience>=3){
av_log(s->avctx, AV_LOG_ERROR, "dc<0 at %dx%d\n", s->mb_x, s->mb_y);
return -1;
}
level = 0;
}
if (n < 4) {
*dc_val = level * s->y_dc_scale;
} else {
*dc_val = level * s->c_dc_scale;
}
if(IS_3IV1)
*dc_val = level * 8;
if(s->error_resilience>=3){ return ff_mpeg4_pred_dc(s, n, level, dir_ptr, 0);
if(*dc_val > 2048 + s->y_dc_scale + s->c_dc_scale){
av_log(s->avctx, AV_LOG_ERROR, "dc overflow at %dx%d\n", s->mb_x, s->mb_y);
return -1;
}
}
return level;
} }
/** /**
...@@ -4842,13 +4828,7 @@ static inline int mpeg4_decode_block(MpegEncContext * s, DCTELEM * block, ...@@ -4842,13 +4828,7 @@ static inline int mpeg4_decode_block(MpegEncContext * s, DCTELEM * block,
not_coded: not_coded:
if (intra) { if (intra) {
if(s->qscale >= s->intra_dc_threshold){ if(s->qscale >= s->intra_dc_threshold){
uint16_t *dc_val; block[0] = ff_mpeg4_pred_dc(s, n, block[0], &dc_pred_dir, 0);
block[0] += ff_mpeg4_pred_dc(s, n, &dc_val, &dc_pred_dir);
if (n < 4) {
*dc_val = block[0] * s->y_dc_scale;
} else {
*dc_val = block[0] * s->c_dc_scale;
}
if(i == -1) i=0; if(i == -1) i=0;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment