]> git.sesse.net Git - ffmpeg/blob - libavcodec/iff.c
avcodec/iff: Check that there are enough bytes in dgb before reading
[ffmpeg] / libavcodec / iff.c
1 /*
2  * IFF ACBM/ANIM/DEEP/ILBM/PBM/RGB8/RGBN bitmap decoder
3  * Copyright (c) 2010 Peter Ross <pross@xvid.org>
4  * Copyright (c) 2010 Sebastian Vater <cdgs.basty@googlemail.com>
5  * Copyright (c) 2016 Paul B Mahol
6  *
7  * This file is part of FFmpeg.
8  *
9  * FFmpeg is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2.1 of the License, or (at your option) any later version.
13  *
14  * FFmpeg is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with FFmpeg; if not, write to the Free Software
21  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22  */
23
24 /**
25  * @file
26  * IFF ACBM/ANIM/DEEP/ILBM/PBM/RGB8/RGBN bitmap decoder
27  */
28
29 #include <stdint.h>
30
31 #include "libavutil/imgutils.h"
32
33 #include "bytestream.h"
34 #include "avcodec.h"
35 #include "internal.h"
36 #include "mathops.h"
37
38 // TODO: masking bits
39 typedef enum {
40     MASK_NONE,
41     MASK_HAS_MASK,
42     MASK_HAS_TRANSPARENT_COLOR,
43     MASK_LASSO
44 } mask_type;
45
46 typedef struct IffContext {
47     AVFrame *frame;
48     int planesize;
49     uint8_t * planebuf;
50     uint8_t * ham_buf;      ///< temporary buffer for planar to chunky conversation
51     uint32_t *ham_palbuf;   ///< HAM decode table
52     uint32_t *mask_buf;     ///< temporary buffer for palette indices
53     uint32_t *mask_palbuf;  ///< masking palette table
54     unsigned  compression;  ///< delta compression method used
55     unsigned  is_short;     ///< short compression method used
56     unsigned  is_interlaced;///< video is interlaced
57     unsigned  is_brush;     ///< video is in ANBR format
58     unsigned  bpp;          ///< bits per plane to decode (differs from bits_per_coded_sample if HAM)
59     unsigned  ham;          ///< 0 if non-HAM or number of hold bits (6 for bpp > 6, 4 otherwise)
60     unsigned  flags;        ///< 1 for EHB, 0 is no extra half darkening
61     unsigned  transparency; ///< TODO: transparency color index in palette
62     unsigned  masking;      ///< TODO: masking method used
63     int init; // 1 if buffer and palette data already initialized, 0 otherwise
64     int16_t   tvdc[16];     ///< TVDC lookup table
65     GetByteContext gb;
66     uint8_t *video[2];
67     unsigned video_size;
68     uint32_t *pal[2];
69 } IffContext;
70
71 #define LUT8_PART(plane, v)                             \
72     AV_LE2NE64C(UINT64_C(0x0000000)<<32 | v) << plane,  \
73     AV_LE2NE64C(UINT64_C(0x1000000)<<32 | v) << plane,  \
74     AV_LE2NE64C(UINT64_C(0x0010000)<<32 | v) << plane,  \
75     AV_LE2NE64C(UINT64_C(0x1010000)<<32 | v) << plane,  \
76     AV_LE2NE64C(UINT64_C(0x0000100)<<32 | v) << plane,  \
77     AV_LE2NE64C(UINT64_C(0x1000100)<<32 | v) << plane,  \
78     AV_LE2NE64C(UINT64_C(0x0010100)<<32 | v) << plane,  \
79     AV_LE2NE64C(UINT64_C(0x1010100)<<32 | v) << plane,  \
80     AV_LE2NE64C(UINT64_C(0x0000001)<<32 | v) << plane,  \
81     AV_LE2NE64C(UINT64_C(0x1000001)<<32 | v) << plane,  \
82     AV_LE2NE64C(UINT64_C(0x0010001)<<32 | v) << plane,  \
83     AV_LE2NE64C(UINT64_C(0x1010001)<<32 | v) << plane,  \
84     AV_LE2NE64C(UINT64_C(0x0000101)<<32 | v) << plane,  \
85     AV_LE2NE64C(UINT64_C(0x1000101)<<32 | v) << plane,  \
86     AV_LE2NE64C(UINT64_C(0x0010101)<<32 | v) << plane,  \
87     AV_LE2NE64C(UINT64_C(0x1010101)<<32 | v) << plane
88
89 #define LUT8(plane) {                           \
90     LUT8_PART(plane, 0x0000000),                \
91     LUT8_PART(plane, 0x1000000),                \
92     LUT8_PART(plane, 0x0010000),                \
93     LUT8_PART(plane, 0x1010000),                \
94     LUT8_PART(plane, 0x0000100),                \
95     LUT8_PART(plane, 0x1000100),                \
96     LUT8_PART(plane, 0x0010100),                \
97     LUT8_PART(plane, 0x1010100),                \
98     LUT8_PART(plane, 0x0000001),                \
99     LUT8_PART(plane, 0x1000001),                \
100     LUT8_PART(plane, 0x0010001),                \
101     LUT8_PART(plane, 0x1010001),                \
102     LUT8_PART(plane, 0x0000101),                \
103     LUT8_PART(plane, 0x1000101),                \
104     LUT8_PART(plane, 0x0010101),                \
105     LUT8_PART(plane, 0x1010101),                \
106 }
107
108 // 8 planes * 8-bit mask
109 static const uint64_t plane8_lut[8][256] = {
110     LUT8(0), LUT8(1), LUT8(2), LUT8(3),
111     LUT8(4), LUT8(5), LUT8(6), LUT8(7),
112 };
113
114 #define LUT32(plane) {                                \
115              0,          0,          0,          0,   \
116              0,          0,          0, 1 << plane,   \
117              0,          0, 1 << plane,          0,   \
118              0,          0, 1 << plane, 1 << plane,   \
119              0, 1 << plane,          0,          0,   \
120              0, 1 << plane,          0, 1 << plane,   \
121              0, 1 << plane, 1 << plane,          0,   \
122              0, 1 << plane, 1 << plane, 1 << plane,   \
123     1 << plane,          0,          0,          0,   \
124     1 << plane,          0,          0, 1 << plane,   \
125     1 << plane,          0, 1 << plane,          0,   \
126     1 << plane,          0, 1 << plane, 1 << plane,   \
127     1 << plane, 1 << plane,          0,          0,   \
128     1 << plane, 1 << plane,          0, 1 << plane,   \
129     1 << plane, 1 << plane, 1 << plane,          0,   \
130     1 << plane, 1 << plane, 1 << plane, 1 << plane,   \
131 }
132
133 // 32 planes * 4-bit mask * 4 lookup tables each
134 static const uint32_t plane32_lut[32][16*4] = {
135     LUT32( 0), LUT32( 1), LUT32( 2), LUT32( 3),
136     LUT32( 4), LUT32( 5), LUT32( 6), LUT32( 7),
137     LUT32( 8), LUT32( 9), LUT32(10), LUT32(11),
138     LUT32(12), LUT32(13), LUT32(14), LUT32(15),
139     LUT32(16), LUT32(17), LUT32(18), LUT32(19),
140     LUT32(20), LUT32(21), LUT32(22), LUT32(23),
141     LUT32(24), LUT32(25), LUT32(26), LUT32(27),
142     LUT32(28), LUT32(29), LUT32(30), LUT32(31),
143 };
144
145 // Gray to RGB, required for palette table of grayscale images with bpp < 8
146 static av_always_inline uint32_t gray2rgb(const uint32_t x) {
147     return x << 16 | x << 8 | x;
148 }
149
150 /**
151  * Convert CMAP buffer (stored in extradata) to lavc palette format
152  */
153 static int cmap_read_palette(AVCodecContext *avctx, uint32_t *pal)
154 {
155     IffContext *s = avctx->priv_data;
156     int count, i;
157     const uint8_t *const palette = avctx->extradata + AV_RB16(avctx->extradata);
158     int palette_size = avctx->extradata_size - AV_RB16(avctx->extradata);
159
160     if (avctx->bits_per_coded_sample > 8) {
161         av_log(avctx, AV_LOG_ERROR, "bits_per_coded_sample > 8 not supported\n");
162         return AVERROR_INVALIDDATA;
163     }
164
165     count = 1 << avctx->bits_per_coded_sample;
166     // If extradata is smaller than actually needed, fill the remaining with black.
167     count = FFMIN(palette_size / 3, count);
168     if (count) {
169         for (i = 0; i < count; i++)
170             pal[i] = 0xFF000000 | AV_RB24(palette + i*3);
171         if (s->flags && count >= 32) { // EHB
172             for (i = 0; i < 32; i++)
173                 pal[i + 32] = 0xFF000000 | (AV_RB24(palette + i*3) & 0xFEFEFE) >> 1;
174             count = FFMAX(count, 64);
175         }
176     } else { // Create gray-scale color palette for bps < 8
177         count = 1 << avctx->bits_per_coded_sample;
178
179         for (i = 0; i < count; i++)
180             pal[i] = 0xFF000000 | gray2rgb((i * 255) >> avctx->bits_per_coded_sample);
181     }
182     if (s->masking == MASK_HAS_MASK) {
183         memcpy(pal + (1 << avctx->bits_per_coded_sample), pal, count * 4);
184         for (i = 0; i < count; i++)
185             pal[i] &= 0xFFFFFF;
186     } else if (s->masking == MASK_HAS_TRANSPARENT_COLOR &&
187         s->transparency < 1 << avctx->bits_per_coded_sample)
188         pal[s->transparency] &= 0xFFFFFF;
189     return 0;
190 }
191
192 /**
193  * Extracts the IFF extra context and updates internal
194  * decoder structures.
195  *
196  * @param avctx the AVCodecContext where to extract extra context to
197  * @param avpkt the AVPacket to extract extra context from or NULL to use avctx
198  * @return >= 0 in case of success, a negative error code otherwise
199  */
200 static int extract_header(AVCodecContext *const avctx,
201                           const AVPacket *const avpkt)
202 {
203     IffContext *s = avctx->priv_data;
204     const uint8_t *buf;
205     unsigned buf_size = 0;
206     int i, palette_size;
207
208     if (avctx->extradata_size < 2) {
209         av_log(avctx, AV_LOG_ERROR, "not enough extradata\n");
210         return AVERROR_INVALIDDATA;
211     }
212     palette_size = avctx->extradata_size - AV_RB16(avctx->extradata);
213
214     if (avpkt && avctx->codec_tag == MKTAG('A', 'N', 'I', 'M')) {
215         uint32_t chunk_id;
216         uint64_t data_size;
217         GetByteContext *gb = &s->gb;
218
219         bytestream2_skip(gb, 4);
220         while (bytestream2_get_bytes_left(gb) >= 1) {
221             chunk_id  = bytestream2_get_le32(gb);
222             data_size = bytestream2_get_be32(gb);
223
224             if (chunk_id == MKTAG('B', 'M', 'H', 'D')) {
225                 bytestream2_skip(gb, data_size + (data_size & 1));
226             } else if (chunk_id == MKTAG('A', 'N', 'H', 'D')) {
227                 unsigned extra;
228                 if (data_size < 40)
229                     return AVERROR_INVALIDDATA;
230
231                 s->compression = (bytestream2_get_byte(gb) << 8) | (s->compression & 0xFF);
232                 bytestream2_skip(gb, 19);
233                 extra = bytestream2_get_be32(gb);
234                 s->is_short = !(extra & 1);
235                 s->is_brush = extra == 2;
236                 s->is_interlaced = !!(extra & 0x40);
237                 data_size -= 24;
238                 bytestream2_skip(gb, data_size + (data_size & 1));
239             } else if (chunk_id == MKTAG('D', 'L', 'T', 'A') ||
240                        chunk_id == MKTAG('B', 'O', 'D', 'Y')) {
241                 if (chunk_id == MKTAG('B','O','D','Y'))
242                     s->compression &= 0xFF;
243                 break;
244             } else if (chunk_id == MKTAG('C', 'M', 'A', 'P')) {
245                 int count = data_size / 3;
246                 uint32_t *pal = s->pal[0];
247
248                 if (count > 256)
249                     return AVERROR_INVALIDDATA;
250                 if (s->ham) {
251                     for (i = 0; i < count; i++)
252                         pal[i] = 0xFF000000 | bytestream2_get_le24(gb);
253                 } else {
254                     for (i = 0; i < count; i++)
255                         pal[i] = 0xFF000000 | bytestream2_get_be24(gb);
256                 }
257                 bytestream2_skip(gb, data_size & 1);
258             } else {
259                 bytestream2_skip(gb, data_size + (data_size&1));
260             }
261         }
262     } else if (!avpkt) {
263         buf = avctx->extradata;
264         buf_size = bytestream_get_be16(&buf);
265         if (buf_size <= 1 || palette_size < 0) {
266             av_log(avctx, AV_LOG_ERROR,
267                    "Invalid palette size received: %u -> palette data offset: %d\n",
268                    buf_size, palette_size);
269             return AVERROR_INVALIDDATA;
270         }
271     }
272
273     if (buf_size >= 41) {
274         s->compression  = bytestream_get_byte(&buf);
275         s->bpp          = bytestream_get_byte(&buf);
276         s->ham          = bytestream_get_byte(&buf);
277         s->flags        = bytestream_get_byte(&buf);
278         s->transparency = bytestream_get_be16(&buf);
279         s->masking      = bytestream_get_byte(&buf);
280         for (i = 0; i < 16; i++)
281             s->tvdc[i] = bytestream_get_be16(&buf);
282
283         if (s->masking == MASK_HAS_MASK) {
284             if (s->bpp >= 8 && !s->ham) {
285                 avctx->pix_fmt = AV_PIX_FMT_RGB32;
286                 av_freep(&s->mask_buf);
287                 av_freep(&s->mask_palbuf);
288                 s->mask_buf = av_malloc((s->planesize * 32) + AV_INPUT_BUFFER_PADDING_SIZE);
289                 if (!s->mask_buf)
290                     return AVERROR(ENOMEM);
291                 if (s->bpp > 16) {
292                     av_log(avctx, AV_LOG_ERROR, "bpp %d too large for palette\n", s->bpp);
293                     av_freep(&s->mask_buf);
294                     return AVERROR(ENOMEM);
295                 }
296                 s->mask_palbuf = av_malloc((2 << s->bpp) * sizeof(uint32_t) + AV_INPUT_BUFFER_PADDING_SIZE);
297                 if (!s->mask_palbuf) {
298                     av_freep(&s->mask_buf);
299                     return AVERROR(ENOMEM);
300                 }
301             }
302             s->bpp++;
303         } else if (s->masking != MASK_NONE && s->masking != MASK_HAS_TRANSPARENT_COLOR) {
304             av_log(avctx, AV_LOG_ERROR, "Masking not supported\n");
305             return AVERROR_PATCHWELCOME;
306         }
307         if (!s->bpp || s->bpp > 32) {
308             av_log(avctx, AV_LOG_ERROR, "Invalid number of bitplanes: %u\n", s->bpp);
309             return AVERROR_INVALIDDATA;
310         } else if (s->ham >= 8) {
311             av_log(avctx, AV_LOG_ERROR, "Invalid number of hold bits for HAM: %u\n", s->ham);
312             return AVERROR_INVALIDDATA;
313         }
314
315         av_freep(&s->ham_buf);
316         av_freep(&s->ham_palbuf);
317
318         if (s->ham) {
319             int i, count = FFMIN(palette_size / 3, 1 << s->ham);
320             int ham_count;
321             const uint8_t *const palette = avctx->extradata + AV_RB16(avctx->extradata);
322
323             s->ham_buf = av_malloc((s->planesize * 8) + AV_INPUT_BUFFER_PADDING_SIZE);
324             if (!s->ham_buf)
325                 return AVERROR(ENOMEM);
326
327             ham_count = 8 * (1 << s->ham);
328             s->ham_palbuf = av_malloc((ham_count << !!(s->masking == MASK_HAS_MASK)) * sizeof (uint32_t) + AV_INPUT_BUFFER_PADDING_SIZE);
329             if (!s->ham_palbuf) {
330                 av_freep(&s->ham_buf);
331                 return AVERROR(ENOMEM);
332             }
333
334             if (count) { // HAM with color palette attached
335                 // prefill with black and palette and set HAM take direct value mask to zero
336                 memset(s->ham_palbuf, 0, (1 << s->ham) * 2 * sizeof (uint32_t));
337                 for (i=0; i < count; i++) {
338                     s->ham_palbuf[i*2+1] = 0xFF000000 | AV_RL24(palette + i*3);
339                 }
340                 count = 1 << s->ham;
341             } else { // HAM with grayscale color palette
342                 count = 1 << s->ham;
343                 for (i=0; i < count; i++) {
344                     s->ham_palbuf[i*2]   = 0xFF000000; // take direct color value from palette
345                     s->ham_palbuf[i*2+1] = 0xFF000000 | av_le2ne32(gray2rgb((i * 255) >> s->ham));
346                 }
347             }
348             for (i=0; i < count; i++) {
349                 uint32_t tmp = i << (8 - s->ham);
350                 tmp |= tmp >> s->ham;
351                 s->ham_palbuf[(i+count)*2]     = 0xFF00FFFF; // just modify blue color component
352                 s->ham_palbuf[(i+count*2)*2]   = 0xFFFFFF00; // just modify red color component
353                 s->ham_palbuf[(i+count*3)*2]   = 0xFFFF00FF; // just modify green color component
354                 s->ham_palbuf[(i+count)*2+1]   = 0xFF000000 | tmp << 16;
355                 s->ham_palbuf[(i+count*2)*2+1] = 0xFF000000 | tmp;
356                 s->ham_palbuf[(i+count*3)*2+1] = 0xFF000000 | tmp << 8;
357             }
358             if (s->masking == MASK_HAS_MASK) {
359                 for (i = 0; i < ham_count; i++)
360                     s->ham_palbuf[(1 << s->bpp) + i] = s->ham_palbuf[i] | 0xFF000000;
361             }
362         }
363     }
364
365     return 0;
366 }
367
368 static av_cold int decode_end(AVCodecContext *avctx)
369 {
370     IffContext *s = avctx->priv_data;
371     av_freep(&s->planebuf);
372     av_freep(&s->ham_buf);
373     av_freep(&s->ham_palbuf);
374     av_freep(&s->video[0]);
375     av_freep(&s->video[1]);
376     av_freep(&s->pal[0]);
377     av_freep(&s->pal[1]);
378     return 0;
379 }
380
381 static av_cold int decode_init(AVCodecContext *avctx)
382 {
383     IffContext *s = avctx->priv_data;
384     int err;
385
386     if (avctx->bits_per_coded_sample <= 8) {
387         int palette_size;
388
389         if (avctx->extradata_size >= 2)
390             palette_size = avctx->extradata_size - AV_RB16(avctx->extradata);
391         else
392             palette_size = 0;
393         avctx->pix_fmt = (avctx->bits_per_coded_sample < 8) ||
394                          (avctx->extradata_size >= 2 && palette_size) ? AV_PIX_FMT_PAL8 : AV_PIX_FMT_GRAY8;
395     } else if (avctx->bits_per_coded_sample <= 32) {
396         if (avctx->codec_tag == MKTAG('R', 'G', 'B', '8')) {
397             avctx->pix_fmt = AV_PIX_FMT_RGB32;
398         } else if (avctx->codec_tag == MKTAG('R', 'G', 'B', 'N')) {
399             avctx->pix_fmt = AV_PIX_FMT_RGB444;
400         } else if (avctx->codec_tag != MKTAG('D', 'E', 'E', 'P')) {
401             if (avctx->bits_per_coded_sample == 24) {
402                 avctx->pix_fmt = AV_PIX_FMT_0BGR32;
403             } else if (avctx->bits_per_coded_sample == 32) {
404                 avctx->pix_fmt = AV_PIX_FMT_BGR32;
405             } else {
406                 avpriv_request_sample(avctx, "unknown bits_per_coded_sample");
407                 return AVERROR_PATCHWELCOME;
408             }
409         }
410     } else {
411         return AVERROR_INVALIDDATA;
412     }
413
414     if ((err = av_image_check_size(avctx->width, avctx->height, 0, avctx)))
415         return err;
416     s->planesize = FFALIGN(avctx->width, 16) >> 3; // Align plane size in bits to word-boundary
417     s->planebuf  = av_malloc(s->planesize + AV_INPUT_BUFFER_PADDING_SIZE);
418     if (!s->planebuf)
419         return AVERROR(ENOMEM);
420
421     s->bpp = avctx->bits_per_coded_sample;
422
423     if (avctx->codec_tag == MKTAG('A', 'N', 'I', 'M')) {
424         s->video_size = FFALIGN(avctx->width, 2) * avctx->height * s->bpp;
425         s->video[0] = av_calloc(FFALIGN(avctx->width, 2) * avctx->height, s->bpp);
426         s->video[1] = av_calloc(FFALIGN(avctx->width, 2) * avctx->height, s->bpp);
427         s->pal[0] = av_calloc(256, sizeof(*s->pal[0]));
428         s->pal[1] = av_calloc(256, sizeof(*s->pal[1]));
429         if (!s->video[0] || !s->video[1] || !s->pal[0] || !s->pal[1])
430             return AVERROR(ENOMEM);
431     }
432
433     if ((err = extract_header(avctx, NULL)) < 0)
434         return err;
435
436     return 0;
437 }
438
439 /**
440  * Decode interleaved plane buffer up to 8bpp
441  * @param dst Destination buffer
442  * @param buf Source buffer
443  * @param buf_size
444  * @param plane plane number to decode as
445  */
446 static void decodeplane8(uint8_t *dst, const uint8_t *buf, int buf_size, int plane)
447 {
448     const uint64_t *lut = plane8_lut[plane];
449     if (plane >= 8) {
450         av_log(NULL, AV_LOG_WARNING, "Ignoring extra planes beyond 8\n");
451         return;
452     }
453     do {
454         uint64_t v = AV_RN64A(dst) | lut[*buf++];
455         AV_WN64A(dst, v);
456         dst += 8;
457     } while (--buf_size);
458 }
459
460 /**
461  * Decode interleaved plane buffer up to 24bpp
462  * @param dst Destination buffer
463  * @param buf Source buffer
464  * @param buf_size
465  * @param plane plane number to decode as
466  */
467 static void decodeplane32(uint32_t *dst, const uint8_t *buf, int buf_size, int plane)
468 {
469     const uint32_t *lut = plane32_lut[plane];
470     do {
471         unsigned mask = (*buf >> 2) & ~3;
472         dst[0] |= lut[mask++];
473         dst[1] |= lut[mask++];
474         dst[2] |= lut[mask++];
475         dst[3] |= lut[mask];
476         mask    = (*buf++ << 2) & 0x3F;
477         dst[4] |= lut[mask++];
478         dst[5] |= lut[mask++];
479         dst[6] |= lut[mask++];
480         dst[7] |= lut[mask];
481         dst    += 8;
482     } while (--buf_size);
483 }
484
485 #define DECODE_HAM_PLANE32(x)       \
486     first       = buf[x] << 1;      \
487     second      = buf[(x)+1] << 1;  \
488     delta      &= pal[first++];     \
489     delta      |= pal[first];       \
490     dst[x]      = delta;            \
491     delta      &= pal[second++];    \
492     delta      |= pal[second];      \
493     dst[(x)+1]  = delta
494
495 /**
496  * Converts one line of HAM6/8-encoded chunky buffer to 24bpp.
497  *
498  * @param dst the destination 24bpp buffer
499  * @param buf the source 8bpp chunky buffer
500  * @param pal the HAM decode table
501  * @param buf_size the plane size in bytes
502  */
503 static void decode_ham_plane32(uint32_t *dst, const uint8_t  *buf,
504                                const uint32_t *const pal, unsigned buf_size)
505 {
506     uint32_t delta = pal[1]; /* first palette entry */
507     do {
508         uint32_t first, second;
509         DECODE_HAM_PLANE32(0);
510         DECODE_HAM_PLANE32(2);
511         DECODE_HAM_PLANE32(4);
512         DECODE_HAM_PLANE32(6);
513         buf += 8;
514         dst += 8;
515     } while (--buf_size);
516 }
517
518 static void lookup_pal_indicies(uint32_t *dst, const uint32_t *buf,
519                          const uint32_t *const pal, unsigned width)
520 {
521     do {
522         *dst++ = pal[*buf++];
523     } while (--width);
524 }
525
526 /**
527  * Decode one complete byterun1 encoded line.
528  *
529  * @param dst the destination buffer where to store decompressed bitstream
530  * @param dst_size the destination plane size in bytes
531  * @param buf the source byterun1 compressed bitstream
532  * @param buf_end the EOF of source byterun1 compressed bitstream
533  * @return number of consumed bytes in byterun1 compressed bitstream
534  */
535 static int decode_byterun(uint8_t *dst, int dst_size,
536                           GetByteContext *gb)
537 {
538     unsigned x;
539     for (x = 0; x < dst_size && bytestream2_get_bytes_left(gb) > 0;) {
540         unsigned length;
541         const int8_t value = bytestream2_get_byte(gb);
542         if (value >= 0) {
543             length = FFMIN3(value + 1, dst_size - x, bytestream2_get_bytes_left(gb));
544             bytestream2_get_buffer(gb, dst + x, length);
545             if (length < value + 1)
546                 bytestream2_skip(gb, value + 1 - length);
547         } else if (value > -128) {
548             length = FFMIN(-value + 1, dst_size - x);
549             memset(dst + x, bytestream2_get_byte(gb), length);
550         } else { // noop
551             continue;
552         }
553         x += length;
554     }
555     if (x < dst_size) {
556         av_log(NULL, AV_LOG_WARNING, "decode_byterun ended before plane size\n");
557         memset(dst+x, 0, dst_size - x);
558     }
559     return bytestream2_tell(gb);
560 }
561
562 #define DECODE_RGBX_COMMON(type) \
563     if (!length) { \
564         length = bytestream2_get_byte(gb); \
565         if (!length) { \
566             length = bytestream2_get_be16(gb); \
567             if (!length) \
568                 return; \
569         } \
570     } \
571     for (i = 0; i < length; i++) { \
572         *(type *)(dst + y*linesize + x * sizeof(type)) = pixel; \
573         x += 1; \
574         if (x >= width) { \
575             y += 1; \
576             if (y >= height) \
577                 return; \
578             x = 0; \
579         } \
580     }
581
582 /**
583  * Decode RGB8 buffer
584  * @param[out] dst Destination buffer
585  * @param width Width of destination buffer (pixels)
586  * @param height Height of destination buffer (pixels)
587  * @param linesize Line size of destination buffer (bytes)
588  */
589 static void decode_rgb8(GetByteContext *gb, uint8_t *dst, int width, int height, int linesize)
590 {
591     int x = 0, y = 0, i, length;
592     while (bytestream2_get_bytes_left(gb) >= 4) {
593         uint32_t pixel = 0xFF000000 | bytestream2_get_be24(gb);
594         length = bytestream2_get_byte(gb) & 0x7F;
595         DECODE_RGBX_COMMON(uint32_t)
596     }
597 }
598
599 /**
600  * Decode RGBN buffer
601  * @param[out] dst Destination buffer
602  * @param width Width of destination buffer (pixels)
603  * @param height Height of destination buffer (pixels)
604  * @param linesize Line size of destination buffer (bytes)
605  */
606 static void decode_rgbn(GetByteContext *gb, uint8_t *dst, int width, int height, int linesize)
607 {
608     int x = 0, y = 0, i, length;
609     while (bytestream2_get_bytes_left(gb) >= 2) {
610         uint32_t pixel = bytestream2_get_be16u(gb);
611         length = pixel & 0x7;
612         pixel >>= 4;
613         DECODE_RGBX_COMMON(uint16_t)
614     }
615 }
616
617 /**
618  * Decode DEEP RLE 32-bit buffer
619  * @param[out] dst Destination buffer
620  * @param[in] src Source buffer
621  * @param src_size Source buffer size (bytes)
622  * @param width Width of destination buffer (pixels)
623  * @param height Height of destination buffer (pixels)
624  * @param linesize Line size of destination buffer (bytes)
625  */
626 static void decode_deep_rle32(uint8_t *dst, const uint8_t *src, int src_size, int width, int height, int linesize)
627 {
628     const uint8_t *src_end = src + src_size;
629     int x = 0, y = 0, i;
630     while (src + 5 <= src_end) {
631         int opcode;
632         opcode = *(int8_t *)src++;
633         if (opcode >= 0) {
634             int size = opcode + 1;
635             for (i = 0; i < size; i++) {
636                 int length = FFMIN(size - i, width);
637                 memcpy(dst + y*linesize + x * 4, src, length * 4);
638                 src += length * 4;
639                 x += length;
640                 i += length;
641                 if (x >= width) {
642                     x = 0;
643                     y += 1;
644                     if (y >= height)
645                         return;
646                 }
647             }
648         } else {
649             int size = -opcode + 1;
650             uint32_t pixel = AV_RN32(src);
651             for (i = 0; i < size; i++) {
652                 *(uint32_t *)(dst + y*linesize + x * 4) = pixel;
653                 x += 1;
654                 if (x >= width) {
655                     x = 0;
656                     y += 1;
657                     if (y >= height)
658                         return;
659                 }
660             }
661             src += 4;
662         }
663     }
664 }
665
666 /**
667  * Decode DEEP TVDC 32-bit buffer
668  * @param[out] dst Destination buffer
669  * @param[in] src Source buffer
670  * @param src_size Source buffer size (bytes)
671  * @param width Width of destination buffer (pixels)
672  * @param height Height of destination buffer (pixels)
673  * @param linesize Line size of destination buffer (bytes)
674  * @param[int] tvdc TVDC lookup table
675  */
676 static void decode_deep_tvdc32(uint8_t *dst, const uint8_t *src, int src_size, int width, int height, int linesize, const int16_t *tvdc)
677 {
678     int x = 0, y = 0, plane = 0;
679     int8_t pixel = 0;
680     int i, j;
681
682     for (i = 0; i < src_size * 2;) {
683 #define GETNIBBLE ((i & 1) ?  (src[i>>1] & 0xF) : (src[i>>1] >> 4))
684         int d = tvdc[GETNIBBLE];
685         i++;
686         if (d) {
687             pixel += d;
688             dst[y * linesize + x*4 + plane] = pixel;
689             x++;
690         } else {
691             if (i >= src_size * 2)
692                 return;
693             d = GETNIBBLE + 1;
694             i++;
695             d = FFMIN(d, width - x);
696             for (j = 0; j < d; j++) {
697                 dst[y * linesize + x*4 + plane] = pixel;
698                 x++;
699             }
700         }
701         if (x >= width) {
702             plane++;
703             if (plane >= 4) {
704                 y++;
705                 if (y >= height)
706                     return;
707                 plane = 0;
708             }
709             x = 0;
710             pixel = 0;
711             i = (i + 1) & ~1;
712         }
713     }
714 }
715
716 static void decode_short_horizontal_delta(uint8_t *dst,
717                                           const uint8_t *buf, const uint8_t *buf_end,
718                                           int w, int bpp, int dst_size)
719 {
720     int planepitch = FFALIGN(w, 16) >> 3;
721     int pitch = planepitch * bpp;
722     GetByteContext ptrs, gb;
723     PutByteContext pb;
724     unsigned ofssrc, pos;
725     int i, k;
726
727     bytestream2_init(&ptrs, buf, buf_end - buf);
728     bytestream2_init_writer(&pb, dst, dst_size);
729
730     for (k = 0; k < bpp; k++) {
731         ofssrc = bytestream2_get_be32(&ptrs);
732         pos = 0;
733
734         if (!ofssrc)
735             continue;
736
737         if (ofssrc >= buf_end - buf)
738             continue;
739
740         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
741         while (bytestream2_peek_be16(&gb) != 0xFFFF && bytestream2_get_bytes_left(&gb) > 3) {
742             int16_t offset = bytestream2_get_be16(&gb);
743             unsigned noffset;
744
745             if (offset >= 0) {
746                 unsigned data = bytestream2_get_be16(&gb);
747
748                 pos += offset * 2;
749                 noffset = (pos / planepitch) * pitch + (pos % planepitch) + k * planepitch;
750                 bytestream2_seek_p(&pb, noffset, SEEK_SET);
751                 bytestream2_put_be16(&pb, data);
752             } else {
753                 uint16_t count = bytestream2_get_be16(&gb);
754
755                 pos += 2 * -(offset + 2);
756                 for (i = 0; i < count; i++) {
757                     uint16_t data = bytestream2_get_be16(&gb);
758
759                     pos += 2;
760                     noffset = (pos / planepitch) * pitch + (pos % planepitch) + k * planepitch;
761                     bytestream2_seek_p(&pb, noffset, SEEK_SET);
762                     bytestream2_put_be16(&pb, data);
763                 }
764             }
765         }
766     }
767 }
768
769 static void decode_byte_vertical_delta(uint8_t *dst,
770                                        const uint8_t *buf, const uint8_t *buf_end,
771                                        int w, int xor, int bpp, int dst_size)
772 {
773     int ncolumns = ((w + 15) / 16) * 2;
774     int dstpitch = ncolumns * bpp;
775     unsigned ofsdst, ofssrc, opcode, x;
776     GetByteContext ptrs, gb;
777     PutByteContext pb;
778     int i, j, k;
779
780     bytestream2_init(&ptrs, buf, buf_end - buf);
781     bytestream2_init_writer(&pb, dst, dst_size);
782
783     for (k = 0; k < bpp; k++) {
784         ofssrc = bytestream2_get_be32(&ptrs);
785
786         if (!ofssrc)
787             continue;
788
789         if (ofssrc >= buf_end - buf)
790             continue;
791
792         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
793         for (j = 0; j < ncolumns; j++) {
794             ofsdst = j + k * ncolumns;
795
796             i = bytestream2_get_byte(&gb);
797             while (i > 0) {
798                 opcode = bytestream2_get_byte(&gb);
799
800                 if (opcode == 0) {
801                     opcode  = bytestream2_get_byte(&gb);
802                     x = bytestream2_get_byte(&gb);
803
804                     while (opcode) {
805                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
806                         if (xor && ofsdst < dst_size) {
807                             bytestream2_put_byte(&pb, dst[ofsdst] ^ x);
808                         } else {
809                             bytestream2_put_byte(&pb, x);
810                         }
811                         ofsdst += dstpitch;
812                         opcode--;
813                     }
814                 } else if (opcode < 0x80) {
815                     ofsdst += opcode * dstpitch;
816                 } else {
817                     opcode &= 0x7f;
818
819                     while (opcode) {
820                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
821                         if (xor && ofsdst < dst_size) {
822                             bytestream2_put_byte(&pb, dst[ofsdst] ^ bytestream2_get_byte(&gb));
823                         } else {
824                             bytestream2_put_byte(&pb, bytestream2_get_byte(&gb));
825                         }
826                         ofsdst += dstpitch;
827                         opcode--;
828                     }
829                 }
830                 i--;
831             }
832         }
833     }
834 }
835
836 static void decode_delta_j(uint8_t *dst,
837                            const uint8_t *buf, const uint8_t *buf_end,
838                            int w, int h, int bpp, int dst_size)
839 {
840     int32_t pitch;
841     uint8_t *ptr;
842     uint32_t type, flag, cols, groups, rows, bytes;
843     uint32_t offset;
844     int planepitch_byte = (w + 7) / 8;
845     int planepitch = ((w + 15) / 16) * 2;
846     int kludge_j, b, g, r, d;
847     GetByteContext gb;
848
849     pitch = planepitch * bpp;
850     kludge_j = w < 320 ? (320 - w) / 8 / 2 : 0;
851
852     bytestream2_init(&gb, buf, buf_end - buf);
853
854     while (bytestream2_get_bytes_left(&gb) >= 2) {
855         type = bytestream2_get_be16(&gb);
856
857         switch (type) {
858         case 0:
859             return;
860         case 1:
861             flag   = bytestream2_get_be16(&gb);
862             cols   = bytestream2_get_be16(&gb);
863             groups = bytestream2_get_be16(&gb);
864
865             for (g = 0; g < groups; g++) {
866                 offset = bytestream2_get_be16(&gb);
867
868                 if (cols * bpp == 0 || bytestream2_get_bytes_left(&gb) < cols * bpp) {
869                     av_log(NULL, AV_LOG_ERROR, "cols*bpp is invalid (%d*%d)", cols, bpp);
870                     return;
871                 }
872
873                 if (kludge_j)
874                     offset = ((offset / (320 / 8)) * pitch) + (offset % (320 / 8)) - kludge_j;
875                 else
876                     offset = ((offset / planepitch_byte) * pitch) + (offset % planepitch_byte);
877
878                 for (b = 0; b < cols; b++) {
879                     for (d = 0; d < bpp; d++) {
880                         uint8_t value = bytestream2_get_byte(&gb);
881
882                         if (offset >= dst_size)
883                             return;
884                         ptr = dst + offset;
885
886                         if (flag)
887                             ptr[0] ^= value;
888                         else
889                             ptr[0]  = value;
890
891                         offset += planepitch;
892                     }
893                 }
894                 if ((cols * bpp) & 1)
895                     bytestream2_skip(&gb, 1);
896             }
897             break;
898         case 2:
899             flag   = bytestream2_get_be16(&gb);
900             rows   = bytestream2_get_be16(&gb);
901             bytes  = bytestream2_get_be16(&gb);
902             groups = bytestream2_get_be16(&gb);
903
904             for (g = 0; g < groups; g++) {
905                 offset = bytestream2_get_be16(&gb);
906
907                 if (kludge_j)
908                     offset = ((offset / (320 / 8)) * pitch) + (offset % (320/ 8)) - kludge_j;
909                 else
910                     offset = ((offset / planepitch_byte) * pitch) + (offset % planepitch_byte);
911
912                 for (r = 0; r < rows; r++) {
913                     for (d = 0; d < bpp; d++) {
914                         unsigned noffset = offset + (r * pitch) + d * planepitch;
915
916                         if (!bytes || bytestream2_get_bytes_left(&gb) < bytes) {
917                             av_log(NULL, AV_LOG_ERROR, "bytes %d is invalid", bytes);
918                             return;
919                         }
920
921                         for (b = 0; b < bytes; b++) {
922                             uint8_t value = bytestream2_get_byte(&gb);
923
924                             if (noffset >= dst_size)
925                                 return;
926                             ptr = dst + noffset;
927
928                             if (flag)
929                                 ptr[0] ^= value;
930                             else
931                                 ptr[0]  = value;
932
933                             noffset++;
934                         }
935                     }
936                 }
937                 if ((rows * bytes * bpp) & 1)
938                     bytestream2_skip(&gb, 1);
939             }
940             break;
941         default:
942             return;
943         }
944     }
945 }
946
947 static void decode_short_vertical_delta(uint8_t *dst,
948                                         const uint8_t *buf, const uint8_t *buf_end,
949                                         int w, int bpp, int dst_size)
950 {
951     int ncolumns = (w + 15) >> 4;
952     int dstpitch = ncolumns * bpp * 2;
953     unsigned ofsdst, ofssrc, ofsdata, opcode, x;
954     GetByteContext ptrs, gb, dptrs, dgb;
955     PutByteContext pb;
956     int i, j, k;
957
958     if (buf_end - buf <= 64)
959         return;
960
961     bytestream2_init(&ptrs, buf, buf_end - buf);
962     bytestream2_init(&dptrs, buf + 32, (buf_end - buf) - 32);
963     bytestream2_init_writer(&pb, dst, dst_size);
964
965     for (k = 0; k < bpp; k++) {
966         ofssrc = bytestream2_get_be32(&ptrs);
967         ofsdata = bytestream2_get_be32(&dptrs);
968
969         if (!ofssrc)
970             continue;
971
972         if (ofssrc >= buf_end - buf)
973             return;
974
975         if (ofsdata >= buf_end - buf)
976             return;
977
978         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
979         bytestream2_init(&dgb, buf + ofsdata, buf_end - (buf + ofsdata));
980         for (j = 0; j < ncolumns; j++) {
981             ofsdst = (j + k * ncolumns) * 2;
982
983             i = bytestream2_get_byte(&gb);
984             while (i > 0) {
985                 opcode = bytestream2_get_byte(&gb);
986
987                 if (opcode == 0) {
988                     opcode = bytestream2_get_byte(&gb);
989                     x = bytestream2_get_be16(&dgb);
990
991                     while (opcode) {
992                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
993                         bytestream2_put_be16(&pb, x);
994                         ofsdst += dstpitch;
995                         opcode--;
996                     }
997                 } else if (opcode < 0x80) {
998                     ofsdst += opcode * dstpitch;
999                 } else {
1000                     opcode &= 0x7f;
1001
1002                     while (opcode) {
1003                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1004                         bytestream2_put_be16(&pb, bytestream2_get_be16(&dgb));
1005                         ofsdst += dstpitch;
1006                         opcode--;
1007                     }
1008                 }
1009                 i--;
1010             }
1011         }
1012     }
1013 }
1014
1015 static void decode_long_vertical_delta(uint8_t *dst,
1016                                        const uint8_t *buf, const uint8_t *buf_end,
1017                                        int w, int bpp, int dst_size)
1018 {
1019     int ncolumns = (w + 31) >> 5;
1020     int dstpitch = ((w + 15) / 16 * 2) * bpp;
1021     unsigned ofsdst, ofssrc, ofsdata, opcode, x;
1022     GetByteContext ptrs, gb, dptrs, dgb;
1023     PutByteContext pb;
1024     int i, j, k, h;
1025
1026     if (buf_end - buf <= 64)
1027         return;
1028
1029     h = (((w + 15) / 16 * 2) != ((w + 31) / 32 * 4)) ? 1 : 0;
1030     bytestream2_init(&ptrs, buf, buf_end - buf);
1031     bytestream2_init(&dptrs, buf + 32, (buf_end - buf) - 32);
1032     bytestream2_init_writer(&pb, dst, dst_size);
1033
1034     for (k = 0; k < bpp; k++) {
1035         ofssrc = bytestream2_get_be32(&ptrs);
1036         ofsdata = bytestream2_get_be32(&dptrs);
1037
1038         if (!ofssrc)
1039             continue;
1040
1041         if (ofssrc >= buf_end - buf)
1042             return;
1043
1044         if (ofsdata >= buf_end - buf)
1045             return;
1046
1047         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
1048         bytestream2_init(&dgb, buf + ofsdata, buf_end - (buf + ofsdata));
1049         for (j = 0; j < ncolumns; j++) {
1050             ofsdst = (j + k * ncolumns) * 4 - h * (2 * k);
1051
1052             i = bytestream2_get_byte(&gb);
1053             while (i > 0) {
1054                 opcode = bytestream2_get_byte(&gb);
1055
1056                 if (opcode == 0) {
1057                     opcode = bytestream2_get_byte(&gb);
1058                     if (h && (j == (ncolumns - 1))) {
1059                         x = bytestream2_get_be16(&dgb);
1060                         bytestream2_skip(&dgb, 2);
1061                     } else {
1062                         x = bytestream2_get_be32(&dgb);
1063                     }
1064
1065                     while (opcode) {
1066                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1067                         if (h && (j == (ncolumns - 1))) {
1068                             bytestream2_put_be16(&pb, x);
1069                         } else {
1070                             bytestream2_put_be32(&pb, x);
1071                         }
1072                         ofsdst += dstpitch;
1073                         opcode--;
1074                     }
1075                 } else if (opcode < 0x80) {
1076                     ofsdst += opcode * dstpitch;
1077                 } else {
1078                     opcode &= 0x7f;
1079
1080                     while (opcode) {
1081                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1082                         if (h && (j == (ncolumns - 1))) {
1083                             bytestream2_put_be16(&pb, bytestream2_get_be16(&dgb));
1084                             bytestream2_skip(&dgb, 2);
1085                         } else {
1086                             bytestream2_put_be32(&pb, bytestream2_get_be32(&dgb));
1087                         }
1088                         ofsdst += dstpitch;
1089                         opcode--;
1090                     }
1091                 }
1092                 i--;
1093             }
1094         }
1095     }
1096 }
1097
1098 static void decode_short_vertical_delta2(uint8_t *dst,
1099                                          const uint8_t *buf, const uint8_t *buf_end,
1100                                          int w, int bpp, int dst_size)
1101 {
1102     int ncolumns = (w + 15) >> 4;
1103     int dstpitch = ncolumns * bpp * 2;
1104     unsigned ofsdst, ofssrc, opcode, x;
1105     GetByteContext ptrs, gb;
1106     PutByteContext pb;
1107     int i, j, k;
1108
1109     bytestream2_init(&ptrs, buf, buf_end - buf);
1110     bytestream2_init_writer(&pb, dst, dst_size);
1111
1112     for (k = 0; k < bpp; k++) {
1113         ofssrc = bytestream2_get_be32(&ptrs);
1114
1115         if (!ofssrc)
1116             continue;
1117
1118         if (ofssrc >= buf_end - buf)
1119             continue;
1120
1121         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
1122         for (j = 0; j < ncolumns; j++) {
1123             ofsdst = (j + k * ncolumns) * 2;
1124
1125             i = bytestream2_get_be16(&gb);
1126             while (i > 0 && bytestream2_get_bytes_left(&gb) > 4) {
1127                 opcode = bytestream2_get_be16(&gb);
1128
1129                 if (opcode == 0) {
1130                     opcode = bytestream2_get_be16(&gb);
1131                     x = bytestream2_get_be16(&gb);
1132
1133                     while (opcode && bytestream2_get_bytes_left_p(&pb) > 1) {
1134                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1135                         bytestream2_put_be16(&pb, x);
1136                         ofsdst += dstpitch;
1137                         opcode--;
1138                     }
1139                 } else if (opcode < 0x8000) {
1140                     ofsdst += opcode * dstpitch;
1141                 } else {
1142                     opcode &= 0x7fff;
1143
1144                     while (opcode && bytestream2_get_bytes_left(&gb) > 1 &&
1145                            bytestream2_get_bytes_left_p(&pb) > 1) {
1146                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1147                         bytestream2_put_be16(&pb, bytestream2_get_be16(&gb));
1148                         ofsdst += dstpitch;
1149                         opcode--;
1150                     }
1151                 }
1152                 i--;
1153             }
1154         }
1155     }
1156 }
1157
1158 static void decode_long_vertical_delta2(uint8_t *dst,
1159                                         const uint8_t *buf, const uint8_t *buf_end,
1160                                         int w, int bpp, int dst_size)
1161 {
1162     int ncolumns = (w + 31) >> 5;
1163     int dstpitch = ((w + 15) / 16 * 2) * bpp;
1164     unsigned ofsdst, ofssrc, opcode, x;
1165     unsigned skip = 0x80000000, mask = skip - 1;
1166     GetByteContext ptrs, gb;
1167     PutByteContext pb;
1168     int i, j, k, h;
1169
1170     h = (((w + 15) / 16 * 2) != ((w + 31) / 32 * 4)) ? 1 : 0;
1171     bytestream2_init(&ptrs, buf, buf_end - buf);
1172     bytestream2_init_writer(&pb, dst, dst_size);
1173
1174     for (k = 0; k < bpp; k++) {
1175         ofssrc = bytestream2_get_be32(&ptrs);
1176
1177         if (!ofssrc)
1178             continue;
1179
1180         if (ofssrc >= buf_end - buf)
1181             continue;
1182
1183         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
1184         for (j = 0; j < ncolumns; j++) {
1185             ofsdst = (j + k * ncolumns) * 4 - h * (2 * k);
1186
1187             if (h && (j == (ncolumns - 1))) {
1188                 skip = 0x8000;
1189                 mask = skip - 1;
1190             }
1191
1192             i = bytestream2_get_be32(&gb);
1193             while (i > 0 && bytestream2_get_bytes_left(&gb) > 4) {
1194                 opcode = bytestream2_get_be32(&gb);
1195
1196                 if (opcode == 0) {
1197                     if (h && (j == ncolumns - 1)) {
1198                         opcode = bytestream2_get_be16(&gb);
1199                         x = bytestream2_get_be16(&gb);
1200                     } else {
1201                         opcode = bytestream2_get_be32(&gb);
1202                         x = bytestream2_get_be32(&gb);
1203                     }
1204
1205                     while (opcode && bytestream2_get_bytes_left_p(&pb) > 1) {
1206                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1207                         if (h && (j == ncolumns - 1))
1208                             bytestream2_put_be16(&pb, x);
1209                         else
1210                             bytestream2_put_be32(&pb, x);
1211                         ofsdst += dstpitch;
1212                         opcode--;
1213                     }
1214                 } else if (opcode < skip) {
1215                     ofsdst += opcode * dstpitch;
1216                 } else {
1217                     opcode &= mask;
1218
1219                     while (opcode && bytestream2_get_bytes_left(&gb) > 1 &&
1220                            bytestream2_get_bytes_left_p(&pb) > 1) {
1221                         bytestream2_seek_p(&pb, ofsdst, SEEK_SET);
1222                         if (h && (j == ncolumns - 1)) {
1223                             bytestream2_put_be16(&pb, bytestream2_get_be16(&gb));
1224                         } else {
1225                             bytestream2_put_be32(&pb, bytestream2_get_be32(&gb));
1226                         }
1227                         ofsdst += dstpitch;
1228                         opcode--;
1229                     }
1230                 }
1231                 i--;
1232             }
1233         }
1234     }
1235 }
1236
1237 static void decode_delta_d(uint8_t *dst,
1238                            const uint8_t *buf, const uint8_t *buf_end,
1239                            int w, int flag, int bpp, int dst_size)
1240 {
1241     int planepitch = FFALIGN(w, 16) >> 3;
1242     int pitch = planepitch * bpp;
1243     int planepitch_byte = (w + 7) / 8;
1244     unsigned entries, ofssrc;
1245     GetByteContext gb, ptrs;
1246     PutByteContext pb;
1247     int k;
1248
1249     if (buf_end - buf <= 4 * bpp)
1250         return;
1251
1252     bytestream2_init_writer(&pb, dst, dst_size);
1253     bytestream2_init(&ptrs, buf, bpp * 4);
1254
1255     for (k = 0; k < bpp; k++) {
1256         ofssrc = bytestream2_get_be32(&ptrs);
1257
1258         if (!ofssrc)
1259             continue;
1260
1261         if (ofssrc >= buf_end - buf)
1262             continue;
1263
1264         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
1265
1266         entries = bytestream2_get_be32(&gb);
1267         while (entries && bytestream2_get_bytes_left(&gb) >= 8) {
1268             int32_t opcode  = bytestream2_get_be32(&gb);
1269             unsigned offset = bytestream2_get_be32(&gb);
1270
1271             bytestream2_seek_p(&pb, (offset / planepitch_byte) * pitch + (offset % planepitch_byte) + k * planepitch, SEEK_SET);
1272             if (opcode >= 0) {
1273                 uint32_t x = bytestream2_get_be32(&gb);
1274                 while (opcode && bytestream2_get_bytes_left_p(&pb) > 0) {
1275                     bytestream2_put_be32(&pb, x);
1276                     bytestream2_skip_p(&pb, pitch - 4);
1277                     opcode--;
1278                 }
1279             } else {
1280                 opcode = -opcode;
1281                 while (opcode && bytestream2_get_bytes_left(&gb) > 0) {
1282                     bytestream2_put_be32(&pb, bytestream2_get_be32(&gb));
1283                     bytestream2_skip_p(&pb, pitch - 4);
1284                     opcode--;
1285                 }
1286             }
1287             entries--;
1288         }
1289     }
1290 }
1291
1292 static void decode_delta_e(uint8_t *dst,
1293                            const uint8_t *buf, const uint8_t *buf_end,
1294                            int w, int flag, int bpp, int dst_size)
1295 {
1296     int planepitch = FFALIGN(w, 16) >> 3;
1297     int pitch = planepitch * bpp;
1298     int planepitch_byte = (w + 7) / 8;
1299     unsigned entries, ofssrc;
1300     GetByteContext gb, ptrs;
1301     PutByteContext pb;
1302     int k;
1303
1304     if (buf_end - buf <= 4 * bpp)
1305         return;
1306
1307     bytestream2_init_writer(&pb, dst, dst_size);
1308     bytestream2_init(&ptrs, buf, bpp * 4);
1309
1310     for (k = 0; k < bpp; k++) {
1311         ofssrc = bytestream2_get_be32(&ptrs);
1312
1313         if (!ofssrc)
1314             continue;
1315
1316         if (ofssrc >= buf_end - buf)
1317             continue;
1318
1319         bytestream2_init(&gb, buf + ofssrc, buf_end - (buf + ofssrc));
1320
1321         entries = bytestream2_get_be16(&gb);
1322         while (entries && bytestream2_get_bytes_left(&gb) >= 6) {
1323             int16_t opcode  = bytestream2_get_be16(&gb);
1324             unsigned offset = bytestream2_get_be32(&gb);
1325
1326             bytestream2_seek_p(&pb, (offset / planepitch_byte) * pitch + (offset % planepitch_byte) + k * planepitch, SEEK_SET);
1327             if (opcode >= 0) {
1328                 uint16_t x = bytestream2_get_be16(&gb);
1329                 while (opcode && bytestream2_get_bytes_left_p(&pb) > 0) {
1330                     bytestream2_put_be16(&pb, x);
1331                     bytestream2_skip_p(&pb, pitch - 2);
1332                     opcode--;
1333                 }
1334             } else {
1335                 opcode = -opcode;
1336                 while (opcode && bytestream2_get_bytes_left(&gb) > 0) {
1337                     bytestream2_put_be16(&pb, bytestream2_get_be16(&gb));
1338                     bytestream2_skip_p(&pb, pitch - 2);
1339                     opcode--;
1340                 }
1341             }
1342             entries--;
1343         }
1344     }
1345 }
1346
1347 static void decode_delta_l(uint8_t *dst,
1348                            const uint8_t *buf, const uint8_t *buf_end,
1349                            int w, int flag, int bpp, int dst_size)
1350 {
1351     GetByteContext off0, off1, dgb, ogb;
1352     PutByteContext pb;
1353     unsigned poff0, poff1;
1354     int i, k, dstpitch;
1355     int planepitch_byte = (w + 7) / 8;
1356     int planepitch = ((w + 15) / 16) * 2;
1357     int pitch = planepitch * bpp;
1358
1359     if (buf_end - buf <= 64)
1360         return;
1361
1362     bytestream2_init(&off0, buf, buf_end - buf);
1363     bytestream2_init(&off1, buf + 32, buf_end - (buf + 32));
1364     bytestream2_init_writer(&pb, dst, dst_size);
1365
1366     dstpitch = flag ? (((w + 7) / 8) * bpp): 2;
1367
1368     for (k = 0; k < bpp; k++) {
1369         poff0 = bytestream2_get_be32(&off0);
1370         poff1 = bytestream2_get_be32(&off1);
1371
1372         if (!poff0)
1373             continue;
1374
1375         if (2LL * poff0 >= buf_end - buf)
1376             return;
1377
1378         if (2LL * poff1 >= buf_end - buf)
1379             return;
1380
1381         bytestream2_init(&dgb, buf + 2 * poff0, buf_end - (buf + 2 * poff0));
1382         bytestream2_init(&ogb, buf + 2 * poff1, buf_end - (buf + 2 * poff1));
1383
1384         while (bytestream2_peek_be16(&ogb) != 0xFFFF && bytestream2_get_bytes_left(&ogb) >= 4) {
1385             uint32_t offset = bytestream2_get_be16(&ogb);
1386             int16_t cnt = bytestream2_get_be16(&ogb);
1387             uint16_t data;
1388
1389             offset = ((2 * offset) / planepitch_byte) * pitch + ((2 * offset) % planepitch_byte) + k * planepitch;
1390             if (cnt < 0) {
1391                 if (bytestream2_get_bytes_left(&dgb) < 2)
1392                     break;
1393                 bytestream2_seek_p(&pb, offset, SEEK_SET);
1394                 cnt = -cnt;
1395                 data = bytestream2_get_be16(&dgb);
1396                 for (i = 0; i < cnt; i++) {
1397                     bytestream2_put_be16(&pb, data);
1398                     bytestream2_skip_p(&pb, dstpitch - 2);
1399                 }
1400             } else {
1401                 if (bytestream2_get_bytes_left(&dgb) < 2*cnt)
1402                     break;
1403                 bytestream2_seek_p(&pb, offset, SEEK_SET);
1404                 for (i = 0; i < cnt; i++) {
1405                     data = bytestream2_get_be16(&dgb);
1406                     bytestream2_put_be16(&pb, data);
1407                     bytestream2_skip_p(&pb, dstpitch - 2);
1408                 }
1409             }
1410         }
1411     }
1412 }
1413
1414 static int unsupported(AVCodecContext *avctx)
1415 {
1416     IffContext *s = avctx->priv_data;
1417     avpriv_request_sample(avctx, "bitmap (compression 0x%0x, bpp %i, ham %i, interlaced %i)", s->compression, s->bpp, s->ham, s->is_interlaced);
1418     return AVERROR_INVALIDDATA;
1419 }
1420
1421 static int decode_frame(AVCodecContext *avctx,
1422                         void *data, int *got_frame,
1423                         AVPacket *avpkt)
1424 {
1425     IffContext *s          = avctx->priv_data;
1426     AVFrame *frame         = data;
1427     const uint8_t *buf     = avpkt->data;
1428     int buf_size           = avpkt->size;
1429     const uint8_t *buf_end = buf + buf_size;
1430     int y, plane, res;
1431     GetByteContext *gb = &s->gb;
1432     const AVPixFmtDescriptor *desc;
1433
1434     bytestream2_init(gb, avpkt->data, avpkt->size);
1435
1436     if ((res = extract_header(avctx, avpkt)) < 0)
1437         return res;
1438
1439     if ((res = ff_get_buffer(avctx, frame, 0)) < 0)
1440         return res;
1441     s->frame = frame;
1442
1443     buf      += bytestream2_tell(gb);
1444     buf_size -= bytestream2_tell(gb);
1445     desc = av_pix_fmt_desc_get(avctx->pix_fmt);
1446
1447     if (!s->init && avctx->bits_per_coded_sample <= 8 &&
1448         avctx->pix_fmt == AV_PIX_FMT_PAL8) {
1449         if ((res = cmap_read_palette(avctx, (uint32_t *)frame->data[1])) < 0)
1450             return res;
1451     } else if (!s->init && avctx->bits_per_coded_sample <= 8 &&
1452                avctx->pix_fmt == AV_PIX_FMT_RGB32) {
1453         if ((res = cmap_read_palette(avctx, s->mask_palbuf)) < 0)
1454             return res;
1455     }
1456     s->init = 1;
1457
1458     if (s->compression <= 0xff && (avctx->codec_tag == MKTAG('A', 'N', 'I', 'M'))) {
1459         if (avctx->pix_fmt == AV_PIX_FMT_PAL8)
1460             memcpy(s->pal[0], s->frame->data[1], 256 * 4);
1461     }
1462
1463     switch (s->compression) {
1464     case 0x0:
1465         if (avctx->codec_tag == MKTAG('A', 'C', 'B', 'M')) {
1466             if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
1467                 memset(frame->data[0], 0, avctx->height * frame->linesize[0]);
1468                 for (plane = 0; plane < s->bpp; plane++) {
1469                     for (y = 0; y < avctx->height && buf < buf_end; y++) {
1470                         uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1471                         decodeplane8(row, buf, FFMIN(s->planesize, buf_end - buf), plane);
1472                         buf += s->planesize;
1473                     }
1474                 }
1475             } else if (s->ham) { // HAM to AV_PIX_FMT_BGR32
1476                 memset(frame->data[0], 0, avctx->height * frame->linesize[0]);
1477                 for (y = 0; y < avctx->height; y++) {
1478                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1479                     memset(s->ham_buf, 0, s->planesize * 8);
1480                     for (plane = 0; plane < s->bpp; plane++) {
1481                         const uint8_t * start = buf + (plane * avctx->height + y) * s->planesize;
1482                         if (start >= buf_end)
1483                             break;
1484                         decodeplane8(s->ham_buf, start, FFMIN(s->planesize, buf_end - start), plane);
1485                     }
1486                     decode_ham_plane32((uint32_t *)row, s->ham_buf, s->ham_palbuf, s->planesize);
1487                 }
1488             } else
1489                 return unsupported(avctx);
1490         } else if (avctx->codec_tag == MKTAG('D', 'E', 'E', 'P')) {
1491             int raw_width = avctx->width * (av_get_bits_per_pixel(desc) >> 3);
1492             int x;
1493             for (y = 0; y < avctx->height && buf < buf_end; y++) {
1494                 uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1495                 memcpy(row, buf, FFMIN(raw_width, buf_end - buf));
1496                 buf += raw_width;
1497                 if (avctx->pix_fmt == AV_PIX_FMT_BGR32) {
1498                     for (x = 0; x < avctx->width; x++)
1499                         row[4 * x + 3] = row[4 * x + 3] & 0xF0 | (row[4 * x + 3] >> 4);
1500                 }
1501             }
1502         } else if (avctx->codec_tag == MKTAG('I', 'L', 'B', 'M') || // interleaved
1503                    avctx->codec_tag == MKTAG('A', 'N', 'I', 'M')) {
1504             if (avctx->codec_tag == MKTAG('A', 'N', 'I', 'M'))
1505                 memcpy(s->video[0], buf, FFMIN(buf_end - buf, s->video_size));
1506             if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
1507                 for (y = 0; y < avctx->height; y++) {
1508                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1509                     memset(row, 0, avctx->width);
1510                     for (plane = 0; plane < s->bpp && buf < buf_end; plane++) {
1511                         decodeplane8(row, buf, FFMIN(s->planesize, buf_end - buf), plane);
1512                         buf += s->planesize;
1513                     }
1514                 }
1515             } else if (s->ham) { // HAM to AV_PIX_FMT_BGR32
1516                 for (y = 0; y < avctx->height; y++) {
1517                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1518                     memset(s->ham_buf, 0, s->planesize * 8);
1519                     for (plane = 0; plane < s->bpp && buf < buf_end; plane++) {
1520                         decodeplane8(s->ham_buf, buf, FFMIN(s->planesize, buf_end - buf), plane);
1521                         buf += s->planesize;
1522                     }
1523                     decode_ham_plane32((uint32_t *)row, s->ham_buf, s->ham_palbuf, s->planesize);
1524                 }
1525             } else { // AV_PIX_FMT_BGR32
1526                 for (y = 0; y < avctx->height; y++) {
1527                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1528                     memset(row, 0, avctx->width << 2);
1529                     for (plane = 0; plane < s->bpp && buf < buf_end; plane++) {
1530                         decodeplane32((uint32_t *)row, buf,
1531                                       FFMIN(s->planesize, buf_end - buf), plane);
1532                         buf += s->planesize;
1533                     }
1534                 }
1535             }
1536         } else if (avctx->codec_tag == MKTAG('P', 'B', 'M', ' ')) { // IFF-PBM
1537             if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
1538                 for (y = 0; y < avctx->height && buf_end > buf; y++) {
1539                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1540                     memcpy(row, buf, FFMIN(avctx->width, buf_end - buf));
1541                     buf += avctx->width + (avctx->width % 2); // padding if odd
1542                 }
1543             } else if (s->ham) { // IFF-PBM: HAM to AV_PIX_FMT_BGR32
1544                 for (y = 0; y < avctx->height && buf_end > buf; y++) {
1545                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1546                     memcpy(s->ham_buf, buf, FFMIN(avctx->width, buf_end - buf));
1547                     buf += avctx->width + (avctx->width & 1); // padding if odd
1548                     decode_ham_plane32((uint32_t *)row, s->ham_buf, s->ham_palbuf, s->planesize);
1549                 }
1550             } else
1551                 return unsupported(avctx);
1552         }
1553         break;
1554     case 0x1:
1555         if (avctx->codec_tag == MKTAG('I', 'L', 'B', 'M') || // interleaved
1556             avctx->codec_tag == MKTAG('A', 'N', 'I', 'M')) {
1557             if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
1558                 uint8_t *video = s->video[0];
1559
1560                 for (y = 0; y < avctx->height; y++) {
1561                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1562                     memset(row, 0, avctx->width);
1563                     for (plane = 0; plane < s->bpp; plane++) {
1564                         buf += decode_byterun(s->planebuf, s->planesize, gb);
1565                         if (avctx->codec_tag == MKTAG('A', 'N', 'I', 'M')) {
1566                             memcpy(video, s->planebuf, s->planesize);
1567                             video += s->planesize;
1568                         }
1569                         decodeplane8(row, s->planebuf, s->planesize, plane);
1570                     }
1571                 }
1572             } else if (avctx->bits_per_coded_sample <= 8) { //8-bit (+ mask) to AV_PIX_FMT_BGR32
1573                 for (y = 0; y < avctx->height; y++) {
1574                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1575                     memset(s->mask_buf, 0, avctx->width * sizeof(uint32_t));
1576                     for (plane = 0; plane < s->bpp; plane++) {
1577                         buf += decode_byterun(s->planebuf, s->planesize, gb);
1578                         decodeplane32(s->mask_buf, s->planebuf, s->planesize, plane);
1579                     }
1580                     lookup_pal_indicies((uint32_t *)row, s->mask_buf, s->mask_palbuf, avctx->width);
1581                 }
1582             } else if (s->ham) { // HAM to AV_PIX_FMT_BGR32
1583                 uint8_t *video = s->video[0];
1584                 for (y = 0; y < avctx->height; y++) {
1585                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1586                     memset(s->ham_buf, 0, s->planesize * 8);
1587                     for (plane = 0; plane < s->bpp; plane++) {
1588                         buf += decode_byterun(s->planebuf, s->planesize, gb);
1589                         if (avctx->codec_tag == MKTAG('A', 'N', 'I', 'M')) {
1590                             memcpy(video, s->planebuf, s->planesize);
1591                             video += s->planesize;
1592                         }
1593                         decodeplane8(s->ham_buf, s->planebuf, s->planesize, plane);
1594                     }
1595                     decode_ham_plane32((uint32_t *)row, s->ham_buf, s->ham_palbuf, s->planesize);
1596                 }
1597             } else { // AV_PIX_FMT_BGR32
1598                 for (y = 0; y < avctx->height; y++) {
1599                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1600                     memset(row, 0, avctx->width << 2);
1601                     for (plane = 0; plane < s->bpp; plane++) {
1602                         buf += decode_byterun(s->planebuf, s->planesize, gb);
1603                         decodeplane32((uint32_t *)row, s->planebuf, s->planesize, plane);
1604                     }
1605                 }
1606             }
1607         } else if (avctx->codec_tag == MKTAG('P', 'B', 'M', ' ')) { // IFF-PBM
1608             if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
1609                 for (y = 0; y < avctx->height; y++) {
1610                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1611                     buf += decode_byterun(row, avctx->width, gb);
1612                 }
1613             } else if (s->ham) { // IFF-PBM: HAM to AV_PIX_FMT_BGR32
1614                 for (y = 0; y < avctx->height; y++) {
1615                     uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1616                     buf += decode_byterun(s->ham_buf, avctx->width, gb);
1617                     decode_ham_plane32((uint32_t *)row, s->ham_buf, s->ham_palbuf, s->planesize);
1618                 }
1619             } else
1620                 return unsupported(avctx);
1621         } else if (avctx->codec_tag == MKTAG('D', 'E', 'E', 'P')) { // IFF-DEEP
1622             if (av_get_bits_per_pixel(desc) == 32)
1623                 decode_deep_rle32(frame->data[0], buf, buf_size, avctx->width, avctx->height, frame->linesize[0]);
1624             else
1625                 return unsupported(avctx);
1626         }
1627         break;
1628     case 0x4:
1629         if (avctx->codec_tag == MKTAG('R', 'G', 'B', '8') && avctx->pix_fmt == AV_PIX_FMT_RGB32)
1630             decode_rgb8(gb, frame->data[0], avctx->width, avctx->height, frame->linesize[0]);
1631         else if (avctx->codec_tag == MKTAG('R', 'G', 'B', 'N') && avctx->pix_fmt == AV_PIX_FMT_RGB444)
1632             decode_rgbn(gb, frame->data[0], avctx->width, avctx->height, frame->linesize[0]);
1633         else
1634             return unsupported(avctx);
1635         break;
1636     case 0x5:
1637         if (avctx->codec_tag == MKTAG('D', 'E', 'E', 'P')) {
1638             if (av_get_bits_per_pixel(desc) == 32)
1639                 decode_deep_tvdc32(frame->data[0], buf, buf_size, avctx->width, avctx->height, frame->linesize[0], s->tvdc);
1640             else
1641                 return unsupported(avctx);
1642         } else
1643             return unsupported(avctx);
1644         break;
1645     case 0x300:
1646     case 0x301:
1647         decode_short_horizontal_delta(s->video[0], buf, buf_end, avctx->width, s->bpp, s->video_size);
1648         break;
1649     case 0x500:
1650     case 0x501:
1651         decode_byte_vertical_delta(s->video[0], buf, buf_end, avctx->width, s->is_brush, s->bpp, s->video_size);
1652         break;
1653     case 0x700:
1654     case 0x701:
1655         if (s->is_short)
1656             decode_short_vertical_delta(s->video[0], buf, buf_end, avctx->width, s->bpp, s->video_size);
1657         else
1658             decode_long_vertical_delta(s->video[0], buf, buf_end, avctx->width, s->bpp, s->video_size);
1659         break;
1660     case 0x800:
1661     case 0x801:
1662         if (s->is_short)
1663             decode_short_vertical_delta2(s->video[0], buf, buf_end, avctx->width, s->bpp, s->video_size);
1664         else
1665             decode_long_vertical_delta2(s->video[0], buf, buf_end, avctx->width, s->bpp, s->video_size);
1666         break;
1667     case 0x4a00:
1668     case 0x4a01:
1669         decode_delta_j(s->video[0], buf, buf_end, avctx->width, avctx->height, s->bpp, s->video_size);
1670         break;
1671     case 0x6400:
1672     case 0x6401:
1673         if (s->is_interlaced)
1674             return unsupported(avctx);
1675         decode_delta_d(s->video[0], buf, buf_end, avctx->width, s->is_interlaced, s->bpp, s->video_size);
1676         break;
1677     case 0x6500:
1678     case 0x6501:
1679         if (s->is_interlaced)
1680             return unsupported(avctx);
1681         decode_delta_e(s->video[0], buf, buf_end, avctx->width, s->is_interlaced, s->bpp, s->video_size);
1682         break;
1683     case 0x6c00:
1684     case 0x6c01:
1685         decode_delta_l(s->video[0], buf, buf_end, avctx->width, s->is_short, s->bpp, s->video_size);
1686         break;
1687     default:
1688         return unsupported(avctx);
1689     }
1690
1691     if (s->compression <= 0xff && (avctx->codec_tag == MKTAG('A', 'N', 'I', 'M'))) {
1692         memcpy(s->pal[1], s->pal[0], 256 * 4);
1693         memcpy(s->video[1], s->video[0], s->video_size);
1694     }
1695
1696     if (s->compression > 0xff) {
1697         if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
1698             buf = s->video[0];
1699             for (y = 0; y < avctx->height; y++) {
1700                 uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1701                 memset(row, 0, avctx->width);
1702                 for (plane = 0; plane < s->bpp; plane++) {
1703                     decodeplane8(row, buf, s->planesize, plane);
1704                     buf += s->planesize;
1705                 }
1706             }
1707             memcpy(frame->data[1], s->pal[0], 256 * 4);
1708         } else if (s->ham) {
1709             int i, count = 1 << s->ham;
1710
1711             buf = s->video[0];
1712             memset(s->ham_palbuf, 0, (1 << s->ham) * 2 * sizeof(uint32_t));
1713             for (i = 0; i < count; i++) {
1714                 s->ham_palbuf[i*2+1] = s->pal[0][i];
1715             }
1716             for (i = 0; i < count; i++) {
1717                 uint32_t tmp = i << (8 - s->ham);
1718                 tmp |= tmp >> s->ham;
1719                 s->ham_palbuf[(i+count)*2]     = 0xFF00FFFF;
1720                 s->ham_palbuf[(i+count*2)*2]   = 0xFFFFFF00;
1721                 s->ham_palbuf[(i+count*3)*2]   = 0xFFFF00FF;
1722                 s->ham_palbuf[(i+count)*2+1]   = 0xFF000000 | tmp << 16;
1723                 s->ham_palbuf[(i+count*2)*2+1] = 0xFF000000 | tmp;
1724                 s->ham_palbuf[(i+count*3)*2+1] = 0xFF000000 | tmp << 8;
1725             }
1726             if (s->masking == MASK_HAS_MASK) {
1727                 for (i = 0; i < 8 * (1 << s->ham); i++)
1728                     s->ham_palbuf[(1 << s->bpp) + i] = s->ham_palbuf[i] | 0xFF000000;
1729             }
1730             for (y = 0; y < avctx->height; y++) {
1731                 uint8_t *row = &frame->data[0][y * frame->linesize[0]];
1732                 memset(s->ham_buf, 0, s->planesize * 8);
1733                 for (plane = 0; plane < s->bpp; plane++) {
1734                     decodeplane8(s->ham_buf, buf, s->planesize, plane);
1735                     buf += s->planesize;
1736                 }
1737                 decode_ham_plane32((uint32_t *)row, s->ham_buf, s->ham_palbuf, s->planesize);
1738             }
1739         } else {
1740             return unsupported(avctx);
1741         }
1742
1743         if (!s->is_brush) {
1744             FFSWAP(uint8_t *, s->video[0], s->video[1]);
1745             FFSWAP(uint32_t *, s->pal[0], s->pal[1]);
1746         }
1747     }
1748
1749     if (avpkt->flags & AV_PKT_FLAG_KEY) {
1750         frame->key_frame = 1;
1751         frame->pict_type = AV_PICTURE_TYPE_I;
1752     } else {
1753         frame->key_frame = 0;
1754         frame->pict_type = AV_PICTURE_TYPE_P;
1755     }
1756
1757     *got_frame = 1;
1758
1759     return buf_size;
1760 }
1761
1762 #if CONFIG_IFF_ILBM_DECODER
1763 AVCodec ff_iff_ilbm_decoder = {
1764     .name           = "iff",
1765     .long_name      = NULL_IF_CONFIG_SMALL("IFF ACBM/ANIM/DEEP/ILBM/PBM/RGB8/RGBN"),
1766     .type           = AVMEDIA_TYPE_VIDEO,
1767     .id             = AV_CODEC_ID_IFF_ILBM,
1768     .priv_data_size = sizeof(IffContext),
1769     .init           = decode_init,
1770     .close          = decode_end,
1771     .decode         = decode_frame,
1772     .capabilities   = AV_CODEC_CAP_DR1,
1773 };
1774 #endif