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