[FFmpeg-devel] [PATCH 5/5] vorbis: copy metadata for the packet

Ben Boeckel mathstuf at gmail.com
Sat Oct 19 15:40:46 CEST 2013


---
 libavformat/oggparsevorbis.c | 33 ++++++++++++++++++++++++++++++---
 1 file changed, 30 insertions(+), 3 deletions(-)

diff --git a/libavformat/oggparsevorbis.c b/libavformat/oggparsevorbis.c
index 8b2c051..3d39226 100644
--- a/libavformat/oggparsevorbis.c
+++ b/libavformat/oggparsevorbis.c
@@ -353,6 +353,33 @@ static int vorbis_header(AVFormatContext *s, int idx)
     return 1;
 }
 
+static int vorbis_update_header(AVFormatContext *s, int idx)
+{
+    struct ogg *ogg = s->priv_data;
+    struct ogg_stream *os = ogg->streams + idx;
+    AVStream *st = s->streams[idx];
+    AVDictionary *old_metadata = st->metadata;
+    int r = vorbis_header(s, idx);
+
+    /* Update the metadata if necessary. */
+    if (st->metadata && st->metadata != old_metadata) {
+        AVDictionaryEntry *t = NULL;
+        os->new_metadata = NULL;
+        os->new_metadata_size = 0;
+        while ((t = av_dict_get(st->metadata, "", t, AV_DICT_IGNORE_SUFFIX))) {
+            int keylen = strlen(t->key);
+            int valuelen = strlen(t->value);
+            size_t new_size = os->new_metadata_size + keylen + 1 + valuelen + 1;
+            os->new_metadata = av_realloc(os->new_metadata, new_size);
+            memcpy(os->new_metadata + os->new_metadata_size, t->key, keylen + 1);
+            memcpy(os->new_metadata + os->new_metadata_size + keylen + 1, t->value, valuelen + 1);
+            os->new_metadata_size = new_size;
+        }
+    }
+
+    return r;
+}
+
 static int vorbis_packet(AVFormatContext *s, int idx)
 {
     struct ogg *ogg = s->priv_data;
@@ -377,7 +404,7 @@ static int vorbis_packet(AVFormatContext *s, int idx)
             os->pflags |= AV_PKT_FLAG_CORRUPT;
             return 0;
         } else if (flags) {
-            vorbis_header(s, idx);
+            vorbis_update_header(s, idx);
             flags = 0;
         }
         duration += d;
@@ -389,7 +416,7 @@ static int vorbis_packet(AVFormatContext *s, int idx)
                     duration = os->granule;
                     break;
                 } else if (flags) {
-                    vorbis_header(s, idx);
+                    vorbis_update_header(s, idx);
                     flags = 0;
                 }
                 duration += d;
@@ -415,7 +442,7 @@ static int vorbis_packet(AVFormatContext *s, int idx)
             os->pflags |= AV_PKT_FLAG_CORRUPT;
             return 0;
         } else if (!duration) {
-            vorbis_header(s, idx);
+            vorbis_update_header(s, idx);
             flags = 0;
         }
         os->pduration = duration;
-- 
1.8.3.1



More information about the ffmpeg-devel mailing list