00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00028 #include "libavutil/imgutils.h"
00029 #include "bytestream.h"
00030 #include "avcodec.h"
00031 #include "get_bits.h"
00032
00033 typedef struct {
00034 AVFrame frame;
00035 int planesize;
00036 uint8_t * planebuf;
00037 int init;
00038 } IffContext;
00039
00040 #define LUT8_PART(plane, v) \
00041 AV_LE2NE64C(UINT64_C(0x0000000)<<32 | v) << plane, \
00042 AV_LE2NE64C(UINT64_C(0x1000000)<<32 | v) << plane, \
00043 AV_LE2NE64C(UINT64_C(0x0010000)<<32 | v) << plane, \
00044 AV_LE2NE64C(UINT64_C(0x1010000)<<32 | v) << plane, \
00045 AV_LE2NE64C(UINT64_C(0x0000100)<<32 | v) << plane, \
00046 AV_LE2NE64C(UINT64_C(0x1000100)<<32 | v) << plane, \
00047 AV_LE2NE64C(UINT64_C(0x0010100)<<32 | v) << plane, \
00048 AV_LE2NE64C(UINT64_C(0x1010100)<<32 | v) << plane, \
00049 AV_LE2NE64C(UINT64_C(0x0000001)<<32 | v) << plane, \
00050 AV_LE2NE64C(UINT64_C(0x1000001)<<32 | v) << plane, \
00051 AV_LE2NE64C(UINT64_C(0x0010001)<<32 | v) << plane, \
00052 AV_LE2NE64C(UINT64_C(0x1010001)<<32 | v) << plane, \
00053 AV_LE2NE64C(UINT64_C(0x0000101)<<32 | v) << plane, \
00054 AV_LE2NE64C(UINT64_C(0x1000101)<<32 | v) << plane, \
00055 AV_LE2NE64C(UINT64_C(0x0010101)<<32 | v) << plane, \
00056 AV_LE2NE64C(UINT64_C(0x1010101)<<32 | v) << plane
00057
00058 #define LUT8(plane) { \
00059 LUT8_PART(plane, 0x0000000), \
00060 LUT8_PART(plane, 0x1000000), \
00061 LUT8_PART(plane, 0x0010000), \
00062 LUT8_PART(plane, 0x1010000), \
00063 LUT8_PART(plane, 0x0000100), \
00064 LUT8_PART(plane, 0x1000100), \
00065 LUT8_PART(plane, 0x0010100), \
00066 LUT8_PART(plane, 0x1010100), \
00067 LUT8_PART(plane, 0x0000001), \
00068 LUT8_PART(plane, 0x1000001), \
00069 LUT8_PART(plane, 0x0010001), \
00070 LUT8_PART(plane, 0x1010001), \
00071 LUT8_PART(plane, 0x0000101), \
00072 LUT8_PART(plane, 0x1000101), \
00073 LUT8_PART(plane, 0x0010101), \
00074 LUT8_PART(plane, 0x1010101), \
00075 }
00076
00077
00078 static const uint64_t plane8_lut[8][256] = {
00079 LUT8(0), LUT8(1), LUT8(2), LUT8(3),
00080 LUT8(4), LUT8(5), LUT8(6), LUT8(7),
00081 };
00082
00083 #define LUT32(plane) { \
00084 0, 0, 0, 0, \
00085 0, 0, 0, 1 << plane, \
00086 0, 0, 1 << plane, 0, \
00087 0, 0, 1 << plane, 1 << plane, \
00088 0, 1 << plane, 0, 0, \
00089 0, 1 << plane, 0, 1 << plane, \
00090 0, 1 << plane, 1 << plane, 0, \
00091 0, 1 << plane, 1 << plane, 1 << plane, \
00092 1 << plane, 0, 0, 0, \
00093 1 << plane, 0, 0, 1 << plane, \
00094 1 << plane, 0, 1 << plane, 0, \
00095 1 << plane, 0, 1 << plane, 1 << plane, \
00096 1 << plane, 1 << plane, 0, 0, \
00097 1 << plane, 1 << plane, 0, 1 << plane, \
00098 1 << plane, 1 << plane, 1 << plane, 0, \
00099 1 << plane, 1 << plane, 1 << plane, 1 << plane, \
00100 }
00101
00102
00103 static const uint32_t plane32_lut[32][16*4] = {
00104 LUT32( 0), LUT32( 1), LUT32( 2), LUT32( 3),
00105 LUT32( 4), LUT32( 5), LUT32( 6), LUT32( 7),
00106 LUT32( 8), LUT32( 9), LUT32(10), LUT32(11),
00107 LUT32(12), LUT32(13), LUT32(14), LUT32(15),
00108 LUT32(16), LUT32(17), LUT32(18), LUT32(19),
00109 LUT32(20), LUT32(21), LUT32(22), LUT32(23),
00110 LUT32(24), LUT32(25), LUT32(26), LUT32(27),
00111 LUT32(28), LUT32(29), LUT32(30), LUT32(31),
00112 };
00113
00114
00115 static av_always_inline uint32_t gray2rgb(const uint32_t x) {
00116 return x << 16 | x << 8 | x;
00117 }
00118
00122 static int ff_cmap_read_palette(AVCodecContext *avctx, uint32_t *pal)
00123 {
00124 int count, i;
00125
00126 if (avctx->bits_per_coded_sample > 8) {
00127 av_log(avctx, AV_LOG_ERROR, "bit_per_coded_sample > 8 not supported\n");
00128 return AVERROR_INVALIDDATA;
00129 }
00130
00131 count = 1 << avctx->bits_per_coded_sample;
00132
00133 count = FFMIN(avctx->extradata_size / 3, count);
00134 if (count) {
00135 for (i=0; i < count; i++) {
00136 pal[i] = 0xFF000000 | AV_RB24( avctx->extradata + i*3 );
00137 }
00138 } else {
00139 count = 1 << avctx->bits_per_coded_sample;
00140
00141 for (i=0; i < count; i++) {
00142 pal[i] = 0xFF000000 | gray2rgb((i * 255) >> avctx->bits_per_coded_sample);
00143 }
00144 }
00145 return 0;
00146 }
00147
00148 static av_cold int decode_init(AVCodecContext *avctx)
00149 {
00150 IffContext *s = avctx->priv_data;
00151 int err;
00152
00153 if (avctx->bits_per_coded_sample <= 8) {
00154 avctx->pix_fmt = (avctx->bits_per_coded_sample < 8 ||
00155 avctx->extradata_size) ? PIX_FMT_PAL8
00156 : PIX_FMT_GRAY8;
00157 } else if (avctx->bits_per_coded_sample <= 32) {
00158 avctx->pix_fmt = PIX_FMT_BGR32;
00159 } else {
00160 return AVERROR_INVALIDDATA;
00161 }
00162
00163 if ((err = av_image_check_size(avctx->width, avctx->height, 0, avctx)))
00164 return err;
00165 s->planesize = FFALIGN(avctx->width, 16) >> 3;
00166 s->planebuf = av_malloc(s->planesize + FF_INPUT_BUFFER_PADDING_SIZE);
00167 if (!s->planebuf)
00168 return AVERROR(ENOMEM);
00169
00170 s->frame.reference = 1;
00171
00172 return 0;
00173 }
00174
00182 static void decodeplane8(uint8_t *dst, const uint8_t *buf, int buf_size, int plane)
00183 {
00184 const uint64_t *lut = plane8_lut[plane];
00185 do {
00186 uint64_t v = AV_RN64A(dst) | lut[*buf++];
00187 AV_WN64A(dst, v);
00188 dst += 8;
00189 } while (--buf_size);
00190 }
00191
00199 static void decodeplane32(uint32_t *dst, const uint8_t *buf, int buf_size, int plane)
00200 {
00201 const uint32_t *lut = plane32_lut[plane];
00202 do {
00203 unsigned mask = (*buf >> 2) & ~3;
00204 dst[0] |= lut[mask++];
00205 dst[1] |= lut[mask++];
00206 dst[2] |= lut[mask++];
00207 dst[3] |= lut[mask];
00208 mask = (*buf++ << 2) & 0x3F;
00209 dst[4] |= lut[mask++];
00210 dst[5] |= lut[mask++];
00211 dst[6] |= lut[mask++];
00212 dst[7] |= lut[mask];
00213 dst += 8;
00214 } while (--buf_size);
00215 }
00216
00226 static int decode_byterun(uint8_t *dst, int dst_size,
00227 const uint8_t *buf, const uint8_t *const buf_end) {
00228 const uint8_t *const buf_start = buf;
00229 unsigned x;
00230 for (x = 0; x < dst_size && buf < buf_end;) {
00231 unsigned length;
00232 const int8_t value = *buf++;
00233 if (value >= 0) {
00234 length = value + 1;
00235 memcpy(dst + x, buf, FFMIN3(length, dst_size - x, buf_end - buf));
00236 buf += length;
00237 } else if (value > -128) {
00238 length = -value + 1;
00239 memset(dst + x, *buf++, FFMIN(length, dst_size - x));
00240 } else {
00241 continue;
00242 }
00243 x += length;
00244 }
00245 return buf - buf_start;
00246 }
00247
00248 static int decode_frame_ilbm(AVCodecContext *avctx,
00249 void *data, int *data_size,
00250 AVPacket *avpkt)
00251 {
00252 IffContext *s = avctx->priv_data;
00253 const uint8_t *buf = avpkt->data;
00254 int buf_size = avpkt->size;
00255 const uint8_t *buf_end = buf+buf_size;
00256 int y, plane, res;
00257
00258 if (s->init) {
00259 if ((res = avctx->reget_buffer(avctx, &s->frame)) < 0) {
00260 av_log(avctx, AV_LOG_ERROR, "reget_buffer() failed\n");
00261 return res;
00262 }
00263 } else if ((res = avctx->get_buffer(avctx, &s->frame)) < 0) {
00264 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
00265 return res;
00266 } else if (avctx->bits_per_coded_sample <= 8 && avctx->pix_fmt != PIX_FMT_GRAY8) {
00267 if ((res = ff_cmap_read_palette(avctx, (uint32_t*)s->frame.data[1])) < 0)
00268 return res;
00269 }
00270 s->init = 1;
00271
00272 if (avctx->codec_tag == MKTAG('I','L','B','M')) {
00273 if (avctx->pix_fmt == PIX_FMT_PAL8 || avctx->pix_fmt == PIX_FMT_GRAY8) {
00274 for (y = 0; y < avctx->height && buf < buf_end; y++ ) {
00275 uint8_t *row = &s->frame.data[0][ y*s->frame.linesize[0] ];
00276 memset(row, 0, avctx->width);
00277 for (plane = 0; plane < avctx->bits_per_coded_sample && buf < buf_end; plane++) {
00278 decodeplane8(row, buf, FFMIN(s->planesize, buf_end - buf), plane);
00279 buf += s->planesize;
00280 }
00281 }
00282 } else {
00283 for(y = 0; y < avctx->height; y++ ) {
00284 uint8_t *row = &s->frame.data[0][y*s->frame.linesize[0]];
00285 memset(row, 0, avctx->width << 2);
00286 for (plane = 0; plane < avctx->bits_per_coded_sample && buf < buf_end; plane++) {
00287 decodeplane32((uint32_t *) row, buf, FFMIN(s->planesize, buf_end - buf), plane);
00288 buf += s->planesize;
00289 }
00290 }
00291 }
00292 } else if (avctx->pix_fmt == PIX_FMT_PAL8 || avctx->pix_fmt == PIX_FMT_GRAY8) {
00293 for(y = 0; y < avctx->height; y++ ) {
00294 uint8_t *row = &s->frame.data[0][y * s->frame.linesize[0]];
00295 memcpy(row, buf, FFMIN(avctx->width, buf_end - buf));
00296 buf += avctx->width + (avctx->width % 2);
00297 }
00298 }
00299
00300 *data_size = sizeof(AVFrame);
00301 *(AVFrame*)data = s->frame;
00302 return buf_size;
00303 }
00304
00305 static int decode_frame_byterun1(AVCodecContext *avctx,
00306 void *data, int *data_size,
00307 AVPacket *avpkt)
00308 {
00309 IffContext *s = avctx->priv_data;
00310 const uint8_t *buf = avpkt->data;
00311 int buf_size = avpkt->size;
00312 const uint8_t *buf_end = buf+buf_size;
00313 int y, plane, res;
00314
00315 if (s->init) {
00316 if ((res = avctx->reget_buffer(avctx, &s->frame)) < 0) {
00317 av_log(avctx, AV_LOG_ERROR, "reget_buffer() failed\n");
00318 return res;
00319 }
00320 } else if ((res = avctx->get_buffer(avctx, &s->frame)) < 0) {
00321 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
00322 return res;
00323 } else if (avctx->bits_per_coded_sample <= 8 && avctx->pix_fmt != PIX_FMT_GRAY8) {
00324 if ((res = ff_cmap_read_palette(avctx, (uint32_t*)s->frame.data[1])) < 0)
00325 return res;
00326 }
00327 s->init = 1;
00328
00329 if (avctx->codec_tag == MKTAG('I','L','B','M')) {
00330 if (avctx->pix_fmt == PIX_FMT_PAL8 || avctx->pix_fmt == PIX_FMT_GRAY8) {
00331 for(y = 0; y < avctx->height ; y++ ) {
00332 uint8_t *row = &s->frame.data[0][ y*s->frame.linesize[0] ];
00333 memset(row, 0, avctx->width);
00334 for (plane = 0; plane < avctx->bits_per_coded_sample; plane++) {
00335 buf += decode_byterun(s->planebuf, s->planesize, buf, buf_end);
00336 decodeplane8(row, s->planebuf, s->planesize, plane);
00337 }
00338 }
00339 } else {
00340 for(y = 0; y < avctx->height ; y++ ) {
00341 uint8_t *row = &s->frame.data[0][y*s->frame.linesize[0]];
00342 memset(row, 0, avctx->width << 2);
00343 for (plane = 0; plane < avctx->bits_per_coded_sample; plane++) {
00344 buf += decode_byterun(s->planebuf, s->planesize, buf, buf_end);
00345 decodeplane32((uint32_t *) row, s->planebuf, s->planesize, plane);
00346 }
00347 }
00348 }
00349 } else {
00350 for(y = 0; y < avctx->height ; y++ ) {
00351 uint8_t *row = &s->frame.data[0][y*s->frame.linesize[0]];
00352 buf += decode_byterun(row, avctx->width, buf, buf_end);
00353 }
00354 }
00355
00356 *data_size = sizeof(AVFrame);
00357 *(AVFrame*)data = s->frame;
00358 return buf_size;
00359 }
00360
00361 static av_cold int decode_end(AVCodecContext *avctx)
00362 {
00363 IffContext *s = avctx->priv_data;
00364 if (s->frame.data[0])
00365 avctx->release_buffer(avctx, &s->frame);
00366 av_freep(&s->planebuf);
00367 return 0;
00368 }
00369
00370 AVCodec ff_iff_ilbm_decoder = {
00371 .name = "iff_ilbm",
00372 .type = AVMEDIA_TYPE_VIDEO,
00373 .id = CODEC_ID_IFF_ILBM,
00374 .priv_data_size = sizeof(IffContext),
00375 .init = decode_init,
00376 .close = decode_end,
00377 .decode = decode_frame_ilbm,
00378 .capabilities = CODEC_CAP_DR1,
00379 .long_name = NULL_IF_CONFIG_SMALL("IFF ILBM"),
00380 };
00381
00382 AVCodec ff_iff_byterun1_decoder = {
00383 .name = "iff_byterun1",
00384 .type = AVMEDIA_TYPE_VIDEO,
00385 .id = CODEC_ID_IFF_BYTERUN1,
00386 .priv_data_size = sizeof(IffContext),
00387 .init = decode_init,
00388 .close = decode_end,
00389 .decode = decode_frame_byterun1,
00390 .capabilities = CODEC_CAP_DR1,
00391 .long_name = NULL_IF_CONFIG_SMALL("IFF ByteRun1"),
00392 };