00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00027 #include "avcodec.h"
00028 #include "bytestream.h"
00029 #include "mathops.h"
00030
00031
00032 typedef enum CinVideoBitmapIndex {
00033 CIN_CUR_BMP = 0,
00034 CIN_PRE_BMP = 1,
00035 CIN_INT_BMP = 2
00036 } CinVideoBitmapIndex;
00037
00038 typedef struct CinVideoContext {
00039 AVCodecContext *avctx;
00040 AVFrame frame;
00041 unsigned int bitmap_size;
00042 uint32_t palette[256];
00043 uint8_t *bitmap_table[3];
00044 } CinVideoContext;
00045
00046 typedef struct CinAudioContext {
00047 AVFrame frame;
00048 int initial_decode_frame;
00049 int delta;
00050 } CinAudioContext;
00051
00052
00053
00054 static const int16_t cinaudio_delta16_table[256] = {
00055 0, 0, 0, 0, 0, 0, 0, 0,
00056 0, 0, 0, 0, 0, 0, 0, 0,
00057 0, 0, 0, -30210, -27853, -25680, -23677, -21829,
00058 -20126, -18556, -17108, -15774, -14543, -13408, -12362, -11398,
00059 -10508, -9689, -8933, -8236, -7593, -7001, -6455, -5951,
00060 -5487, -5059, -4664, -4300, -3964, -3655, -3370, -3107,
00061 -2865, -2641, -2435, -2245, -2070, -1908, -1759, -1622,
00062 -1495, -1379, -1271, -1172, -1080, -996, -918, -847,
00063 -781, -720, -663, -612, -564, -520, -479, -442,
00064 -407, -376, -346, -319, -294, -271, -250, -230,
00065 -212, -196, -181, -166, -153, -141, -130, -120,
00066 -111, -102, -94, -87, -80, -74, -68, -62,
00067 -58, -53, -49, -45, -41, -38, -35, -32,
00068 -30, -27, -25, -23, -21, -20, -18, -17,
00069 -15, -14, -13, -12, -11, -10, -9, -8,
00070 -7, -6, -5, -4, -3, -2, -1, 0,
00071 0, 1, 2, 3, 4, 5, 6, 7,
00072 8, 9, 10, 11, 12, 13, 14, 15,
00073 17, 18, 20, 21, 23, 25, 27, 30,
00074 32, 35, 38, 41, 45, 49, 53, 58,
00075 62, 68, 74, 80, 87, 94, 102, 111,
00076 120, 130, 141, 153, 166, 181, 196, 212,
00077 230, 250, 271, 294, 319, 346, 376, 407,
00078 442, 479, 520, 564, 612, 663, 720, 781,
00079 847, 918, 996, 1080, 1172, 1271, 1379, 1495,
00080 1622, 1759, 1908, 2070, 2245, 2435, 2641, 2865,
00081 3107, 3370, 3655, 3964, 4300, 4664, 5059, 5487,
00082 5951, 6455, 7001, 7593, 8236, 8933, 9689, 10508,
00083 11398, 12362, 13408, 14543, 15774, 17108, 18556, 20126,
00084 21829, 23677, 25680, 27853, 30210, 0, 0, 0,
00085 0, 0, 0, 0, 0, 0, 0, 0,
00086 0, 0, 0, 0, 0, 0, 0, 0
00087 };
00088
00089
00090 static av_cold int cinvideo_decode_init(AVCodecContext *avctx)
00091 {
00092 CinVideoContext *cin = avctx->priv_data;
00093 unsigned int i;
00094
00095 cin->avctx = avctx;
00096 avctx->pix_fmt = PIX_FMT_PAL8;
00097
00098 avcodec_get_frame_defaults(&cin->frame);
00099 cin->frame.data[0] = NULL;
00100
00101 cin->bitmap_size = avctx->width * avctx->height;
00102 for (i = 0; i < 3; ++i) {
00103 cin->bitmap_table[i] = av_mallocz(cin->bitmap_size);
00104 if (!cin->bitmap_table[i])
00105 av_log(avctx, AV_LOG_ERROR, "Can't allocate bitmap buffers.\n");
00106 }
00107
00108 return 0;
00109 }
00110
00111 static void cin_apply_delta_data(const unsigned char *src, unsigned char *dst, int size)
00112 {
00113 while (size--)
00114 *dst++ += *src++;
00115 }
00116
00117 static int cin_decode_huffman(const unsigned char *src, int src_size, unsigned char *dst, int dst_size)
00118 {
00119 int b, huff_code = 0;
00120 unsigned char huff_code_table[15];
00121 unsigned char *dst_cur = dst;
00122 unsigned char *dst_end = dst + dst_size;
00123 const unsigned char *src_end = src + src_size;
00124
00125 memcpy(huff_code_table, src, 15); src += 15;
00126
00127 while (src < src_end) {
00128 huff_code = *src++;
00129 if ((huff_code >> 4) == 15) {
00130 b = huff_code << 4;
00131 huff_code = *src++;
00132 *dst_cur++ = b | (huff_code >> 4);
00133 } else
00134 *dst_cur++ = huff_code_table[huff_code >> 4];
00135 if (dst_cur >= dst_end)
00136 break;
00137
00138 huff_code &= 15;
00139 if (huff_code == 15) {
00140 *dst_cur++ = *src++;
00141 } else
00142 *dst_cur++ = huff_code_table[huff_code];
00143 if (dst_cur >= dst_end)
00144 break;
00145 }
00146
00147 return dst_cur - dst;
00148 }
00149
00150 static int cin_decode_lzss(const unsigned char *src, int src_size, unsigned char *dst, int dst_size)
00151 {
00152 uint16_t cmd;
00153 int i, sz, offset, code;
00154 unsigned char *dst_end = dst + dst_size, *dst_start = dst;
00155 const unsigned char *src_end = src + src_size;
00156
00157 while (src < src_end && dst < dst_end) {
00158 code = *src++;
00159 for (i = 0; i < 8 && src < src_end && dst < dst_end; ++i) {
00160 if (code & (1 << i)) {
00161 *dst++ = *src++;
00162 } else {
00163 cmd = AV_RL16(src); src += 2;
00164 offset = cmd >> 4;
00165 if ((int) (dst - dst_start) < offset + 1)
00166 return AVERROR_INVALIDDATA;
00167 sz = (cmd & 0xF) + 2;
00168
00169
00170 sz = FFMIN(sz, dst_end - dst);
00171 while (sz--) {
00172 *dst = *(dst - offset - 1);
00173 ++dst;
00174 }
00175 }
00176 }
00177 }
00178
00179 return 0;
00180 }
00181
00182 static int cin_decode_rle(const unsigned char *src, int src_size, unsigned char *dst, int dst_size)
00183 {
00184 int len, code;
00185 unsigned char *dst_end = dst + dst_size;
00186 const unsigned char *src_end = src + src_size;
00187
00188 while (src + 1 < src_end && dst < dst_end) {
00189 code = *src++;
00190 if (code & 0x80) {
00191 len = code - 0x7F;
00192 memset(dst, *src++, FFMIN(len, dst_end - dst));
00193 } else {
00194 len = code + 1;
00195 if (len > src_end-src) {
00196 av_log(0, AV_LOG_ERROR, "RLE overread\n");
00197 return AVERROR_INVALIDDATA;
00198 }
00199 memcpy(dst, src, FFMIN(len, dst_end - dst));
00200 src += len;
00201 }
00202 dst += len;
00203 }
00204 return 0;
00205 }
00206
00207 static int cinvideo_decode_frame(AVCodecContext *avctx,
00208 void *data, int *data_size,
00209 AVPacket *avpkt)
00210 {
00211 const uint8_t *buf = avpkt->data;
00212 int buf_size = avpkt->size;
00213 CinVideoContext *cin = avctx->priv_data;
00214 int i, y, palette_type, palette_colors_count, bitmap_frame_type, bitmap_frame_size, res = 0;
00215
00216 palette_type = buf[0];
00217 palette_colors_count = AV_RL16(buf+1);
00218 bitmap_frame_type = buf[3];
00219 buf += 4;
00220
00221 bitmap_frame_size = buf_size - 4;
00222
00223
00224 if (bitmap_frame_size < palette_colors_count * (3 + (palette_type != 0)))
00225 return AVERROR_INVALIDDATA;
00226 if (palette_type == 0) {
00227 if (palette_colors_count > 256)
00228 return AVERROR_INVALIDDATA;
00229 for (i = 0; i < palette_colors_count; ++i) {
00230 cin->palette[i] = 0xFFU << 24 | bytestream_get_le24(&buf);
00231 bitmap_frame_size -= 3;
00232 }
00233 } else {
00234 for (i = 0; i < palette_colors_count; ++i) {
00235 cin->palette[buf[0]] = 0xFFU << 24 | AV_RL24(buf+1);
00236 buf += 4;
00237 bitmap_frame_size -= 4;
00238 }
00239 }
00240
00241
00242 switch (bitmap_frame_type) {
00243 case 9:
00244 cin_decode_rle(buf, bitmap_frame_size,
00245 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00246 break;
00247 case 34:
00248 cin_decode_rle(buf, bitmap_frame_size,
00249 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00250 cin_apply_delta_data(cin->bitmap_table[CIN_PRE_BMP],
00251 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00252 break;
00253 case 35:
00254 cin_decode_huffman(buf, bitmap_frame_size,
00255 cin->bitmap_table[CIN_INT_BMP], cin->bitmap_size);
00256 cin_decode_rle(cin->bitmap_table[CIN_INT_BMP], bitmap_frame_size,
00257 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00258 break;
00259 case 36:
00260 bitmap_frame_size = cin_decode_huffman(buf, bitmap_frame_size,
00261 cin->bitmap_table[CIN_INT_BMP], cin->bitmap_size);
00262 cin_decode_rle(cin->bitmap_table[CIN_INT_BMP], bitmap_frame_size,
00263 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00264 cin_apply_delta_data(cin->bitmap_table[CIN_PRE_BMP],
00265 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00266 break;
00267 case 37:
00268 cin_decode_huffman(buf, bitmap_frame_size,
00269 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00270 break;
00271 case 38:
00272 res = cin_decode_lzss(buf, bitmap_frame_size,
00273 cin->bitmap_table[CIN_CUR_BMP],
00274 cin->bitmap_size);
00275 if (res < 0)
00276 return res;
00277 break;
00278 case 39:
00279 res = cin_decode_lzss(buf, bitmap_frame_size,
00280 cin->bitmap_table[CIN_CUR_BMP],
00281 cin->bitmap_size);
00282 if (res < 0)
00283 return res;
00284 cin_apply_delta_data(cin->bitmap_table[CIN_PRE_BMP],
00285 cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_size);
00286 break;
00287 }
00288
00289 cin->frame.buffer_hints = FF_BUFFER_HINTS_VALID | FF_BUFFER_HINTS_PRESERVE | FF_BUFFER_HINTS_REUSABLE;
00290 if (avctx->reget_buffer(avctx, &cin->frame)) {
00291 av_log(cin->avctx, AV_LOG_ERROR, "delphinecinvideo: reget_buffer() failed to allocate a frame\n");
00292 return -1;
00293 }
00294
00295 memcpy(cin->frame.data[1], cin->palette, sizeof(cin->palette));
00296 cin->frame.palette_has_changed = 1;
00297 for (y = 0; y < cin->avctx->height; ++y)
00298 memcpy(cin->frame.data[0] + (cin->avctx->height - 1 - y) * cin->frame.linesize[0],
00299 cin->bitmap_table[CIN_CUR_BMP] + y * cin->avctx->width,
00300 cin->avctx->width);
00301
00302 FFSWAP(uint8_t *, cin->bitmap_table[CIN_CUR_BMP], cin->bitmap_table[CIN_PRE_BMP]);
00303
00304 *data_size = sizeof(AVFrame);
00305 *(AVFrame *)data = cin->frame;
00306
00307 return buf_size;
00308 }
00309
00310 static av_cold int cinvideo_decode_end(AVCodecContext *avctx)
00311 {
00312 CinVideoContext *cin = avctx->priv_data;
00313 int i;
00314
00315 if (cin->frame.data[0])
00316 avctx->release_buffer(avctx, &cin->frame);
00317
00318 for (i = 0; i < 3; ++i)
00319 av_free(cin->bitmap_table[i]);
00320
00321 return 0;
00322 }
00323
00324 static av_cold int cinaudio_decode_init(AVCodecContext *avctx)
00325 {
00326 CinAudioContext *cin = avctx->priv_data;
00327
00328 if (avctx->channels != 1) {
00329 av_log_ask_for_sample(avctx, "Number of channels is not supported\n");
00330 return AVERROR_PATCHWELCOME;
00331 }
00332
00333 cin->initial_decode_frame = 1;
00334 cin->delta = 0;
00335 avctx->sample_fmt = AV_SAMPLE_FMT_S16;
00336
00337 avcodec_get_frame_defaults(&cin->frame);
00338 avctx->coded_frame = &cin->frame;
00339
00340 return 0;
00341 }
00342
00343 static int cinaudio_decode_frame(AVCodecContext *avctx, void *data,
00344 int *got_frame_ptr, AVPacket *avpkt)
00345 {
00346 const uint8_t *buf = avpkt->data;
00347 CinAudioContext *cin = avctx->priv_data;
00348 const uint8_t *buf_end = buf + avpkt->size;
00349 int16_t *samples;
00350 int delta, ret;
00351
00352
00353 cin->frame.nb_samples = avpkt->size - cin->initial_decode_frame;
00354 if ((ret = avctx->get_buffer(avctx, &cin->frame)) < 0) {
00355 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
00356 return ret;
00357 }
00358 samples = (int16_t *)cin->frame.data[0];
00359
00360 delta = cin->delta;
00361 if (cin->initial_decode_frame) {
00362 cin->initial_decode_frame = 0;
00363 delta = sign_extend(AV_RL16(buf), 16);
00364 buf += 2;
00365 *samples++ = delta;
00366 }
00367 while (buf < buf_end) {
00368 delta += cinaudio_delta16_table[*buf++];
00369 delta = av_clip_int16(delta);
00370 *samples++ = delta;
00371 }
00372 cin->delta = delta;
00373
00374 *got_frame_ptr = 1;
00375 *(AVFrame *)data = cin->frame;
00376
00377 return avpkt->size;
00378 }
00379
00380
00381 AVCodec ff_dsicinvideo_decoder = {
00382 .name = "dsicinvideo",
00383 .type = AVMEDIA_TYPE_VIDEO,
00384 .id = AV_CODEC_ID_DSICINVIDEO,
00385 .priv_data_size = sizeof(CinVideoContext),
00386 .init = cinvideo_decode_init,
00387 .close = cinvideo_decode_end,
00388 .decode = cinvideo_decode_frame,
00389 .capabilities = CODEC_CAP_DR1,
00390 .long_name = NULL_IF_CONFIG_SMALL("Delphine Software International CIN video"),
00391 };
00392
00393 AVCodec ff_dsicinaudio_decoder = {
00394 .name = "dsicinaudio",
00395 .type = AVMEDIA_TYPE_AUDIO,
00396 .id = AV_CODEC_ID_DSICINAUDIO,
00397 .priv_data_size = sizeof(CinAudioContext),
00398 .init = cinaudio_decode_init,
00399 .decode = cinaudio_decode_frame,
00400 .capabilities = CODEC_CAP_DR1,
00401 .long_name = NULL_IF_CONFIG_SMALL("Delphine Software International CIN audio"),
00402 };