7ac78b0e5cbd9472f89e90cb27655600a65d33f9
[ffmpeg.git] / libavcodec / iff.c
1 /*
2  * IFF PBM/ILBM bitmap decoder
3  * Copyright (c) 2010 Peter Ross <pross@xvid.org>
4  * Copyright (c) 2010 Sebastian Vater <cdgs.basty@googlemail.com>
5  *
6  * This file is part of Libav.
7  *
8  * Libav is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2.1 of the License, or (at your option) any later version.
12  *
13  * Libav is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with Libav; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21  */
22
23 /**
24  * @file
25  * IFF PBM/ILBM bitmap decoder
26  */
27
28 #include "libavutil/imgutils.h"
29 #include "bytestream.h"
30 #include "avcodec.h"
31 #include "get_bits.h"
32 #include "internal.h"
33
34 typedef struct {
35     AVFrame *frame;
36     int planesize;
37     uint8_t * planebuf;
38     int init; // 1 if buffer and palette data already initialized, 0 otherwise
39 } IffContext;
40
41 #define LUT8_PART(plane, v)                             \
42     AV_LE2NE64C(UINT64_C(0x0000000)<<32 | v) << plane,  \
43     AV_LE2NE64C(UINT64_C(0x1000000)<<32 | v) << plane,  \
44     AV_LE2NE64C(UINT64_C(0x0010000)<<32 | v) << plane,  \
45     AV_LE2NE64C(UINT64_C(0x1010000)<<32 | v) << plane,  \
46     AV_LE2NE64C(UINT64_C(0x0000100)<<32 | v) << plane,  \
47     AV_LE2NE64C(UINT64_C(0x1000100)<<32 | v) << plane,  \
48     AV_LE2NE64C(UINT64_C(0x0010100)<<32 | v) << plane,  \
49     AV_LE2NE64C(UINT64_C(0x1010100)<<32 | v) << plane,  \
50     AV_LE2NE64C(UINT64_C(0x0000001)<<32 | v) << plane,  \
51     AV_LE2NE64C(UINT64_C(0x1000001)<<32 | v) << plane,  \
52     AV_LE2NE64C(UINT64_C(0x0010001)<<32 | v) << plane,  \
53     AV_LE2NE64C(UINT64_C(0x1010001)<<32 | v) << plane,  \
54     AV_LE2NE64C(UINT64_C(0x0000101)<<32 | v) << plane,  \
55     AV_LE2NE64C(UINT64_C(0x1000101)<<32 | v) << plane,  \
56     AV_LE2NE64C(UINT64_C(0x0010101)<<32 | v) << plane,  \
57     AV_LE2NE64C(UINT64_C(0x1010101)<<32 | v) << plane
58
59 #define LUT8(plane) {                           \
60     LUT8_PART(plane, 0x0000000),                \
61     LUT8_PART(plane, 0x1000000),                \
62     LUT8_PART(plane, 0x0010000),                \
63     LUT8_PART(plane, 0x1010000),                \
64     LUT8_PART(plane, 0x0000100),                \
65     LUT8_PART(plane, 0x1000100),                \
66     LUT8_PART(plane, 0x0010100),                \
67     LUT8_PART(plane, 0x1010100),                \
68     LUT8_PART(plane, 0x0000001),                \
69     LUT8_PART(plane, 0x1000001),                \
70     LUT8_PART(plane, 0x0010001),                \
71     LUT8_PART(plane, 0x1010001),                \
72     LUT8_PART(plane, 0x0000101),                \
73     LUT8_PART(plane, 0x1000101),                \
74     LUT8_PART(plane, 0x0010101),                \
75     LUT8_PART(plane, 0x1010101),                \
76 }
77
78 // 8 planes * 8-bit mask
79 static const uint64_t plane8_lut[8][256] = {
80     LUT8(0), LUT8(1), LUT8(2), LUT8(3),
81     LUT8(4), LUT8(5), LUT8(6), LUT8(7),
82 };
83
84 #define LUT32(plane) {                                \
85              0,          0,          0,          0,   \
86              0,          0,          0, 1 << plane,   \
87              0,          0, 1 << plane,          0,   \
88              0,          0, 1 << plane, 1 << plane,   \
89              0, 1 << plane,          0,          0,   \
90              0, 1 << plane,          0, 1 << plane,   \
91              0, 1 << plane, 1 << plane,          0,   \
92              0, 1 << plane, 1 << plane, 1 << plane,   \
93     1 << plane,          0,          0,          0,   \
94     1 << plane,          0,          0, 1 << plane,   \
95     1 << plane,          0, 1 << plane,          0,   \
96     1 << plane,          0, 1 << plane, 1 << plane,   \
97     1 << plane, 1 << plane,          0,          0,   \
98     1 << plane, 1 << plane,          0, 1 << plane,   \
99     1 << plane, 1 << plane, 1 << plane,          0,   \
100     1 << plane, 1 << plane, 1 << plane, 1 << plane,   \
101 }
102
103 // 32 planes * 4-bit mask * 4 lookup tables each
104 static const uint32_t plane32_lut[32][16*4] = {
105     LUT32( 0), LUT32( 1), LUT32( 2), LUT32( 3),
106     LUT32( 4), LUT32( 5), LUT32( 6), LUT32( 7),
107     LUT32( 8), LUT32( 9), LUT32(10), LUT32(11),
108     LUT32(12), LUT32(13), LUT32(14), LUT32(15),
109     LUT32(16), LUT32(17), LUT32(18), LUT32(19),
110     LUT32(20), LUT32(21), LUT32(22), LUT32(23),
111     LUT32(24), LUT32(25), LUT32(26), LUT32(27),
112     LUT32(28), LUT32(29), LUT32(30), LUT32(31),
113 };
114
115 // Gray to RGB, required for palette table of grayscale images with bpp < 8
116 static av_always_inline uint32_t gray2rgb(const uint32_t x) {
117     return x << 16 | x << 8 | x;
118 }
119
120 /**
121  * Convert CMAP buffer (stored in extradata) to lavc palette format
122  */
123 static int cmap_read_palette(AVCodecContext *avctx, uint32_t *pal)
124 {
125     int count, i;
126
127     if (avctx->bits_per_coded_sample > 8) {
128         av_log(avctx, AV_LOG_ERROR, "bit_per_coded_sample > 8 not supported\n");
129         return AVERROR_INVALIDDATA;
130     }
131
132     count = 1 << avctx->bits_per_coded_sample;
133     // If extradata is smaller than actually needed, fill the remaining with black.
134     count = FFMIN(avctx->extradata_size / 3, count);
135     if (count) {
136         for (i = 0; i < count; i++)
137             pal[i] = 0xFF000000 | AV_RB24(avctx->extradata + i * 3);
138     } else { // Create gray-scale color palette for bps < 8
139         count = 1 << avctx->bits_per_coded_sample;
140
141         for (i = 0; i < count; i++)
142             pal[i] = 0xFF000000 | gray2rgb((i * 255) >> avctx->bits_per_coded_sample);
143     }
144     return 0;
145 }
146
147 static av_cold int decode_end(AVCodecContext *avctx)
148 {
149     IffContext *s = avctx->priv_data;
150     av_frame_free(&s->frame);
151     av_freep(&s->planebuf);
152     return 0;
153 }
154
155 static av_cold int decode_init(AVCodecContext *avctx)
156 {
157     IffContext *s = avctx->priv_data;
158     int err;
159
160     if (avctx->bits_per_coded_sample <= 8) {
161         avctx->pix_fmt = (avctx->bits_per_coded_sample < 8 ||
162                           avctx->extradata_size) ? AV_PIX_FMT_PAL8
163                                                  : AV_PIX_FMT_GRAY8;
164     } else if (avctx->bits_per_coded_sample <= 32) {
165         avctx->pix_fmt = AV_PIX_FMT_BGR32;
166     } else {
167         return AVERROR_INVALIDDATA;
168     }
169
170     if ((err = av_image_check_size(avctx->width, avctx->height, 0, avctx)))
171         return err;
172     s->planesize = FFALIGN(avctx->width, 16) >> 3; // Align plane size in bits to word-boundary
173     s->planebuf  = av_malloc(s->planesize + FF_INPUT_BUFFER_PADDING_SIZE);
174     if (!s->planebuf)
175         return AVERROR(ENOMEM);
176
177     s->frame = av_frame_alloc();
178     if (!s->frame) {
179         decode_end(avctx);
180         return AVERROR(ENOMEM);
181     }
182
183     return 0;
184 }
185
186 /**
187  * Decode interleaved plane buffer up to 8bpp
188  * @param dst Destination buffer
189  * @param buf Source buffer
190  * @param buf_size
191  * @param plane plane number to decode as
192  */
193 static void decodeplane8(uint8_t *dst, const uint8_t *buf, int buf_size, int plane)
194 {
195     const uint64_t *lut = plane8_lut[plane];
196     do {
197         uint64_t v = AV_RN64A(dst) | lut[*buf++];
198         AV_WN64A(dst, v);
199         dst += 8;
200     } while (--buf_size);
201 }
202
203 /**
204  * Decode interleaved plane buffer up to 24bpp
205  * @param dst Destination buffer
206  * @param buf Source buffer
207  * @param buf_size
208  * @param plane plane number to decode as
209  */
210 static void decodeplane32(uint32_t *dst, const uint8_t *buf, int buf_size, int plane)
211 {
212     const uint32_t *lut = plane32_lut[plane];
213     do {
214         unsigned mask = (*buf >> 2) & ~3;
215         dst[0] |= lut[mask++];
216         dst[1] |= lut[mask++];
217         dst[2] |= lut[mask++];
218         dst[3] |= lut[mask];
219         mask    = (*buf++ << 2) & 0x3F;
220         dst[4] |= lut[mask++];
221         dst[5] |= lut[mask++];
222         dst[6] |= lut[mask++];
223         dst[7] |= lut[mask];
224         dst    += 8;
225     } while (--buf_size);
226 }
227
228 /**
229  * Decode one complete byterun1 encoded line.
230  *
231  * @param dst the destination buffer where to store decompressed bitstream
232  * @param dst_size the destination plane size in bytes
233  * @param buf the source byterun1 compressed bitstream
234  * @param buf_end the EOF of source byterun1 compressed bitstream
235  * @return number of consumed bytes in byterun1 compressed bitstream
236  */
237 static int decode_byterun(uint8_t *dst, int dst_size,
238                           const uint8_t *buf, const uint8_t *const buf_end)
239 {
240     const uint8_t *const buf_start = buf;
241     unsigned x;
242     for (x = 0; x < dst_size && buf < buf_end;) {
243         unsigned length;
244         const int8_t value = *buf++;
245         if (value >= 0) {
246             length = value + 1;
247             memcpy(dst + x, buf, FFMIN3(length, dst_size - x, buf_end - buf));
248             buf += length;
249         } else if (value > -128) {
250             length = -value + 1;
251             memset(dst + x, *buf++, FFMIN(length, dst_size - x));
252         } else { // noop
253             continue;
254         }
255         x += length;
256     }
257     return buf - buf_start;
258 }
259
260 static int decode_frame_ilbm(AVCodecContext *avctx,
261                              void *data, int *got_frame,
262                              AVPacket *avpkt)
263 {
264     IffContext *s          = avctx->priv_data;
265     const uint8_t *buf     = avpkt->data;
266     int buf_size           = avpkt->size;
267     const uint8_t *buf_end = buf + buf_size;
268     int y, plane, res;
269
270     if ((res = ff_reget_buffer(avctx, s->frame)) < 0)
271         return res;
272
273     if (!s->init && avctx->bits_per_coded_sample <= 8 &&
274         avctx->pix_fmt != AV_PIX_FMT_GRAY8) {
275         if ((res = cmap_read_palette(avctx, (uint32_t *)s->frame->data[1])) < 0)
276             return res;
277     }
278     s->init = 1;
279
280     if (avctx->codec_tag == MKTAG('I', 'L', 'B', 'M')) { // interleaved
281         if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
282             for (y = 0; y < avctx->height; y++) {
283                 uint8_t *row = &s->frame->data[0][y * s->frame->linesize[0]];
284                 memset(row, 0, avctx->width);
285                 for (plane = 0; plane < avctx->bits_per_coded_sample && buf < buf_end;
286                      plane++) {
287                     decodeplane8(row, buf, FFMIN(s->planesize, buf_end - buf), plane);
288                     buf += s->planesize;
289                 }
290             }
291         } else { // AV_PIX_FMT_BGR32
292             for (y = 0; y < avctx->height; y++) {
293                 uint8_t *row = &s->frame->data[0][y * s->frame->linesize[0]];
294                 memset(row, 0, avctx->width << 2);
295                 for (plane = 0; plane < avctx->bits_per_coded_sample && buf < buf_end;
296                      plane++) {
297                     decodeplane32((uint32_t *)row, buf,
298                                   FFMIN(s->planesize, buf_end - buf), plane);
299                     buf += s->planesize;
300                 }
301             }
302         }
303     } else if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) { // IFF-PBM
304         for (y = 0; y < avctx->height && buf < buf_end; y++) {
305             uint8_t *row = &s->frame->data[0][y * s->frame->linesize[0]];
306             memcpy(row, buf, FFMIN(avctx->width, buf_end - buf));
307             buf += avctx->width + (avctx->width % 2); // padding if odd
308         }
309     }
310
311     if ((res = av_frame_ref(data, s->frame)) < 0)
312         return res;
313
314     *got_frame = 1;
315
316     return buf_size;
317 }
318
319 static int decode_frame_byterun1(AVCodecContext *avctx,
320                                  void *data, int *got_frame,
321                                  AVPacket *avpkt)
322 {
323     IffContext *s          = avctx->priv_data;
324     const uint8_t *buf     = avpkt->data;
325     int buf_size           = avpkt->size;
326     const uint8_t *buf_end = buf + buf_size;
327     int y, plane, res;
328
329     if ((res = ff_reget_buffer(avctx, s->frame)) < 0)
330         return res;
331
332     if (!s->init && avctx->bits_per_coded_sample <= 8 &&
333         avctx->pix_fmt != AV_PIX_FMT_GRAY8) {
334         if ((res = cmap_read_palette(avctx, (uint32_t *)s->frame->data[1])) < 0)
335             return res;
336     }
337     s->init = 1;
338
339     if (avctx->codec_tag == MKTAG('I', 'L', 'B', 'M')) { // interleaved
340         if (avctx->pix_fmt == AV_PIX_FMT_PAL8 || avctx->pix_fmt == AV_PIX_FMT_GRAY8) {
341             for (y = 0; y < avctx->height; y++) {
342                 uint8_t *row = &s->frame->data[0][y * s->frame->linesize[0]];
343                 memset(row, 0, avctx->width);
344                 for (plane = 0; plane < avctx->bits_per_coded_sample; plane++) {
345                     buf += decode_byterun(s->planebuf, s->planesize, buf, buf_end);
346                     decodeplane8(row, s->planebuf, s->planesize, plane);
347                 }
348             }
349         } else { // AV_PIX_FMT_BGR32
350             for (y = 0; y < avctx->height; y++) {
351                 uint8_t *row = &s->frame->data[0][y * s->frame->linesize[0]];
352                 memset(row, 0, avctx->width << 2);
353                 for (plane = 0; plane < avctx->bits_per_coded_sample; plane++) {
354                     buf += decode_byterun(s->planebuf, s->planesize, buf, buf_end);
355                     decodeplane32((uint32_t *)row, s->planebuf, s->planesize, plane);
356                 }
357             }
358         }
359     } else {
360         for (y = 0; y < avctx->height; y++) {
361             uint8_t *row = &s->frame->data[0][y * s->frame->linesize[0]];
362             buf += decode_byterun(row, avctx->width, buf, buf_end);
363         }
364     }
365
366     if ((res = av_frame_ref(data, s->frame)) < 0)
367         return res;
368
369     *got_frame = 1;
370
371     return buf_size;
372 }
373
374 AVCodec ff_iff_ilbm_decoder = {
375     .name           = "iff_ilbm",
376     .long_name      = NULL_IF_CONFIG_SMALL("IFF ILBM"),
377     .type           = AVMEDIA_TYPE_VIDEO,
378     .id             = AV_CODEC_ID_IFF_ILBM,
379     .priv_data_size = sizeof(IffContext),
380     .init           = decode_init,
381     .close          = decode_end,
382     .decode         = decode_frame_ilbm,
383     .capabilities   = CODEC_CAP_DR1,
384 };
385
386 AVCodec ff_iff_byterun1_decoder = {
387     .name           = "iff_byterun1",
388     .long_name      = NULL_IF_CONFIG_SMALL("IFF ByteRun1"),
389     .type           = AVMEDIA_TYPE_VIDEO,
390     .id             = AV_CODEC_ID_IFF_BYTERUN1,
391     .priv_data_size = sizeof(IffContext),
392     .init           = decode_init,
393     .close          = decode_end,
394     .decode         = decode_frame_byterun1,
395     .capabilities   = CODEC_CAP_DR1,
396 };