mirror of
https://github.com/FFmpeg/FFmpeg.git
synced 2025-04-14 00:58:38 +02:00
avcodec/imm4: fix artifacts on some files with special coding mode
This commit is contained in:
parent
53248acfb3
commit
7b966af930
@ -138,7 +138,7 @@ static int get_cbphi(GetBitContext *gb, int x)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int decode_block(AVCodecContext *avctx, GetBitContext *gb,
|
static int decode_block(AVCodecContext *avctx, GetBitContext *gb,
|
||||||
int block, int factor, int flag, int offset)
|
int block, int factor, int flag, int offset, int flag2)
|
||||||
{
|
{
|
||||||
IMM4Context *s = avctx->priv_data;
|
IMM4Context *s = avctx->priv_data;
|
||||||
const uint8_t *scantable = s->intra_scantable.permutated;
|
const uint8_t *scantable = s->intra_scantable.permutated;
|
||||||
@ -169,11 +169,19 @@ static int decode_block(AVCodecContext *avctx, GetBitContext *gb,
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (s->hi == 2 && flag2 && block < 4) {
|
||||||
|
if (flag)
|
||||||
|
s->block[block][scantable[0]] *= 2;
|
||||||
|
s->block[block][scantable[1]] *= 2;
|
||||||
|
s->block[block][scantable[8]] *= 2;
|
||||||
|
s->block[block][scantable[16]] *= 2;
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int decode_blocks(AVCodecContext *avctx, GetBitContext *gb,
|
static int decode_blocks(AVCodecContext *avctx, GetBitContext *gb,
|
||||||
unsigned cbp, int flag, int offset)
|
unsigned cbp, int flag, int offset, unsigned flag2)
|
||||||
{
|
{
|
||||||
IMM4Context *s = avctx->priv_data;
|
IMM4Context *s = avctx->priv_data;
|
||||||
const uint8_t *scantable = s->intra_scantable.permutated;
|
const uint8_t *scantable = s->intra_scantable.permutated;
|
||||||
@ -193,7 +201,7 @@ static int decode_blocks(AVCodecContext *avctx, GetBitContext *gb,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (cbp & (1 << (5 - i))) {
|
if (cbp & (1 << (5 - i))) {
|
||||||
ret = decode_block(avctx, gb, i, s->factor, flag, offset);
|
ret = decode_block(avctx, gb, i, s->factor, flag, offset, flag2);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
@ -212,11 +220,7 @@ static int decode_intra(AVCodecContext *avctx, GetBitContext *gb, AVFrame *frame
|
|||||||
return AVERROR_INVALIDDATA;
|
return AVERROR_INVALIDDATA;
|
||||||
s->factor = intra_cb[s->lo];
|
s->factor = intra_cb[s->lo];
|
||||||
} else {
|
} else {
|
||||||
if (s->hi == 1) {
|
s->factor = s->lo * 2;
|
||||||
s->factor = s->lo * 2;
|
|
||||||
} else {
|
|
||||||
s->factor = s->lo * 2;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (s->hi) {
|
if (s->hi) {
|
||||||
@ -228,14 +232,14 @@ static int decode_intra(AVCodecContext *avctx, GetBitContext *gb, AVFrame *frame
|
|||||||
|
|
||||||
for (y = 0; y < avctx->height; y += 16) {
|
for (y = 0; y < avctx->height; y += 16) {
|
||||||
for (x = 0; x < avctx->width; x += 16) {
|
for (x = 0; x < avctx->width; x += 16) {
|
||||||
unsigned cbphi, cbplo;
|
unsigned flag, cbphi, cbplo;
|
||||||
|
|
||||||
cbplo = get_vlc2(gb, cbplo_tab.table, cbplo_tab.bits, 1) >> 4;
|
cbplo = get_vlc2(gb, cbplo_tab.table, cbplo_tab.bits, 1) >> 4;
|
||||||
skip_bits1(gb);
|
flag = get_bits1(gb);
|
||||||
|
|
||||||
cbphi = get_cbphi(gb, 1);
|
cbphi = get_cbphi(gb, 1);
|
||||||
|
|
||||||
ret = decode_blocks(avctx, gb, cbplo | (cbphi << 2), 0, offset);
|
ret = decode_blocks(avctx, gb, cbplo | (cbphi << 2), 0, offset, flag);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
@ -268,11 +272,7 @@ static int decode_inter(AVCodecContext *avctx, GetBitContext *gb,
|
|||||||
return AVERROR_INVALIDDATA;
|
return AVERROR_INVALIDDATA;
|
||||||
s->factor = inter_cb[s->lo];
|
s->factor = inter_cb[s->lo];
|
||||||
} else {
|
} else {
|
||||||
if (s->hi == 1) {
|
s->factor = s->lo * 2;
|
||||||
s->factor = s->lo * 2;
|
|
||||||
} else {
|
|
||||||
s->factor = s->lo * 2;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (s->hi) {
|
if (s->hi) {
|
||||||
@ -285,7 +285,7 @@ static int decode_inter(AVCodecContext *avctx, GetBitContext *gb,
|
|||||||
for (y = 0; y < avctx->height; y += 16) {
|
for (y = 0; y < avctx->height; y += 16) {
|
||||||
for (x = 0; x < avctx->width; x += 16) {
|
for (x = 0; x < avctx->width; x += 16) {
|
||||||
int reverse, intra_block, value;
|
int reverse, intra_block, value;
|
||||||
unsigned cbphi, cbplo;
|
unsigned cbphi, cbplo, flag2 = 0;
|
||||||
|
|
||||||
if (get_bits1(gb)) {
|
if (get_bits1(gb)) {
|
||||||
copy_block16(frame->data[0] + y * frame->linesize[0] + x,
|
copy_block16(frame->data[0] + y * frame->linesize[0] + x,
|
||||||
@ -307,12 +307,12 @@ static int decode_inter(AVCodecContext *avctx, GetBitContext *gb,
|
|||||||
intra_block = value & 0x07;
|
intra_block = value & 0x07;
|
||||||
reverse = intra_block == 3;
|
reverse = intra_block == 3;
|
||||||
if (reverse)
|
if (reverse)
|
||||||
skip_bits1(gb);
|
flag2 = get_bits1(gb);
|
||||||
|
|
||||||
cbplo = value >> 4;
|
cbplo = value >> 4;
|
||||||
cbphi = get_cbphi(gb, reverse);
|
cbphi = get_cbphi(gb, reverse);
|
||||||
if (intra_block) {
|
if (intra_block) {
|
||||||
ret = decode_blocks(avctx, gb, cbplo | (cbphi << 2), 0, offset);
|
ret = decode_blocks(avctx, gb, cbplo | (cbphi << 2), 0, offset, flag2);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
@ -329,8 +329,9 @@ static int decode_inter(AVCodecContext *avctx, GetBitContext *gb,
|
|||||||
s->idsp.idct_put(frame->data[2] + (y >> 1) * frame->linesize[2] + (x >> 1),
|
s->idsp.idct_put(frame->data[2] + (y >> 1) * frame->linesize[2] + (x >> 1),
|
||||||
frame->linesize[2], s->block[5]);
|
frame->linesize[2], s->block[5]);
|
||||||
} else {
|
} else {
|
||||||
skip_bits(gb, 2);
|
flag2 = get_bits1(gb);
|
||||||
ret = decode_blocks(avctx, gb, cbplo | (cbphi << 2), 1, offset);
|
skip_bits1(gb);
|
||||||
|
ret = decode_blocks(avctx, gb, cbplo | (cbphi << 2), 1, offset, flag2);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user