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