X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavformat%2Fapetag.c;h=bf9918a0b383c725571d01d4613cdf8b427ac518;hb=a9a1bc56abf1fa79104996bf7b98b12ca42cd32c;hp=4d25a8e96975e99c2805979aa6c6a9e67e276a01;hpb=f8911b987de4a84ff8ae92f41ff492ece4acadb9;p=ffmpeg diff --git a/libavformat/apetag.c b/libavformat/apetag.c index 4d25a8e9697..bf9918a0b38 100644 --- a/libavformat/apetag.c +++ b/libavformat/apetag.c @@ -26,8 +26,6 @@ #include "apetag.h" #include "internal.h" -#define APE_TAG_VERSION 2000 -#define APE_TAG_FOOTER_BYTES 32 #define APE_TAG_FLAG_CONTAINS_HEADER (1 << 31) #define APE_TAG_FLAG_IS_HEADER (1 << 29) #define APE_TAG_FLAG_IS_BINARY (1 << 1) @@ -57,7 +55,7 @@ static int ape_tag_read_field(AVFormatContext *s) return -1; if (flags & APE_TAG_FLAG_IS_BINARY) { uint8_t filename[1024]; - enum CodecID id; + enum AVCodecID id; AVStream *st = avformat_new_stream(s, NULL); if (!st) return AVERROR(ENOMEM); @@ -70,7 +68,7 @@ static int ape_tag_read_field(AVFormatContext *s) av_dict_set(&st->metadata, key, filename, 0); - if ((id = ff_guess_image2_codec(filename)) != CODEC_ID_NONE) { + if ((id = ff_guess_image2_codec(filename)) != AV_CODEC_ID_NONE) { AVPacket pkt; int ret; @@ -113,50 +111,59 @@ static int ape_tag_read_field(AVFormatContext *s) return 0; } -void ff_ape_parse_tag(AVFormatContext *s) +int64_t ff_ape_parse_tag(AVFormatContext *s) { AVIOContext *pb = s->pb; int file_size = avio_size(pb); uint32_t val, fields, tag_bytes; uint8_t buf[8]; + int64_t tag_start; int i; if (file_size < APE_TAG_FOOTER_BYTES) - return; + return 0; avio_seek(pb, file_size - APE_TAG_FOOTER_BYTES, SEEK_SET); avio_read(pb, buf, 8); /* APETAGEX */ - if (strncmp(buf, "APETAGEX", 8)) { - return; + if (strncmp(buf, APE_TAG_PREAMBLE, 8)) { + return 0; } val = avio_rl32(pb); /* APE tag version */ if (val > APE_TAG_VERSION) { av_log(s, AV_LOG_ERROR, "Unsupported tag version. (>=%d)\n", APE_TAG_VERSION); - return; + return 0; } tag_bytes = avio_rl32(pb); /* tag size */ if (tag_bytes - APE_TAG_FOOTER_BYTES > (1024 * 1024 * 16)) { av_log(s, AV_LOG_ERROR, "Tag size is way too big\n"); - return; + return 0; + } + + tag_start = file_size - tag_bytes - APE_TAG_FOOTER_BYTES; + if (tag_start < 0) { + av_log(s, AV_LOG_ERROR, "Invalid tag size %u.\n", tag_bytes); + return 0; } fields = avio_rl32(pb); /* number of fields */ if (fields > 65536) { av_log(s, AV_LOG_ERROR, "Too many tag fields (%d)\n", fields); - return; + return 0; } val = avio_rl32(pb); /* flags */ if (val & APE_TAG_FLAG_IS_HEADER) { av_log(s, AV_LOG_ERROR, "APE Tag is a header\n"); - return; + return 0; } avio_seek(pb, file_size - tag_bytes, SEEK_SET); for (i=0; i