From 247e882711e1e20d84ba1262c2c76b7a05587d01 Mon Sep 17 00:00:00 2001 From: Sylvain Dupont Date: Thu, 10 Feb 2011 21:41:59 +0000 Subject: VIDEO: Added some skipping when bad data is found in Indeo3 Some Urban Runner videos are badly encoded and contain corrupted data. When the decoder realizes that there is some bad data, it skips the rest of the frame. The original Indeo3 DLL decoder does the same. svn-id: r55876 --- video/codecs/indeo3.cpp | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) (limited to 'video') diff --git a/video/codecs/indeo3.cpp b/video/codecs/indeo3.cpp index cc87d26e2b..d9dde1e8e5 100644 --- a/video/codecs/indeo3.cpp +++ b/video/codecs/indeo3.cpp @@ -564,6 +564,16 @@ void Indeo3Decoder::decodeChunk(byte *cur, byte *ref, int width, int height, lp2++; break; case 1: + if (correction_type_sp[0][*buf1] != 1) { + // both correction types must be DYAD. If it's not the case + // we have an incorrect data and we should skip the rest. + // This occurs in some Urban Runner videos, and produced a glitch. + // The glitch is not visible anymore if we skip this part of the frame. + // The old Y values are then used. + // This is also the behavior of the codec in the original game. + //warning("Glitch"); + return; + } res = ((FROM_LE_16(((uint16 *)(ref_lp))[0]) >> 1) + correction_lp[lp2 & 0x01][*buf1]) << 1; ((uint16 *)cur_lp)[0] = FROM_LE_16(res); res = ((FROM_LE_16(((uint16 *)(ref_lp))[1]) >> 1) + correction_lp[lp2 & 0x01][k]) << 1; @@ -616,6 +626,12 @@ void Indeo3Decoder::decodeChunk(byte *cur, byte *ref, int width, int height, rle_v3 = 1; } case 6: + if (lp2 > 0) { + //This case can't happen either. + //If it occurs, it must happen on the first line. + //warning("Glitch"); + return; + } if (ref_vectors != NULL) { for (i = 0, j = 0; i < 4; i++, j += width_tbl[1]) cur_lp[j] = ref_lp[j]; @@ -805,6 +821,11 @@ void Indeo3Decoder::decodeChunk(byte *cur, byte *ref, int width, int height, break; case 1: + if (correction_type_sp[lp2 & 0x01][*buf1] != 1) { + //See the mode 0/1 + //warning("Glitch"); + return; + } cur_lp[width_tbl[1]] = FROM_LE_32(((FROM_LE_32(lv1) >> 1) + correctionloworder_lp[lp2 & 0x01][*buf1]) << 1); cur_lp[width_tbl[1]+1] = FROM_LE_32(((FROM_LE_32(lv2) >> 1) + correctionloworder_lp[lp2 & 0x01][k]) << 1); if (lp2 > 0 || strip->ypos != 0 || flag1 == 0) { @@ -1056,6 +1077,12 @@ void Indeo3Decoder::decodeChunk(byte *cur, byte *ref, int width, int height, break; case 1: + if (correction_type_sp[lp2 & 0x01][*buf1] != 1) { + // See mode 0/1 + //warning("Glitch"); + return; + } + lv1 = (uint16)(correction_lp[lp2 & 0x01][*buf1++]); lv2 = (uint16)(correction_lp[lp2 & 0x01][k]); res = (uint16)(((FROM_LE_16(((uint16 *)ref_lp)[0]) >> 1) + lv1) << 1); @@ -1137,6 +1164,7 @@ void Indeo3Decoder::decodeChunk(byte *cur, byte *ref, int width, int height, // FIXME: I've seen case 13 happen in Urban // Runner. Perhaps it uses a more recent form of // Indeo 3? There appears to have been several. + // -> This should not happen anymore with the other skipping for bad data. warning("Indeo3Decoder::decodeChunk: Unknown case %d", k); return; } -- cgit v1.2.3