> > > > +static int decode_header(PSDContext * s) > > +{ > > + int signature, version, color_mode, len_section, compression; > > + int ret = 0; > > + > > + if (bytestream2_get_bytes_left(&s->gb) < 30) {/* File header > section + color map data section length */ > > + av_log(s->avctx, AV_LOG_ERROR, "Header too short to parse.\n"); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + signature = bytestream2_get_le32(&s->gb); > > + if (signature != MKTAG('8','B','P','S')) { > > + av_log(s->avctx, AV_LOG_ERROR, "Wrong signature %d.\n", > signature); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + version = bytestream2_get_be16(&s->gb); > > + if (version != 1) { > > + av_log(s->avctx, AV_LOG_ERROR, "Wrong version %d.\n", version); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + bytestream2_skip(&s->gb, 6);/* reserved */ > > + > > + s->channel_count = bytestream2_get_be16(&s->gb); > > + if ((s->channel_count < 1) || (s->channel_count > 56)) { > > + av_log(s->avctx, AV_LOG_ERROR, "Invalid channel count %d.\n", > s->channel_count); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + s->height = bytestream2_get_be32(&s->gb); > > + > > + if ((s->height < 1) || (s->height > 30000)) { > > + av_log(s->avctx, AV_LOG_ERROR, "Invalid height %d.\n", > s->height); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + s->width = bytestream2_get_be32(&s->gb); > > + if ((s->width < 1) || (s->width > 30000)) { > > + av_log(s->avctx, AV_LOG_ERROR, "Invalid width %d.\n", s->width); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + if ((ret = ff_set_dimensions(s->avctx, s->width, s->height)) < 0) > > + return ret; > > + > > + s->channel_depth = bytestream2_get_be16(&s->gb); > > + > > + color_mode = bytestream2_get_be16(&s->gb); > > + switch (color_mode) { > > + case 0: > > + s->color_mode = PSD_BITMAP; > > + break; > > + case 1: > > + s->color_mode = PSD_GRAYSCALE; > > + break; > > + case 2: > > + s->color_mode = PSD_INDEXED; > > + break; > > + case 3: > > + s->color_mode = PSD_RGB; > > + break; > > + case 4: > > + s->color_mode = PSD_CMYK; > > + break; > > + case 7: > > + s->color_mode = PSD_MULTICHANNEL; > > + break; > > + case 8: > > + s->color_mode = PSD_DUOTONE; > > + break; > > + case 9: > > + s->color_mode = PSD_LAB; > > + break; > > + default: > > + av_log(s->avctx, AV_LOG_ERROR, "Unknown color mode %d.\n", > color_mode); > > + return AVERROR_INVALIDDATA; > > + } > > + > > + /* color map data */ > > + len_section = bytestream2_get_be32(&s->gb); > > + if (bytestream2_get_bytes_left(&s->gb) < (len_section + 4)) { /* > section and len next section */ > > len_section + 4 can overflow, len_section is signed here so can be > negative too > Ok i will correct that.
> > > [...] > > +static int decode_frame(AVCodecContext *avctx, void *data, > > + int *got_frame, AVPacket *avpkt) > > +{ > > + int ret; > > + uint8_t *ptr; > > + const uint8_t * ptr_data; > > + int index_out, c, y, x, p; > > + > > + AVFrame *picture = data; > > + > > + PSDContext *s = avctx->priv_data; > > + s->avctx = avctx; > > + s->channel_count = 0; > > + s->channel_depth = 0; > > + s->tmp = NULL; > > + s->line_size = 0; > > + > > + bytestream2_init(&s->gb, avpkt->data, avpkt->size); > > + > > + if ((ret = decode_header(s)) < 0) > > + return ret; > > + > > + s->pixel_size = s->channel_depth >> 3;/* in byte */ > > > + s->line_size = s->width * s->pixel_size; > For this one i doesn't think there can be an overflow, width can't be > 30 000 (checked before), and pixel_size is 16bit > > + s->uncompressed_size = s->line_size * s->height * s->channel_count; > > Does it seems ok, if i replace unsigned long by uint_64 ? > > did you test this code with a fuzzer ? > No i didn't know how to do that. _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org http://ffmpeg.org/mailman/listinfo/ffmpeg-devel