|
|
|
@ -399,7 +399,7 @@ static void av_always_inline horizontal_fill(unsigned int bpp, uint8_t* dst, |
|
|
|
|
static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
const uint8_t *src, int size, int lines) |
|
|
|
|
{ |
|
|
|
|
int c, line, pixels, code; |
|
|
|
|
int c, line, pixels, code, ret; |
|
|
|
|
const uint8_t *ssrc = src; |
|
|
|
|
int width = ((s->width * s->bpp) + 7) >> 3; |
|
|
|
|
|
|
|
|
@ -434,7 +434,7 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
(unsigned long)width * lines, ret); |
|
|
|
|
av_free(src2); |
|
|
|
|
av_free(zbuf); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_UNKNOWN; |
|
|
|
|
} |
|
|
|
|
src = zbuf; |
|
|
|
|
for (line = 0; line < lines; line++) { |
|
|
|
@ -465,9 +465,9 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
if (size > 1 && !src[0] && (src[1]&1)) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Old style LZW is unsupported\n"); |
|
|
|
|
} |
|
|
|
|
if (ff_lzw_decode_init(s->lzw, 8, src, size, FF_LZW_TIFF) < 0) { |
|
|
|
|
if ((ret = ff_lzw_decode_init(s->lzw, 8, src, size, FF_LZW_TIFF)) < 0) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Error initializing LZW decoder\n"); |
|
|
|
|
return -1; |
|
|
|
|
return ret; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
if (s->compr == TIFF_CCITT_RLE || s->compr == TIFF_G3 |
|
|
|
@ -485,7 +485,7 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"Uncompressed fax mode is not supported (yet)\n"); |
|
|
|
|
av_free(src2); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
if (!s->fill_order) { |
|
|
|
|
memcpy(src2, src, size); |
|
|
|
@ -513,7 +513,7 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
for (line = 0; line < lines; line++) { |
|
|
|
|
if (src - ssrc > size) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Source data overread\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
switch (s->compr) { |
|
|
|
|
case TIFF_RAW: |
|
|
|
@ -541,7 +541,7 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
if (pixels + code > width) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"Copy went out of bounds\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
if (ssrc + size - src < code) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Read went out of bounds\n"); |
|
|
|
@ -556,7 +556,7 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
if (pixels + code > width) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"Run went out of bounds\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
c = *src++; |
|
|
|
|
horizontal_fill(s->bpp * (s->avctx->pix_fmt == AV_PIX_FMT_PAL8), |
|
|
|
@ -570,7 +570,7 @@ static int tiff_unpack_strip(TiffContext *s, uint8_t *dst, int stride, |
|
|
|
|
if (pixels < width) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Decoded only %i bytes of %i\n", |
|
|
|
|
pixels, width); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
if (s->bpp < 8 && s->avctx->pix_fmt == AV_PIX_FMT_PAL8) |
|
|
|
|
horizontal_fill(s->bpp, dst, 1, dst, 0, width, 0); |
|
|
|
@ -705,7 +705,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"This format is not supported (bpp=%d, %d components)\n", |
|
|
|
|
s->bpp, count); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
if (count == 1) |
|
|
|
|
s->bpp = value; |
|
|
|
@ -719,7 +719,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
case TIFF_LONG: |
|
|
|
|
s->bpp = 0; |
|
|
|
|
if (bytestream2_get_bytes_left(&s->gb) < type_sizes[type] * count) |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
for (i = 0; i < count; i++) |
|
|
|
|
s->bpp += tget(&s->gb, type, s->le); |
|
|
|
|
break; |
|
|
|
@ -757,17 +757,17 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
break; |
|
|
|
|
#else |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Deflate: ZLib not compiled in\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR(ENOSYS); |
|
|
|
|
#endif |
|
|
|
|
case TIFF_JPEG: |
|
|
|
|
case TIFF_NEWJPEG: |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"JPEG compression is not supported\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_PATCHWELCOME; |
|
|
|
|
default: |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Unknown compression method %i\n", |
|
|
|
|
s->compr); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case TIFF_ROWSPERSTRIP: |
|
|
|
@ -776,7 +776,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
if (value < 1) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"Incorrect value of rows per strip\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
s->rps = value; |
|
|
|
|
break; |
|
|
|
@ -793,7 +793,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
if (s->strippos > bytestream2_size(&s->gb)) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"Tag referencing position outside the image\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case TIFF_STRIP_SIZE: |
|
|
|
@ -809,7 +809,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
if (s->stripsizesoff > bytestream2_size(&s->gb)) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, |
|
|
|
|
"Tag referencing position outside the image\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case TIFF_TILE_BYTE_COUNTS: |
|
|
|
@ -836,7 +836,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
default: |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Color mode %d is not supported\n", |
|
|
|
|
value); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case TIFF_FILL_ORDER: |
|
|
|
@ -851,7 +851,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
pal = (uint32_t *) s->palette; |
|
|
|
|
off = type_sizes[type]; |
|
|
|
|
if (count / 3 > 256 || bytestream2_get_bytes_left(&s->gb) < count / 3 * off * 3) |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
off = (type_sizes[type] - 1) << 3; |
|
|
|
|
for (k = 2; k >= 0; k--) { |
|
|
|
|
for (i = 0; i < count / 3; i++) { |
|
|
|
@ -866,7 +866,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
case TIFF_PLANAR: |
|
|
|
|
if (value == 2) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Planar format is not supported\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_PATCHWELCOME; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case TIFF_T4OPTIONS: |
|
|
|
@ -959,7 +959,7 @@ static int tiff_decode_tag(TiffContext *s) |
|
|
|
|
|
|
|
|
|
bytestream2_seek(&s->gb, pos + s->geotags[i].offset, SEEK_SET); |
|
|
|
|
if (bytestream2_get_bytes_left(&s->gb) < s->geotags[i].count) |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
ap = av_malloc(s->geotags[i].count); |
|
|
|
|
if (!ap) { |
|
|
|
|
av_log(s->avctx, AV_LOG_ERROR, "Error allocating temporary buffer\n"); |
|
|
|
@ -1040,7 +1040,7 @@ static int decode_frame(AVCodecContext *avctx, |
|
|
|
|
le = 0; |
|
|
|
|
else { |
|
|
|
|
av_log(avctx, AV_LOG_ERROR, "TIFF header not found\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
s->le = le; |
|
|
|
|
// TIFF_BPP is not a required tag and defaults to 1
|
|
|
|
@ -1058,7 +1058,7 @@ static int decode_frame(AVCodecContext *avctx, |
|
|
|
|
if (tget_short(&s->gb, le) != 42) { |
|
|
|
|
av_log(avctx, AV_LOG_ERROR, |
|
|
|
|
"The answer to life, universe and everything is not correct!\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
// Reset these offsets so we can tell if they were set this frame
|
|
|
|
|
s->stripsizesoff = s->strippos = 0; |
|
|
|
@ -1073,8 +1073,8 @@ static int decode_frame(AVCodecContext *avctx, |
|
|
|
|
if (bytestream2_get_bytes_left(&s->gb) < entries * 12) |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
for (i = 0; i < entries; i++) { |
|
|
|
|
if (tiff_decode_tag(s) < 0) |
|
|
|
|
return -1; |
|
|
|
|
if ((ret = tiff_decode_tag(s)) < 0) |
|
|
|
|
return ret; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
for (i = 0; i<s->geotag_count; i++) { |
|
|
|
@ -1096,7 +1096,7 @@ static int decode_frame(AVCodecContext *avctx, |
|
|
|
|
|
|
|
|
|
if (!s->strippos && !s->stripoff) { |
|
|
|
|
av_log(avctx, AV_LOG_ERROR, "Image data is missing\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
/* now we have the data and may start decoding */ |
|
|
|
|
if ((ret = init_image(s)) < 0) |
|
|
|
@ -1138,7 +1138,7 @@ static int decode_frame(AVCodecContext *avctx, |
|
|
|
|
|
|
|
|
|
if (soff > avpkt->size || ssize > avpkt->size - soff) { |
|
|
|
|
av_log(avctx, AV_LOG_ERROR, "Invalid strip size/offset\n"); |
|
|
|
|
return -1; |
|
|
|
|
return AVERROR_INVALIDDATA; |
|
|
|
|
} |
|
|
|
|
if (tiff_unpack_strip(s, dst, stride, avpkt->data + soff, ssize, |
|
|
|
|
FFMIN(s->rps, s->height - i)) < 0) |
|
|
|
|