PR #23008 opened by toots
URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/23008
Patch URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/23008.patch


>From 94f82d7b8a69570306ed75a340788f4e3786988c Mon Sep 17 00:00:00 2001
From: Romain Beauxis <[email protected]>
Date: Sun, 3 May 2026 16:18:28 -0500
Subject: [PATCH] avformat/id3v2: make ID3v2 parsing API public

---
 doc/APIchanges               |   7 +++
 libavformat/Makefile         |   1 +
 libavformat/aacdec.c         |  10 ++--
 libavformat/adtsenc.c        |   2 +-
 libavformat/aiffdec.c        |  10 ++--
 libavformat/aiffenc.c        |   2 +-
 libavformat/asf.c            |  10 ++--
 libavformat/bonk.c           |   8 +--
 libavformat/demux.c          |  12 ++--
 libavformat/dsfdec.c         |   8 +--
 libavformat/flac_picture.c   |   2 +-
 libavformat/flacenc.c        |   2 +-
 libavformat/format.c         |   4 +-
 libavformat/hls.c            |  20 +++----
 libavformat/id3v2.c          |  25 ++++----
 libavformat/id3v2.h          | 111 ++++++++---------------------------
 libavformat/id3v2_internal.h | 102 ++++++++++++++++++++++++++++++++
 libavformat/id3v2enc.c       |   2 +-
 libavformat/iff.c            |  10 ++--
 libavformat/mp3dec.c         |   2 +-
 libavformat/mp3enc.c         |   2 +-
 libavformat/omadec.c         |  18 +++---
 libavformat/omaenc.c         |   2 +-
 libavformat/version.h        |   4 +-
 libavformat/wavdec.c         |  10 ++--
 25 files changed, 216 insertions(+), 170 deletions(-)
 create mode 100644 libavformat/id3v2_internal.h

diff --git a/doc/APIchanges b/doc/APIchanges
index f1cbbb41b8..813f78e899 100644
--- a/doc/APIchanges
+++ b/doc/APIchanges
@@ -2,6 +2,13 @@ The last version increases of all libraries were on 2025-03-28
 
 API changes, most recent first:
 
+2026-05-03 - xxxxxxxxxx - lavf 62.14.100 - id3v2.h
+  Add avformat_id3v2_match(), avformat_id3v2_tag_len(),
+  avformat_id3v2_read_dict(), avformat_id3v2_read(),
+  avformat_id3v2_free_extra_meta(), avformat_id3v2_parse_apic(),
+  avformat_id3v2_parse_chapters(), avformat_id3v2_parse_priv_dict(),
+  avformat_id3v2_parse_priv() and related types as public API.
+
 2026-04-14 - 7faa6ee2aa - lavc 62.30.100 - packet.h
   Add AV_PKT_DATA_DYNAMIC_HDR_SMPTE_2094_APP5 side data type.
 
diff --git a/libavformat/Makefile b/libavformat/Makefile
index 7c2fcad93e..e8f28f7207 100644
--- a/libavformat/Makefile
+++ b/libavformat/Makefile
@@ -3,6 +3,7 @@ DESC = FFmpeg container format library
 
 HEADERS = avformat.h                                                    \
           avio.h                                                        \
+          id3v2.h                                                       \
           version.h                                                     \
           version_major.h                                               \
 
diff --git a/libavformat/aacdec.c b/libavformat/aacdec.c
index fef3c69f0b..4a6d75f327 100644
--- a/libavformat/aacdec.c
+++ b/libavformat/aacdec.c
@@ -142,13 +142,13 @@ static int handle_id3(AVFormatContext *s, AVPacket *pkt)
     ID3v2ExtraMeta *id3v2_extra_meta;
     int ret;
 
-    ret = av_append_packet(s->pb, pkt, ff_id3v2_tag_len(pkt->data) - 
pkt->size);
+    ret = av_append_packet(s->pb, pkt, avformat_id3v2_tag_len(pkt->data) - 
pkt->size);
     if (ret < 0)
         return ret;
 
     ffio_init_read_context(&pb, pkt->data, pkt->size);
-    ff_id3v2_read_dict(&pb.pub, &metadata, ID3v2_DEFAULT_MAGIC, 
&id3v2_extra_meta);
-    if ((ret = ff_id3v2_parse_priv_dict(&metadata, id3v2_extra_meta)) < 0)
+    avformat_id3v2_read_dict(&pb.pub, &metadata, ID3v2_DEFAULT_MAGIC, 
&id3v2_extra_meta);
+    if ((ret = avformat_id3v2_parse_priv_dict(&metadata, id3v2_extra_meta)) < 
0)
         goto error;
 
     if (metadata) {
@@ -159,7 +159,7 @@ static int handle_id3(AVFormatContext *s, AVPacket *pkt)
 
 error:
     av_packet_unref(pkt);
-    ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+    avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
     av_dict_free(&metadata);
 
     return ret;
@@ -185,7 +185,7 @@ retry:
         ret = av_append_packet(s->pb, pkt, append);
         if (ret != append)
             return AVERROR_INVALIDDATA;
-        if (!ff_id3v2_match(pkt->data, ID3v2_DEFAULT_MAGIC)) {
+        if (!avformat_id3v2_match(pkt->data, ID3v2_DEFAULT_MAGIC)) {
             av_packet_unref(pkt);
             ret = adts_aac_resync(s);
         } else
diff --git a/libavformat/adtsenc.c b/libavformat/adtsenc.c
index 0671224fc2..2e02cb475b 100644
--- a/libavformat/adtsenc.c
+++ b/libavformat/adtsenc.c
@@ -30,7 +30,7 @@
 #include "libavutil/opt.h"
 #include "avformat.h"
 #include "apetag.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "mux.h"
 
 #define ADTS_HEADER_SIZE 7
diff --git a/libavformat/aiffdec.c b/libavformat/aiffdec.c
index 63194f2726..4edd6c7ed3 100644
--- a/libavformat/aiffdec.c
+++ b/libavformat/aiffdec.c
@@ -278,14 +278,14 @@ static int aiff_read_header(AVFormatContext *s)
             break;
         case MKTAG('I', 'D', '3', ' '):
             position = avio_tell(pb);
-            ff_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, size);
+            avformat_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, 
size);
             if (id3v2_extra_meta)
-                if ((ret = ff_id3v2_parse_apic(s, id3v2_extra_meta)) < 0 ||
-                    (ret = ff_id3v2_parse_chapters(s, id3v2_extra_meta)) < 0) {
-                    ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+                if ((ret = avformat_id3v2_parse_apic(s, id3v2_extra_meta)) < 0 
||
+                    (ret = avformat_id3v2_parse_chapters(s, id3v2_extra_meta)) 
< 0) {
+                    avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
                     return ret;
                 }
-            ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+            avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
             if (position + size > avio_tell(pb))
                 avio_skip(pb, position + size - avio_tell(pb));
             break;
diff --git a/libavformat/aiffenc.c b/libavformat/aiffenc.c
index 2cd1119409..933a6e5cd4 100644
--- a/libavformat/aiffenc.c
+++ b/libavformat/aiffenc.c
@@ -29,7 +29,7 @@
 #include "aiff.h"
 #include "avio_internal.h"
 #include "isom.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "mux.h"
 
 typedef struct AIFFOutputContext {
diff --git a/libavformat/asf.c b/libavformat/asf.c
index 5c118d2dbe..26ad56eedf 100644
--- a/libavformat/asf.c
+++ b/libavformat/asf.c
@@ -21,7 +21,7 @@
 #include "libavutil/mem.h"
 #include "asf.h"
 #include "demux.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "internal.h"
 
 /* List of official tags at 
http://msdn.microsoft.com/en-us/library/dd743066(VS.85).aspx */
@@ -130,11 +130,11 @@ static int get_id3_tag(AVFormatContext *s, int len)
 {
     ID3v2ExtraMeta *id3v2_extra_meta;
 
-    ff_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, len);
+    avformat_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, len);
     if (id3v2_extra_meta) {
-        ff_id3v2_parse_apic(s, id3v2_extra_meta);
-        ff_id3v2_parse_chapters(s, id3v2_extra_meta);
-        ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+        avformat_id3v2_parse_apic(s, id3v2_extra_meta);
+        avformat_id3v2_parse_chapters(s, id3v2_extra_meta);
+        avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
     }
     return 0;
 }
diff --git a/libavformat/bonk.c b/libavformat/bonk.c
index cec89b8c17..fe370b40ef 100644
--- a/libavformat/bonk.c
+++ b/libavformat/bonk.c
@@ -72,11 +72,11 @@ static int bonk_read_header(AVFormatContext *s)
                 break;
             } else if (t == MKTAG(' ','I','D','3')) {
                 avio_seek(s->pb, -3, SEEK_CUR);
-                ff_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &extra_meta, 0);
+                avformat_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &extra_meta, 0);
                 if (extra_meta) {
-                    ff_id3v2_parse_apic(s, extra_meta);
-                    ff_id3v2_parse_priv(s, extra_meta);
-                    ff_id3v2_free_extra_meta(&extra_meta);
+                    avformat_id3v2_parse_apic(s, extra_meta);
+                    avformat_id3v2_parse_priv(s, extra_meta);
+                    avformat_id3v2_free_extra_meta(&extra_meta);
                 }
                 avio_skip(s->pb, 8);
             } else {
diff --git a/libavformat/demux.c b/libavformat/demux.c
index a1909237f0..5a19a7dac9 100644
--- a/libavformat/demux.c
+++ b/libavformat/demux.c
@@ -317,7 +317,7 @@ int avformat_open_input(AVFormatContext **ps, const char 
*filename,
 
     /* e.g. AVFMT_NOFILE formats will not have an AVIOContext */
     if (s->pb && is_id3v2_format(s->iformat))
-        ff_id3v2_read_dict(s->pb, &si->id3v2_meta, ID3v2_DEFAULT_MAGIC, 
&id3v2_extra_meta);
+        avformat_id3v2_read_dict(s->pb, &si->id3v2_meta, ID3v2_DEFAULT_MAGIC, 
&id3v2_extra_meta);
 
     if (ffifmt(s->iformat)->read_header)
         if ((ret = ffifmt(s->iformat)->read_header(s)) < 0) {
@@ -335,13 +335,13 @@ int avformat_open_input(AVFormatContext **ps, const char 
*filename,
     }
 
     if (id3v2_extra_meta) {
-        if ((ret = ff_id3v2_parse_apic(s, id3v2_extra_meta)) < 0)
+        if ((ret = avformat_id3v2_parse_apic(s, id3v2_extra_meta)) < 0)
             goto close;
-        if ((ret = ff_id3v2_parse_chapters(s, id3v2_extra_meta)) < 0)
+        if ((ret = avformat_id3v2_parse_chapters(s, id3v2_extra_meta)) < 0)
             goto close;
-        if ((ret = ff_id3v2_parse_priv(s, id3v2_extra_meta)) < 0)
+        if ((ret = avformat_id3v2_parse_priv(s, id3v2_extra_meta)) < 0)
             goto close;
-        ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+        avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
     }
 
     if ((ret = avformat_queue_attached_pictures(s)) < 0)
@@ -365,7 +365,7 @@ close:
     if (ffifmt(s->iformat)->read_close)
         ffifmt(s->iformat)->read_close(s);
 fail:
-    ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+    avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
     av_dict_free(&tmp);
     if (s->pb && !(s->flags & AVFMT_FLAG_CUSTOM_IO))
         avio_closep(&s->pb);
diff --git a/libavformat/dsfdec.c b/libavformat/dsfdec.c
index 87a5fd0272..20a0436910 100644
--- a/libavformat/dsfdec.c
+++ b/libavformat/dsfdec.c
@@ -56,12 +56,12 @@ static void read_id3(AVFormatContext *s, uint64_t id3pos)
     if (avio_seek(s->pb, id3pos, SEEK_SET) < 0)
         return;
 
-    ff_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, 0);
+    avformat_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, 0);
     if (id3v2_extra_meta) {
-        ff_id3v2_parse_apic(s, id3v2_extra_meta);
-        ff_id3v2_parse_chapters(s, id3v2_extra_meta);
+        avformat_id3v2_parse_apic(s, id3v2_extra_meta);
+        avformat_id3v2_parse_chapters(s, id3v2_extra_meta);
     }
-    ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+    avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
 }
 
 static int dsf_read_header(AVFormatContext *s)
diff --git a/libavformat/flac_picture.c b/libavformat/flac_picture.c
index a81eb71482..347ceae214 100644
--- a/libavformat/flac_picture.c
+++ b/libavformat/flac_picture.c
@@ -26,7 +26,7 @@
 #include "avio_internal.h"
 #include "demux.h"
 #include "flac_picture.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "internal.h"
 
 #define MAX_TRUNC_PICTURE_SIZE (500 * 1024 * 1024)
diff --git a/libavformat/flacenc.c b/libavformat/flacenc.c
index 711119efec..5159428fd6 100644
--- a/libavformat/flacenc.c
+++ b/libavformat/flacenc.c
@@ -28,7 +28,7 @@
 #include "avformat.h"
 #include "avio_internal.h"
 #include "flacenc.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "internal.h"
 #include "mux.h"
 #include "version.h"
diff --git a/libavformat/format.c b/libavformat/format.c
index 83aa980a15..c9451cac6c 100644
--- a/libavformat/format.c
+++ b/libavformat/format.c
@@ -172,8 +172,8 @@ const AVInputFormat *av_probe_input_format3(const 
AVProbeData *pd,
     if (!lpd.buf)
         lpd.buf = (unsigned char *) zerobuffer;
 
-    while (lpd.buf_size > 10 && ff_id3v2_match(lpd.buf, ID3v2_DEFAULT_MAGIC)) {
-        int id3len = ff_id3v2_tag_len(lpd.buf);
+    while (lpd.buf_size > 10 && avformat_id3v2_match(lpd.buf, 
ID3v2_DEFAULT_MAGIC)) {
+        int id3len = avformat_id3v2_tag_len(lpd.buf);
         if (lpd.buf_size > id3len + 16) {
             if (lpd.buf_size < 2LL*id3len + 16)
                 nodat = ID3_ALMOST_GREATER_PROBE;
diff --git a/libavformat/hls.c b/libavformat/hls.c
index df13b139f1..25ce59be71 100644
--- a/libavformat/hls.c
+++ b/libavformat/hls.c
@@ -275,7 +275,7 @@ static void free_playlist_list(HLSContext *c)
         av_freep(&pls->renditions);
         av_freep(&pls->id3_buf);
         av_dict_free(&pls->id3_initial);
-        ff_id3v2_free_extra_meta(&pls->id3_deferred_extra);
+        avformat_id3v2_free_extra_meta(&pls->id3_deferred_extra);
         av_freep(&pls->init_sec_buf);
         av_packet_free(&pls->pkt);
         av_freep(&pls->pb.pub.buffer);
@@ -1165,7 +1165,7 @@ static void parse_id3(AVFormatContext *s, AVIOContext *pb,
     static const char id3_priv_owner_audio_setup[] = 
"com.apple.streaming.audioDescription";
     ID3v2ExtraMeta *meta;
 
-    ff_id3v2_read_dict(pb, metadata, ID3v2_DEFAULT_MAGIC, extra_meta);
+    avformat_id3v2_read_dict(pb, metadata, ID3v2_DEFAULT_MAGIC, extra_meta);
     for (meta = *extra_meta; meta; meta = meta->next) {
         if (!strcmp(meta->tag, "PRIV")) {
             ID3v2ExtraMetaPRIV *priv = &meta->data.priv;
@@ -1236,12 +1236,12 @@ static void handle_id3(AVIOContext *pb, struct playlist 
*pls)
 
         /* get picture attachment and set text metadata */
         if (pls->ctx->nb_streams)
-            ff_id3v2_parse_apic(pls->ctx, extra_meta);
+            avformat_id3v2_parse_apic(pls->ctx, extra_meta);
         else
             /* demuxer not yet opened, defer picture attachment */
             pls->id3_deferred_extra = extra_meta;
 
-        ff_id3v2_parse_priv_dict(&metadata, extra_meta);
+        avformat_id3v2_parse_priv_dict(&metadata, extra_meta);
         av_dict_copy(&pls->ctx->metadata, metadata, 0);
         pls->id3_initial = metadata;
 
@@ -1254,7 +1254,7 @@ static void handle_id3(AVIOContext *pb, struct playlist 
*pls)
     }
 
     if (!pls->id3_deferred_extra)
-        ff_id3v2_free_extra_meta(&extra_meta);
+        avformat_id3v2_free_extra_meta(&extra_meta);
 }
 
 static void intercept_id3(struct playlist *pls, uint8_t *buf,
@@ -1291,9 +1291,9 @@ static void intercept_id3(struct playlist *pls, uint8_t 
*buf,
         if (*len < ID3v2_HEADER_SIZE)
             break;
 
-        if (ff_id3v2_match(buf, ID3v2_DEFAULT_MAGIC)) {
+        if (avformat_id3v2_match(buf, ID3v2_DEFAULT_MAGIC)) {
             int64_t maxsize = seg->size >= 0 ? seg->size : 1024*1024;
-            int taglen = ff_id3v2_tag_len(buf);
+            int taglen = avformat_id3v2_tag_len(buf);
             int tag_got_bytes = FFMIN(taglen, *len);
             int remaining = taglen - tag_got_bytes;
 
@@ -2385,10 +2385,10 @@ static int hls_read_header(AVFormatContext *s)
             return ret;
 
         if (pls->id3_deferred_extra && pls->ctx->nb_streams == 1) {
-            ff_id3v2_parse_apic(pls->ctx, pls->id3_deferred_extra);
+            avformat_id3v2_parse_apic(pls->ctx, pls->id3_deferred_extra);
             avformat_queue_attached_pictures(pls->ctx);
-            ff_id3v2_parse_priv(pls->ctx, pls->id3_deferred_extra);
-            ff_id3v2_free_extra_meta(&pls->id3_deferred_extra);
+            avformat_id3v2_parse_priv(pls->ctx, pls->id3_deferred_extra);
+            avformat_id3v2_free_extra_meta(&pls->id3_deferred_extra);
         }
 
         if (pls->is_id3_timestamped == -1)
diff --git a/libavformat/id3v2.c b/libavformat/id3v2.c
index 4942b1ffca..3023bb33d2 100644
--- a/libavformat/id3v2.c
+++ b/libavformat/id3v2.c
@@ -43,7 +43,7 @@
 #include "avio_internal.h"
 #include "demux.h"
 #include "id3v1.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 
 const AVMetadataConv ff_id3v2_34_metadata_conv[] = {
     { "TALB", "album"        },
@@ -146,7 +146,7 @@ const CodecMime ff_id3v2_mime_tags[] = {
     { "",           AV_CODEC_ID_NONE   },
 };
 
-int ff_id3v2_match(const uint8_t *buf, const char *magic)
+int avformat_id3v2_match(const uint8_t *buf, const char *magic)
 {
     return  buf[0]         == magic[0] &&
             buf[1]         == magic[1] &&
@@ -159,7 +159,7 @@ int ff_id3v2_match(const uint8_t *buf, const char *magic)
            (buf[9] & 0x80) == 0;
 }
 
-int ff_id3v2_tag_len(const uint8_t *buf)
+int avformat_id3v2_tag_len(const uint8_t *buf)
 {
     int len = ((buf[6] & 0x7f) << 21) +
               ((buf[7] & 0x7f) << 14) +
@@ -1122,7 +1122,7 @@ static void id3v2_read_internal(AVIOContext *pb, 
AVDictionary **metadata,
             avio_seek(pb, off, SEEK_SET);
             break;
         }
-        found_header = ff_id3v2_match(buf, magic);
+        found_header = avformat_id3v2_match(buf, magic);
         if (found_header) {
             /* parse ID3v2 header */
             len = ((buf[6] & 0x7f) << 21) |
@@ -1143,19 +1143,19 @@ static void id3v2_read_internal(AVIOContext *pb, 
AVDictionary **metadata,
         *extra_metap = extra_meta.head;
 }
 
-void ff_id3v2_read_dict(AVIOContext *pb, AVDictionary **metadata,
+void avformat_id3v2_read_dict(AVIOContext *pb, AVDictionary **metadata,
                         const char *magic, ID3v2ExtraMeta **extra_meta)
 {
     id3v2_read_internal(pb, metadata, NULL, magic, extra_meta, 0);
 }
 
-void ff_id3v2_read(AVFormatContext *s, const char *magic,
+void avformat_id3v2_read(AVFormatContext *s, const char *magic,
                    ID3v2ExtraMeta **extra_meta, unsigned int max_search_size)
 {
     id3v2_read_internal(s->pb, &s->metadata, s, magic, extra_meta, 
max_search_size);
 }
 
-void ff_id3v2_free_extra_meta(ID3v2ExtraMeta **extra_meta)
+void avformat_id3v2_free_extra_meta(ID3v2ExtraMeta **extra_meta)
 {
     ID3v2ExtraMeta *current = *extra_meta, *next;
     const ID3v2EMFunc *extra_func;
@@ -1171,7 +1171,7 @@ void ff_id3v2_free_extra_meta(ID3v2ExtraMeta **extra_meta)
     *extra_meta = NULL;
 }
 
-int ff_id3v2_parse_apic(AVFormatContext *s, ID3v2ExtraMeta *extra_meta)
+int avformat_id3v2_parse_apic(AVFormatContext *s, ID3v2ExtraMeta *extra_meta)
 {
     ID3v2ExtraMeta *cur;
 
@@ -1202,7 +1202,7 @@ int ff_id3v2_parse_apic(AVFormatContext *s, 
ID3v2ExtraMeta *extra_meta)
     return 0;
 }
 
-int ff_id3v2_parse_chapters(AVFormatContext *s, ID3v2ExtraMeta *cur)
+int avformat_id3v2_parse_chapters(AVFormatContext *s, ID3v2ExtraMeta *cur)
 {
     AVRational time_base = {1, 1000};
     int ret;
@@ -1227,7 +1227,8 @@ int ff_id3v2_parse_chapters(AVFormatContext *s, 
ID3v2ExtraMeta *cur)
     return 0;
 }
 
-int ff_id3v2_parse_priv_dict(AVDictionary **metadata, ID3v2ExtraMeta 
*extra_meta)
+int avformat_id3v2_parse_priv_dict(AVDictionary **metadata,
+                                   ID3v2ExtraMeta *extra_meta)
 {
     ID3v2ExtraMeta *cur;
     int dict_flags = AV_DICT_DONT_OVERWRITE | AV_DICT_DONT_STRDUP_KEY | 
AV_DICT_DONT_STRDUP_VAL;
@@ -1267,7 +1268,7 @@ int ff_id3v2_parse_priv_dict(AVDictionary **metadata, 
ID3v2ExtraMeta *extra_meta
     return 0;
 }
 
-int ff_id3v2_parse_priv(AVFormatContext *s, ID3v2ExtraMeta *extra_meta)
+int avformat_id3v2_parse_priv(AVFormatContext *s, ID3v2ExtraMeta *extra_meta)
 {
-    return ff_id3v2_parse_priv_dict(&s->metadata, extra_meta);
+    return avformat_id3v2_parse_priv_dict(&s->metadata, extra_meta);
 }
diff --git a/libavformat/id3v2.h b/libavformat/id3v2.h
index 9afa5a2ddc..a49705efab 100644
--- a/libavformat/id3v2.h
+++ b/libavformat/id3v2.h
@@ -24,8 +24,6 @@
 
 #include <stdint.h>
 #include "avformat.h"
-#include "internal.h"
-#include "metadata.h"
 
 #define ID3v2_HEADER_SIZE 10
 
@@ -34,26 +32,8 @@
  */
 #define ID3v2_DEFAULT_MAGIC "ID3"
 
-#define ID3v2_FLAG_DATALEN     0x0001
-#define ID3v2_FLAG_UNSYNCH     0x0002
-#define ID3v2_FLAG_ENCRYPTION  0x0004
-#define ID3v2_FLAG_COMPRESSION 0x0008
-
 #define ID3v2_PRIV_METADATA_PREFIX "id3v2_priv."
 
-enum ID3v2Encoding {
-    ID3v2_ENCODING_ISO8859  = 0,
-    ID3v2_ENCODING_UTF16BOM = 1,
-    ID3v2_ENCODING_UTF16BE  = 2,
-    ID3v2_ENCODING_UTF8     = 3,
-};
-
-typedef struct ID3v2EncContext {
-    int      version;       ///< ID3v2 minor version, either 3 or 4
-    int64_t size_pos;       ///< offset of the tag total size
-    int          len;       ///< size of the tag written so far
-} ID3v2EncContext;
-
 typedef struct ID3v2ExtraMetaGEOB {
     uint32_t datasize;
     uint8_t *mime_type;
@@ -98,23 +78,26 @@ typedef struct ID3v2ExtraMeta {
  * @param magic magic bytes to identify the header.
  * If in doubt, use ID3v2_DEFAULT_MAGIC.
  */
-int ff_id3v2_match(const uint8_t *buf, const char *magic);
+int avformat_id3v2_match(const uint8_t *buf, const char *magic);
 
 /**
  * Get the length of an ID3v2 tag.
  * @param buf must be ID3v2_HEADER_SIZE bytes long and point to the start of an
  * already detected ID3v2 tag
  */
-int ff_id3v2_tag_len(const uint8_t *buf);
+int avformat_id3v2_tag_len(const uint8_t *buf);
 
 /**
- * Read an ID3v2 tag into specified dictionary and retrieve supported extra 
metadata.
+ * Read an ID3v2 tag into specified dictionary and retrieve supported
+ * extra metadata.
  *
  * @param metadata Parsed metadata is stored here
- * @param[out] extra_meta If not NULL, extra metadata is parsed into a list of
- * ID3v2ExtraMeta structs and *extra_meta points to the head of the list
+ * @param[out] extra_meta If not NULL, extra metadata is parsed into a
+ * list of ID3v2ExtraMeta structs and *extra_meta points to the head
  */
-void ff_id3v2_read_dict(AVIOContext *pb, AVDictionary **metadata, const char 
*magic, ID3v2ExtraMeta **extra_meta);
+void avformat_id3v2_read_dict(AVIOContext *pb, AVDictionary **metadata,
+                              const char *magic,
+                              ID3v2ExtraMeta **extra_meta);
 
 /**
  * Read an ID3v2 tag, including supported extra metadata.
@@ -123,92 +106,44 @@ void ff_id3v2_read_dict(AVIOContext *pb, AVDictionary 
**metadata, const char *ma
  *
  * @param[out] extra_meta If not NULL, extra metadata is parsed into a list of
  * ID3v2ExtraMeta structs and *extra_meta points to the head of the list
- * @param[opt] max_search_search restrict ID3 magic number search (bytes from 
start)
+ * @param[opt] max_search_size restrict ID3 magic number search
+ * (bytes from start)
  */
-void ff_id3v2_read(AVFormatContext *s, const char *magic, ID3v2ExtraMeta 
**extra_meta,
-                   unsigned int max_search_size);
-
-/**
- * Initialize an ID3v2 tag.
- */
-void ff_id3v2_start(ID3v2EncContext *id3, AVIOContext *pb, int id3v2_version,
-                    const char *magic);
-
-/**
- * Convert and write all global metadata from s into an ID3v2 tag.
- */
-int ff_id3v2_write_metadata(AVFormatContext *s, ID3v2EncContext *id3);
-
-/**
- * Write an attached picture from pkt into an ID3v2 tag.
- */
-int ff_id3v2_write_apic(AVFormatContext *s, ID3v2EncContext *id3, AVPacket 
*pkt);
-
-/**
- * Finalize an opened ID3v2 tag.
- */
-void ff_id3v2_finish(ID3v2EncContext *id3, AVIOContext *pb, int padding_bytes);
-
-/**
- * Write an ID3v2 tag containing all global metadata from s.
- * @param id3v2_version Subversion of ID3v2; supported values are 3 and 4
- * @param magic magic bytes to identify the header
- * If in doubt, use ID3v2_DEFAULT_MAGIC.
- */
-int ff_id3v2_write_simple(struct AVFormatContext *s, int id3v2_version, const 
char *magic);
+void avformat_id3v2_read(AVFormatContext *s, const char *magic,
+                         ID3v2ExtraMeta **extra_meta,
+                         unsigned int max_search_size);
 
 /**
  * Free memory allocated parsing special (non-text) metadata.
- * @param extra_meta Pointer to a pointer to the head of a ID3v2ExtraMeta 
list, *extra_meta is set to NULL.
+ * @param extra_meta Pointer to a pointer to the head of a ID3v2ExtraMeta
+ * list, *extra_meta is set to NULL.
  */
-void ff_id3v2_free_extra_meta(ID3v2ExtraMeta **extra_meta);
+void avformat_id3v2_free_extra_meta(ID3v2ExtraMeta **extra_meta);
 
 /**
  * Create a stream for each APIC (attached picture) extracted from the
  * ID3v2 header.
  */
-int ff_id3v2_parse_apic(AVFormatContext *s, ID3v2ExtraMeta *extra_meta);
+int avformat_id3v2_parse_apic(AVFormatContext *s, ID3v2ExtraMeta *extra_meta);
 
 /**
  * Create chapters for all CHAP tags found in the ID3v2 header.
  */
-int ff_id3v2_parse_chapters(AVFormatContext *s, ID3v2ExtraMeta *extra_meta);
+int avformat_id3v2_parse_chapters(AVFormatContext *s,
+                                   ID3v2ExtraMeta *extra_meta);
 
 /**
  * Parse PRIV tags into a dictionary. The PRIV owner is the metadata key. The
  * PRIV data is the value, with non-printable characters escaped.
  */
-int ff_id3v2_parse_priv_dict(AVDictionary **d, ID3v2ExtraMeta *extra_meta);
+int avformat_id3v2_parse_priv_dict(AVDictionary **d,
+                                   ID3v2ExtraMeta *extra_meta);
 
 /**
  * Add metadata for all PRIV tags in the ID3v2 header. The PRIV owner is the
  * metadata key. The PRIV data is the value, with non-printable characters
  * escaped.
  */
-int ff_id3v2_parse_priv(AVFormatContext *s, ID3v2ExtraMeta *extra_meta);
-
-extern const AVMetadataConv ff_id3v2_34_metadata_conv[];
-extern const AVMetadataConv ff_id3v2_4_metadata_conv[];
-
-/**
- * A list of text information frames allowed in both ID3 v2.3 and v2.4
- * http://www.id3.org/id3v2.4.0-frames
- * http://www.id3.org/id3v2.4.0-changes
- */
-extern const char ff_id3v2_tags[][4];
-
-/**
- * ID3v2.4-only text information frames.
- */
-extern const char ff_id3v2_4_tags[][4];
-
-/**
- * ID3v2.3-only text information frames.
- */
-extern const char ff_id3v2_3_tags[][4];
-
-extern const CodecMime ff_id3v2_mime_tags[];
-
-extern const char * const ff_id3v2_picture_types[21];
+int avformat_id3v2_parse_priv(AVFormatContext *s, ID3v2ExtraMeta *extra_meta);
 
 #endif /* AVFORMAT_ID3V2_H */
diff --git a/libavformat/id3v2_internal.h b/libavformat/id3v2_internal.h
new file mode 100644
index 0000000000..7de661ad91
--- /dev/null
+++ b/libavformat/id3v2_internal.h
@@ -0,0 +1,102 @@
+/*
+ * ID3v2 header parser - internal declarations
+ * Copyright (c) 2003 Fabrice Bellard
+ *
+ * This file is part of FFmpeg.
+ *
+ * FFmpeg is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * FFmpeg is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with FFmpeg; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#ifndef AVFORMAT_ID3V2_INTERNAL_H
+#define AVFORMAT_ID3V2_INTERNAL_H
+
+#include "id3v2.h"
+#include "internal.h"
+#include "metadata.h"
+
+#define ID3v2_FLAG_DATALEN     0x0001
+#define ID3v2_FLAG_UNSYNCH     0x0002
+#define ID3v2_FLAG_ENCRYPTION  0x0004
+#define ID3v2_FLAG_COMPRESSION 0x0008
+
+enum ID3v2Encoding {
+    ID3v2_ENCODING_ISO8859  = 0,
+    ID3v2_ENCODING_UTF16BOM = 1,
+    ID3v2_ENCODING_UTF16BE  = 2,
+    ID3v2_ENCODING_UTF8     = 3,
+};
+
+typedef struct ID3v2EncContext {
+    int      version;       ///< ID3v2 minor version, either 3 or 4
+    int64_t size_pos;       ///< offset of the tag total size
+    int          len;       ///< size of the tag written so far
+} ID3v2EncContext;
+
+/**
+ * Initialize an ID3v2 tag.
+ */
+void ff_id3v2_start(ID3v2EncContext *id3, AVIOContext *pb, int id3v2_version,
+                    const char *magic);
+
+/**
+ * Convert and write all global metadata from s into an ID3v2 tag.
+ */
+int ff_id3v2_write_metadata(AVFormatContext *s, ID3v2EncContext *id3);
+
+/**
+ * Write an attached picture from pkt into an ID3v2 tag.
+ */
+int ff_id3v2_write_apic(AVFormatContext *s, ID3v2EncContext *id3,
+                        AVPacket *pkt);
+
+/**
+ * Finalize an opened ID3v2 tag.
+ */
+void ff_id3v2_finish(ID3v2EncContext *id3, AVIOContext *pb, int padding_bytes);
+
+/**
+ * Write an ID3v2 tag containing all global metadata from s.
+ * @param id3v2_version Subversion of ID3v2; supported values are 3 and 4
+ * @param magic magic bytes to identify the header
+ * If in doubt, use ID3v2_DEFAULT_MAGIC.
+ */
+int ff_id3v2_write_simple(struct AVFormatContext *s, int id3v2_version,
+                          const char *magic);
+
+extern const AVMetadataConv ff_id3v2_34_metadata_conv[];
+extern const AVMetadataConv ff_id3v2_4_metadata_conv[];
+
+/**
+ * A list of text information frames allowed in both ID3 v2.3 and v2.4
+ * http://www.id3.org/id3v2.4.0-frames
+ * http://www.id3.org/id3v2.4.0-changes
+ */
+extern const char ff_id3v2_tags[][4];
+
+/**
+ * ID3v2.4-only text information frames.
+ */
+extern const char ff_id3v2_4_tags[][4];
+
+/**
+ * ID3v2.3-only text information frames.
+ */
+extern const char ff_id3v2_3_tags[][4];
+
+extern const CodecMime ff_id3v2_mime_tags[];
+
+extern const char * const ff_id3v2_picture_types[21];
+
+#endif /* AVFORMAT_ID3V2_INTERNAL_H */
diff --git a/libavformat/id3v2enc.c b/libavformat/id3v2enc.c
index ac907c2758..480d3204c2 100644
--- a/libavformat/id3v2enc.c
+++ b/libavformat/id3v2enc.c
@@ -27,7 +27,7 @@
 #include "avformat.h"
 #include "avio.h"
 #include "avio_internal.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "mux.h"
 
 static void id3v2_put_size(AVIOContext *pb, int size)
diff --git a/libavformat/iff.c b/libavformat/iff.c
index 8dccd58b35..c1b4bc43e5 100644
--- a/libavformat/iff.c
+++ b/libavformat/iff.c
@@ -323,14 +323,14 @@ static int parse_dsd_prop(AVFormatContext *s, AVStream 
*st, uint64_t eof)
             break;
 
         case MKTAG('I','D','3',' '):
-            ff_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, size);
+            avformat_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, 
size);
             if (id3v2_extra_meta) {
-                if ((ret = ff_id3v2_parse_apic(s, id3v2_extra_meta)) < 0 ||
-                    (ret = ff_id3v2_parse_chapters(s, id3v2_extra_meta)) < 0) {
-                    ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+                if ((ret = avformat_id3v2_parse_apic(s, id3v2_extra_meta)) < 0 
||
+                    (ret = avformat_id3v2_parse_chapters(s, id3v2_extra_meta)) 
< 0) {
+                    avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
                     return ret;
                 }
-                ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+                avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
             }
 
             if (size < avio_tell(pb) - orig_pos) {
diff --git a/libavformat/mp3dec.c b/libavformat/mp3dec.c
index 5b153c7c9e..9114278219 100644
--- a/libavformat/mp3dec.c
+++ b/libavformat/mp3dec.c
@@ -122,7 +122,7 @@ static int mp3_read_probe(const AVProbeData *p)
     if   (first_frames>=7) return AVPROBE_SCORE_EXTENSION + 1;
     else if (max_frames>200 && p->buf_size < 2*max_framesizes)return 
AVPROBE_SCORE_EXTENSION;
     else if (max_frames>=4 && p->buf_size < 2*max_framesizes) return 
AVPROBE_SCORE_EXTENSION / 2;
-    else if (ff_id3v2_match(buf0, ID3v2_DEFAULT_MAGIC) && 
2*ff_id3v2_tag_len(buf0) >= p->buf_size)
+    else if (avformat_id3v2_match(buf0, ID3v2_DEFAULT_MAGIC) && 
2*avformat_id3v2_tag_len(buf0) >= p->buf_size)
                            return p->buf_size < PROBE_BUF_MAX ? 
AVPROBE_SCORE_EXTENSION / 4 : AVPROBE_SCORE_EXTENSION - 2;
     else if (first_frames > 1 && whole_used) return 5;
     else if (max_frames>=1 && p->buf_size < 10*max_framesizes) return 1;
diff --git a/libavformat/mp3enc.c b/libavformat/mp3enc.c
index 724c7269dc..3928ca829d 100644
--- a/libavformat/mp3enc.c
+++ b/libavformat/mp3enc.c
@@ -22,7 +22,7 @@
 #include "avformat.h"
 #include "avio_internal.h"
 #include "id3v1.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "mux.h"
 #include "rawenc.h"
 #include "libavutil/avstring.h"
diff --git a/libavformat/omadec.c b/libavformat/omadec.c
index 552a37df18..70db704b6a 100644
--- a/libavformat/omadec.c
+++ b/libavformat/omadec.c
@@ -414,21 +414,21 @@ static int oma_read_header(AVFormatContext *s)
     ID3v2ExtraMeta *extra_meta;
     OMAContext *oc = s->priv_data;
 
-    ff_id3v2_read(s, ID3v2_EA3_MAGIC, &extra_meta, 0);
-    if ((ret = ff_id3v2_parse_chapters(s, extra_meta)) < 0) {
-        ff_id3v2_free_extra_meta(&extra_meta);
+    avformat_id3v2_read(s, ID3v2_EA3_MAGIC, &extra_meta, 0);
+    if ((ret = avformat_id3v2_parse_chapters(s, extra_meta)) < 0) {
+        avformat_id3v2_free_extra_meta(&extra_meta);
         return ret;
     }
 
     ret = avio_read(s->pb, buf, EA3_HEADER_SIZE);
     if (ret < EA3_HEADER_SIZE) {
-        ff_id3v2_free_extra_meta(&extra_meta);
+        avformat_id3v2_free_extra_meta(&extra_meta);
         return -1;
     }
 
     if (memcmp(buf, ((const uint8_t[]){'E', 'A', '3'}), 3) ||
         buf[4] != 0 || buf[5] != EA3_HEADER_SIZE) {
-        ff_id3v2_free_extra_meta(&extra_meta);
+        avformat_id3v2_free_extra_meta(&extra_meta);
         av_log(s, AV_LOG_ERROR, "Couldn't find the EA3 header !\n");
         return AVERROR_INVALIDDATA;
     }
@@ -438,11 +438,11 @@ static int oma_read_header(AVFormatContext *s)
     /* encrypted file */
     eid = AV_RB16(&buf[6]);
     if (eid != -1 && eid != -128 && decrypt_init(s, extra_meta, buf) < 0) {
-        ff_id3v2_free_extra_meta(&extra_meta);
+        avformat_id3v2_free_extra_meta(&extra_meta);
         return -1;
     }
 
-    ff_id3v2_free_extra_meta(&extra_meta);
+    avformat_id3v2_free_extra_meta(&extra_meta);
 
     codec_params = AV_RB24(&buf[33]);
 
@@ -562,8 +562,8 @@ static int oma_read_probe(const AVProbeData *p)
     const uint8_t *buf = p->buf;
     unsigned tag_len = 0;
 
-    if (p->buf_size >= ID3v2_HEADER_SIZE && ff_id3v2_match(buf, 
ID3v2_EA3_MAGIC))
-        tag_len = ff_id3v2_tag_len(buf);
+    if (p->buf_size >= ID3v2_HEADER_SIZE && avformat_id3v2_match(buf, 
ID3v2_EA3_MAGIC))
+        tag_len = avformat_id3v2_tag_len(buf);
 
     /* This check cannot overflow as tag_len has at most 28 bits */
     if (p->buf_size < tag_len + 5)
diff --git a/libavformat/omaenc.c b/libavformat/omaenc.c
index b553bc3e9d..d71c8a2347 100644
--- a/libavformat/omaenc.c
+++ b/libavformat/omaenc.c
@@ -22,7 +22,7 @@
 
 #include "avformat.h"
 #include "avio_internal.h"
-#include "id3v2.h"
+#include "id3v2_internal.h"
 #include "internal.h"
 #include "mux.h"
 #include "oma.h"
diff --git a/libavformat/version.h b/libavformat/version.h
index ff831498b3..14bf700274 100644
--- a/libavformat/version.h
+++ b/libavformat/version.h
@@ -31,8 +31,8 @@
 
 #include "version_major.h"
 
-#define LIBAVFORMAT_VERSION_MINOR  13
-#define LIBAVFORMAT_VERSION_MICRO 102
+#define LIBAVFORMAT_VERSION_MINOR  14
+#define LIBAVFORMAT_VERSION_MICRO 100
 
 #define LIBAVFORMAT_VERSION_INT AV_VERSION_INT(LIBAVFORMAT_VERSION_MAJOR, \
                                                LIBAVFORMAT_VERSION_MINOR, \
diff --git a/libavformat/wavdec.c b/libavformat/wavdec.c
index f56f9d5c59..2e5d98c7a0 100644
--- a/libavformat/wavdec.c
+++ b/libavformat/wavdec.c
@@ -565,13 +565,13 @@ static int wav_read_header(AVFormatContext *s)
         case MKTAG('I', 'D', '3', ' '):
         case MKTAG('i', 'd', '3', ' '): {
             ID3v2ExtraMeta *id3v2_extra_meta;
-            ff_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, 0);
+            avformat_id3v2_read(s, ID3v2_DEFAULT_MAGIC, &id3v2_extra_meta, 0);
             if (id3v2_extra_meta) {
-                ff_id3v2_parse_apic(s, id3v2_extra_meta);
-                ff_id3v2_parse_chapters(s, id3v2_extra_meta);
-                ff_id3v2_parse_priv(s, id3v2_extra_meta);
+                avformat_id3v2_parse_apic(s, id3v2_extra_meta);
+                avformat_id3v2_parse_chapters(s, id3v2_extra_meta);
+                avformat_id3v2_parse_priv(s, id3v2_extra_meta);
             }
-            ff_id3v2_free_extra_meta(&id3v2_extra_meta);
+            avformat_id3v2_free_extra_meta(&id3v2_extra_meta);
             }
             break;
         case MKTAG('c', 'u', 'e', ' '):
-- 
2.52.0

_______________________________________________
ffmpeg-devel mailing list -- [email protected]
To unsubscribe send an email to [email protected]

Reply via email to