[FFmpeg-cvslog] id3v2: fix reading v2.2 attached pictures

Anton Khirnov git at videolan.org
Thu Jan 15 13:10:20 CET 2015


ffmpeg | branch: master | Anton Khirnov <anton at khirnov.net> | Sat Jan 10 09:39:34 2015 +0100| [54bc15d5ebfd07fd468743ba29f709ea19e840b9] | committer: Vittorio Giovara

id3v2: fix reading v2.2 attached pictures

In v2.2, the picture type is not a zero-terminated string, but has a
constant size of 3 bytes.

> http://git.videolan.org/gitweb.cgi/ffmpeg.git/?a=commit;h=54bc15d5ebfd07fd468743ba29f709ea19e840b9
---

 libavformat/id3v2.c |   22 ++++++++++++++++------
 1 file changed, 16 insertions(+), 6 deletions(-)

diff --git a/libavformat/id3v2.c b/libavformat/id3v2.c
index 371564d..3c5c062 100644
--- a/libavformat/id3v2.c
+++ b/libavformat/id3v2.c
@@ -300,7 +300,8 @@ static void read_ttag(AVFormatContext *s, AVIOContext *pb, int taglen,
  * Parse GEOB tag into a ID3v2ExtraMetaGEOB struct.
  */
 static void read_geobtag(AVFormatContext *s, AVIOContext *pb, int taglen,
-                         const char *tag, ID3v2ExtraMeta **extra_meta)
+                         const char *tag, ID3v2ExtraMeta **extra_meta,
+                         int isv34)
 {
     ID3v2ExtraMetaGEOB *geob_data = NULL;
     ID3v2ExtraMeta *new_extra     = NULL;
@@ -432,7 +433,8 @@ static void free_apic(void *obj)
 }
 
 static void read_apic(AVFormatContext *s, AVIOContext *pb, int taglen,
-                      const char *tag, ID3v2ExtraMeta **extra_meta)
+                      const char *tag, ID3v2ExtraMeta **extra_meta,
+                      int isv34)
 {
     int enc, pic_type;
     char mimetype[64];
@@ -442,7 +444,7 @@ static void read_apic(AVFormatContext *s, AVIOContext *pb, int taglen,
     ID3v2ExtraMeta *new_extra = NULL;
     int64_t end               = avio_tell(pb) + taglen;
 
-    if (taglen <= 4)
+    if (taglen <= 4 || (!isv34 && taglen <= 6))
         goto fail;
 
     new_extra = av_mallocz(sizeof(*new_extra));
@@ -454,7 +456,14 @@ static void read_apic(AVFormatContext *s, AVIOContext *pb, int taglen,
     taglen--;
 
     /* mimetype */
-    taglen -= avio_get_str(pb, taglen, mimetype, sizeof(mimetype));
+    if (isv34) {
+        taglen -= avio_get_str(pb, taglen, mimetype, sizeof(mimetype));
+    } else {
+        avio_read(pb, mimetype, 3);
+        mimetype[3] = 0;
+        taglen    -= 3;
+    }
+
     while (mime->id != AV_CODEC_ID_NONE) {
         if (!av_strncasecmp(mime->str, mimetype, sizeof(mimetype))) {
             id = mime->id;
@@ -509,7 +518,8 @@ typedef struct ID3v2EMFunc {
     const char *tag3;
     const char *tag4;
     void (*read)(AVFormatContext *s, AVIOContext *pb, int taglen,
-                 const char *tag, ID3v2ExtraMeta **extra_meta);
+                 const char *tag, ID3v2ExtraMeta **extra_meta,
+                 int isv34);
     void (*free)(void *obj);
 } ID3v2EMFunc;
 
@@ -664,7 +674,7 @@ static void id3v2_parse(AVFormatContext *s, int len, uint8_t version,
                 read_ttag(s, pbx, tlen, tag);
             else
                 /* parse special meta tag */
-                extra_func->read(s, pbx, tlen, tag, extra_meta);
+                extra_func->read(s, pbx, tlen, tag, extra_meta, isv34);
         } else if (!tag[0]) {
             if (tag[1])
                 av_log(s, AV_LOG_WARNING, "invalid frame id, assuming padding");



More information about the ffmpeg-cvslog mailing list