FFmpeg
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
iff.c
Go to the documentation of this file.
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 {
44 } mask_type;
45 
46 typedef struct IffContext {
48  int planesize;
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
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);
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 
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 
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 
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
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;
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 
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 
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 
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 
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 
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 
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
int plane
Definition: avisynth_c.h:291
Definition: iff.c:43
#define NULL
Definition: coverity.c:32
unsigned is_brush
video is in ANBR format
Definition: iff.c:57
const char * s
Definition: avisynth_c.h:631
#define AVERROR_INVALIDDATA
Invalid data found when processing input.
Definition: error.h:59
static void decodeplane32(uint32_t *dst, const uint8_t *buf, int buf_size, int plane)
Decode interleaved plane buffer up to 24bpp.
Definition: iff.c:467
unsigned compression
delta compression method used
Definition: iff.c:54
const AVPixFmtDescriptor * av_pix_fmt_desc_get(enum AVPixelFormat pix_fmt)
Definition: pixdesc.c:2263
This structure describes decoded (raw) audio or video data.
Definition: frame.h:184
ptrdiff_t const GLvoid * data
Definition: opengl_enc.c:101
uint32_t * mask_palbuf
masking palette table
Definition: iff.c:53
misc image utilities
#define AV_LOG_WARNING
Something somehow does not look correct.
Definition: log.h:182
unsigned masking
TODO: masking method used.
Definition: iff.c:62
const char * g
Definition: vf_curves.c:108
const char * desc
Definition: nvenc.c:89
static av_cold int init(AVCodecContext *avctx)
Definition: avrndec.c:35
int av_get_bits_per_pixel(const AVPixFmtDescriptor *pixdesc)
Return the number of bits per pixel used by the pixel format described by pixdesc.
Definition: pixdesc.c:2215
unsigned transparency
TODO: transparency color index in palette.
Definition: iff.c:61
static int cmap_read_palette(AVCodecContext *avctx, uint32_t *pal)
Convert CMAP buffer (stored in extradata) to lavc palette format.
Definition: iff.c:153
GetByteContext gb
Definition: iff.c:65
int size
Definition: avcodec.h:1589
const char * b
Definition: vf_curves.c:109
int flag
Definition: cpu.c:34
static av_always_inline void bytestream2_init_writer(PutByteContext *p, uint8_t *buf, int buf_size)
Definition: bytestream.h:143
enum AVPixelFormat pix_fmt
Pixel format, see AV_PIX_FMT_xxx.
Definition: avcodec.h:1885
static av_always_inline void bytestream2_init(GetByteContext *g, const uint8_t *buf, int buf_size)
Definition: bytestream.h:133
#define av_le2ne32(x)
Definition: bswap.h:96
uint64_t_TMPL AV_WL64 unsigned int_TMPL AV_WL32 unsigned int_TMPL AV_WL24 unsigned int_TMPL AV_WL16 uint64_t_TMPL AV_WB64 unsigned int_TMPL AV_WB32 unsigned int_TMPL AV_WB24 unsigned int_TMPL AV_RB16
Definition: bytestream.h:87
#define AV_PIX_FMT_RGB444
Definition: pixfmt.h:332
unsigned flags
1 for EHB, 0 is no extra half darkening
Definition: iff.c:60
unsigned is_short
short compression method used
Definition: iff.c:55
AVCodec.
Definition: avcodec.h:3559
static void decode_delta_e(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int flag, int bpp, int dst_size)
Definition: iff.c:1292
uint8_t * video[2]
Definition: iff.c:66
static void decodeplane8(uint8_t *dst, const uint8_t *buf, int buf_size, int plane)
Decode interleaved plane buffer up to 8bpp.
Definition: iff.c:446
uint32_t * mask_buf
temporary buffer for palette indices
Definition: iff.c:52
#define DECODE_HAM_PLANE32(x)
Definition: iff.c:485
static av_cold int decode_end(AVCodecContext *avctx)
Definition: iff.c:368
void void avpriv_request_sample(void *avc, const char *msg,...) av_printf_format(2
Log a generic warning message about a missing feature.
uint8_t * planebuf
Definition: iff.c:49
uint8_t
#define av_cold
Definition: attributes.h:82
#define av_malloc(s)
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)
Decode DEEP TVDC 32-bit buffer.
Definition: iff.c:676
float delta
8 bits with AV_PIX_FMT_RGB32 palette
Definition: pixfmt.h:73
uint8_t * ham_buf
temporary buffer for planar to chunky conversation
Definition: iff.c:50
static const OptionGroupDef groups[]
Definition: ffmpeg_opt.c:3011
uint8_t * extradata
some codecs need / can use extradata like Huffman tables.
Definition: avcodec.h:1772
static AVFrame * frame
Definition: iff.c:40
#define height
uint8_t * data
Definition: avcodec.h:1588
#define FFMIN3(a, b, c)
Definition: common.h:97
mask_type
Definition: iff.c:39
ptrdiff_t size
Definition: opengl_enc.c:101
int bits_per_coded_sample
bits per sample/pixel from the demuxer (needed for huffyuv).
Definition: avcodec.h:3050
#define FFALIGN(x, a)
Definition: macros.h:48
#define av_log(a,...)
#define AV_PKT_FLAG_KEY
The packet contains a keyframe.
Definition: avcodec.h:1620
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:176
static av_always_inline unsigned int bytestream2_get_bytes_left_p(PutByteContext *p)
Definition: bytestream.h:159
static const uint16_t mask[17]
Definition: lzw.c:38
#define AVERROR(e)
Definition: error.h:43
static av_always_inline void bytestream2_skip(GetByteContext *g, unsigned int size)
Definition: bytestream.h:164
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification. ...
Definition: internal.h:176
const char * r
Definition: vf_curves.c:107
static av_always_inline unsigned int bytestream2_get_buffer(GetByteContext *g, uint8_t *dst, unsigned int size)
Definition: bytestream.h:263
static av_always_inline unsigned int bytestream2_get_bytes_left(GetByteContext *g)
Definition: bytestream.h:154
GLsizei GLsizei * length
Definition: opengl_enc.c:115
#define AV_PIX_FMT_0BGR32
Definition: pixfmt.h:325
const char * name
Name of the codec implementation.
Definition: avcodec.h:3566
uint64_t_TMPL AV_WL64 unsigned int_TMPL AV_WL32 unsigned int_TMPL AV_RL24
Definition: bytestream.h:87
static const uint8_t offset[127][2]
Definition: vf_spp.c:92
GLsizei count
Definition: opengl_enc.c:109
#define FFMAX(a, b)
Definition: common.h:94
unsigned is_interlaced
video is interlaced
Definition: iff.c:56
int flags
A combination of AV_PKT_FLAG values.
Definition: avcodec.h:1594
#define GETNIBBLE
static av_always_inline void bytestream2_skip_p(PutByteContext *p, unsigned int size)
Definition: bytestream.h:176
#define LUT32(plane)
Definition: iff.c:114
int av_image_check_size(unsigned int w, unsigned int h, int log_offset, void *log_ctx)
Check if the given dimension of an image is valid, meaning that all bytes of the image can be address...
Definition: imgutils.c:251
enum AVPictureType pict_type
Picture type of the frame.
Definition: frame.h:258
#define FFMIN(a, b)
Definition: common.h:96
Definition: iff.c:46
#define width
static void decode_short_vertical_delta(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int bpp, int dst_size)
Definition: iff.c:947
int width
picture width / height.
Definition: avcodec.h:1844
GLsizei GLboolean const GLfloat * value
Definition: opengl_enc.c:109
int32_t
static void decode_short_horizontal_delta(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int bpp, int dst_size)
Definition: iff.c:716
static int decode_byterun(uint8_t *dst, int dst_size, GetByteContext *gb)
Decode one complete byterun1 encoded line.
Definition: iff.c:535
#define AV_WN64A(p, v)
Definition: intreadwrite.h:542
AVFrame * frame
Definition: iff.c:47
#define src
Definition: vp9dsp.c:530
#define AVERROR_PATCHWELCOME
Not yet implemented in FFmpeg, patches welcome.
Definition: error.h:62
static av_always_inline int bytestream2_seek_p(PutByteContext *p, int offset, int whence)
Definition: bytestream.h:232
static av_always_inline int bytestream2_tell(GetByteContext *g)
Definition: bytestream.h:188
#define AV_PIX_FMT_BGR32
Definition: pixfmt.h:322
int init
Definition: iff.c:63
static void decode_long_vertical_delta(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int bpp, int dst_size)
Definition: iff.c:1015
Libavcodec external API header.
uint64_t_TMPL AV_WL64 unsigned int_TMPL AV_WL32 unsigned int_TMPL AV_WL24 unsigned int_TMPL AV_WL16 uint64_t_TMPL AV_WB64 unsigned int_TMPL AV_WB32 unsigned int_TMPL AV_RB24
Definition: bytestream.h:87
int linesize[AV_NUM_DATA_POINTERS]
For video, size in bytes of each picture line.
Definition: frame.h:215
Descriptor that unambiguously describes how the bits of a pixel are stored in the up to 4 data planes...
Definition: pixdesc.h:81
#define DECODE_RGBX_COMMON(type)
Definition: iff.c:562
main external API structure.
Definition: avcodec.h:1657
#define AV_PIX_FMT_RGB32
Definition: pixfmt.h:320
int planesize
Definition: iff.c:48
static void decode_short_vertical_delta2(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int bpp, int dst_size)
Definition: iff.c:1098
int ff_get_buffer(AVCodecContext *avctx, AVFrame *frame, int flags)
Get a buffer for a frame.
Definition: utils.c:928
unsigned int codec_tag
fourcc (LSB first, so "ABCD" -> ('D'<<24) + ('C'<<16) + ('B'<<8) + 'A').
Definition: avcodec.h:1689
void * buf
Definition: avisynth_c.h:553
GLint GLenum type
Definition: opengl_enc.c:105
int extradata_size
Definition: avcodec.h:1773
static void decode_delta_j(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int h, int bpp, int dst_size)
Definition: iff.c:836
static av_always_inline uint32_t gray2rgb(const uint32_t x)
Definition: iff.c:146
static void decode_rgbn(GetByteContext *gb, uint8_t *dst, int width, int height, int linesize)
Decode RGBN buffer.
Definition: iff.c:606
#define AV_RN32(p)
Definition: intreadwrite.h:364
static void decode_long_vertical_delta2(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int bpp, int dst_size)
Definition: iff.c:1158
static void decode_delta_l(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int flag, int bpp, int dst_size)
Definition: iff.c:1347
uint8_t pixel
Definition: tiny_ssim.c:42
void * av_calloc(size_t nmemb, size_t size)
Allocate a block of nmemb * size bytes with alignment suitable for all memory accesses (including vec...
Definition: mem.c:260
uint8_t * data[AV_NUM_DATA_POINTERS]
pointer to the picture/channel planes.
Definition: frame.h:198
static int decode(AVCodecContext *avctx, void *data, int *got_sub, AVPacket *avpkt)
Definition: ccaption_dec.c:752
int palette
Definition: v4l.c:61
static void decode_byte_vertical_delta(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int xor, int bpp, int dst_size)
Definition: iff.c:769
Y , 8bpp.
Definition: pixfmt.h:70
common internal api header.
if(ret< 0)
Definition: vf_mcdeint.c:282
unsigned ham
0 if non-HAM or number of hold bits (6 for bpp > 6, 4 otherwise)
Definition: iff.c:59
static const uint32_t plane32_lut[32][16 *4]
Definition: iff.c:134
static int decode_frame(AVCodecContext *avctx, void *data, int *got_frame, AVPacket *avpkt)
Definition: iff.c:1421
static void decode_delta_d(uint8_t *dst, const uint8_t *buf, const uint8_t *buf_end, int w, int flag, int bpp, int dst_size)
Definition: iff.c:1237
uint32_t * pal[2]
Definition: iff.c:68
static void decode_rgb8(GetByteContext *gb, uint8_t *dst, int width, int height, int linesize)
Decode RGB8 buffer.
Definition: iff.c:589
#define LUT8(plane)
Definition: iff.c:89
static void decode_ham_plane32(uint32_t *dst, const uint8_t *buf, const uint32_t *const pal, unsigned buf_size)
Converts one line of HAM6/8-encoded chunky buffer to 24bpp.
Definition: iff.c:503
#define AV_INPUT_BUFFER_PADDING_SIZE
Required number of additionally allocated bytes at the end of the input bitstream for decoding...
Definition: avcodec.h:731
static av_cold int decode_init(AVCodecContext *avctx)
Definition: iff.c:381
void * priv_data
Definition: avcodec.h:1699
static const uint64_t plane8_lut[8][256]
Definition: iff.c:109
static uint8_t tmp[8]
Definition: des.c:38
int key_frame
1 -> keyframe, 0-> not
Definition: frame.h:253
#define av_freep(p)
void INT64 start
Definition: avisynth_c.h:553
#define av_always_inline
Definition: attributes.h:39
unsigned video_size
Definition: iff.c:67
#define FFSWAP(type, a, b)
Definition: common.h:99
static int extract_header(AVCodecContext *const avctx, const AVPacket *const avpkt)
Extracts the IFF extra context and updates internal decoder structures.
Definition: iff.c:200
static void lookup_pal_indicies(uint32_t *dst, const uint32_t *buf, const uint32_t *const pal, unsigned width)
Definition: iff.c:518
int16_t tvdc[16]
TVDC lookup table.
Definition: iff.c:64
static int unsupported(AVCodecContext *avctx)
Definition: iff.c:1414
#define AV_RN64A(p)
Definition: intreadwrite.h:530
#define MKTAG(a, b, c, d)
Definition: common.h:342
This structure stores compressed data.
Definition: avcodec.h:1565
#define AV_CODEC_CAP_DR1
Codec uses get_buffer() for allocating buffers and supports custom allocators.
Definition: avcodec.h:956
uint32_t * ham_palbuf
HAM decode table.
Definition: iff.c:51
Predicted.
Definition: avutil.h:267
unsigned bpp
bits per plane to decode (differs from bits_per_coded_sample if HAM)
Definition: iff.c:58
static void decode_deep_rle32(uint8_t *dst, const uint8_t *src, int src_size, int width, int height, int linesize)
Decode DEEP RLE 32-bit buffer.
Definition: iff.c:626