summaryrefslogtreecommitdiffstats
path: root/gst/id3demux
diff options
context:
space:
mode:
authorTim-Philipp Müller <tim@centricular.net>2006-03-14 17:56:02 +0000
committerTim-Philipp Müller <tim@centricular.net>2006-03-14 17:56:02 +0000
commit6fe8d341296563c1ecb3fd6a263ace72ec4642a1 (patch)
tree62b721207d83116f8c9e0f9f891914f457afa2f2 /gst/id3demux
parentcc5d085a00dee7476193c2bb86ed3b06b7ec32e6 (diff)
configure.ac: Bump -base requirement to 0.10.5 for gst_tag_from_id3_user_tag(), used by id3demux.
Original commit message from CVS: * configure.ac: Bump -base requirement to 0.10.5 for gst_tag_from_id3_user_tag(), used by id3demux. * gst/id3demux/gstid3demux.c: (plugin_init): * gst/id3demux/id3v2frames.c: (id3demux_id3v2_parse_frame), (parse_user_text_identification_frame), (parse_unique_file_identifier): Add support for UFID and TXXX frames and extract musicbrainz tags.
Diffstat (limited to 'gst/id3demux')
-rw-r--r--gst/id3demux/gstid3demux.c3
-rw-r--r--gst/id3demux/id3v2frames.c92
2 files changed, 94 insertions, 1 deletions
diff --git a/gst/id3demux/gstid3demux.c b/gst/id3demux/gstid3demux.c
index de5b0204..a1ccfadd 100644
--- a/gst/id3demux/gstid3demux.c
+++ b/gst/id3demux/gstid3demux.c
@@ -45,6 +45,7 @@
#include <gst/gst.h>
#include <gst/base/gsttypefindhelper.h>
#include <gst/gst-i18n-plugin.h>
+#include <gst/tag/tag.h>
#include "gstid3demux.h"
#include "id3tags.h"
@@ -1045,6 +1046,8 @@ plugin_init (GstPlugin * plugin)
GST_DEBUG_CATEGORY_INIT (id3demux_debug, "id3demux", 0,
"GStreamer ID3 tag demuxer");
+ gst_tag_register_musicbrainz_tags ();
+
return gst_element_register (plugin, "id3demux",
GST_RANK_PRIMARY, GST_TYPE_ID3DEMUX);
}
diff --git a/gst/id3demux/id3v2frames.c b/gst/id3demux/id3v2frames.c
index bab609de..81ff3472 100644
--- a/gst/id3demux/id3v2frames.c
+++ b/gst/id3demux/id3v2frames.c
@@ -37,6 +37,10 @@ GST_DEBUG_CATEGORY_EXTERN (id3demux_debug);
static gchar *parse_comment_frame (ID3TagsWorking * work);
static GArray *parse_text_identification_frame (ID3TagsWorking * work);
+static gchar *parse_user_text_identification_frame (ID3TagsWorking * work,
+ const gchar ** tag_name);
+static gchar *parse_unique_file_identifier (ID3TagsWorking * work,
+ const gchar ** tag_name);
static gboolean id3v2_tag_to_taglist (ID3TagsWorking * work,
const gchar * tag_name, const gchar * tag_str);
/* Parse a single string into an array of gchar* */
@@ -85,8 +89,11 @@ id3demux_id3v2_parse_frame (ID3TagsWorking * work)
}
tag_name = gst_tag_from_id3_tag (work->frame_id);
- if (tag_name == NULL)
+ if (tag_name == NULL &&
+ strncmp (work->frame_id, "TXXX", 4) != 0 &&
+ strncmp (work->frame_id, "UFID", 4) != 0) {
return FALSE;
+ }
if (work->frame_flags & (ID3V2_FRAME_FORMAT_COMPRESSION |
ID3V2_FRAME_FORMAT_DATA_LENGTH_INDICATOR)) {
@@ -140,6 +147,7 @@ id3demux_id3v2_parse_frame (ID3TagsWorking * work)
tag_fields = parse_text_identification_frame (work);
} else {
/* Handle user text frame */
+ tag_str = parse_user_text_identification_frame (work, &tag_name);
}
} else if (!strcmp (work->frame_id, "COMM")) {
/* Comment */
@@ -150,6 +158,7 @@ id3demux_id3v2_parse_frame (ID3TagsWorking * work)
/* Relative volume */
} else if (!strcmp (work->frame_id, "UFID")) {
/* Unique file identifier */
+ tag_str = parse_unique_file_identifier (work, &tag_name);
}
if (work->frame_flags & ID3V2_FRAME_FORMAT_COMPRESSION)
@@ -251,6 +260,87 @@ parse_text_identification_frame (ID3TagsWorking * work)
return fields;
}
+static gchar *
+parse_user_text_identification_frame (ID3TagsWorking * work,
+ const gchar ** tag_name)
+{
+ gchar *ret;
+ guchar encoding;
+ GArray *fields = NULL;
+
+ *tag_name = NULL;
+
+ if (work->parse_size < 2)
+ return NULL;
+
+ encoding = work->parse_data[0];
+
+ parse_split_strings (encoding, (gchar *) work->parse_data + 1,
+ work->parse_size - 1, &fields);
+
+ if (fields == NULL)
+ return NULL;
+
+ if (fields->len != 2) {
+ GST_WARNING ("Expected 2 fields in TXXX frame, but got %d", fields->len);
+ free_tag_strings (fields);
+ return NULL;
+ }
+
+ *tag_name =
+ gst_tag_from_id3_user_tag ("TXXX", g_array_index (fields, gchar *, 0));
+
+ GST_LOG ("TXXX frame of size %d. Mapped descriptor '%s' to GStreamer tag %s",
+ work->parse_size - 1, g_array_index (fields, gchar *, 0),
+ GST_STR_NULL (*tag_name));
+
+ if (*tag_name) {
+ ret = g_strdup (g_array_index (fields, gchar *, 1));
+ /* GST_LOG ("%s = %s", *tag_name, GST_STR_NULL (ret)); */
+ } else {
+ ret = NULL;
+ }
+
+ free_tag_strings (fields);
+ return ret;
+}
+
+static gchar *
+parse_unique_file_identifier (ID3TagsWorking * work, const gchar ** tag_name)
+{
+ gint len, datalen;
+ gchar *owner_id, *data, *ret = NULL;
+
+ if (work->parse_size < 2)
+ return NULL;
+
+ GST_LOG ("parsing UFID frame of size %d", work->parse_size);
+
+ for (len = 0; len < work->parse_size - 1; ++len) {
+ if (work->parse_data[len] == '\0')
+ break;
+ }
+
+ datalen = work->parse_size - (len + 1);
+ if (datalen <= 0)
+ return NULL;
+
+ owner_id = g_strndup ((gchar *) work->parse_data, len);
+ data = (gchar *) work->parse_data + len + 1;
+ GST_LOG ("UFID owner ID: %s (+ %d bytes of data)", owner_id, datalen);
+
+ if (strcmp (owner_id, "http://musicbrainz.org") == 0 &&
+ g_utf8_validate (data, datalen, NULL)) {
+ *tag_name = GST_TAG_MUSICBRAINZ_TRACKID;
+ ret = g_strndup (data, datalen);
+ } else {
+ GST_INFO ("Unknown UFID owner ID: %s", owner_id);
+ }
+ g_free (owner_id);
+
+ return ret;
+}
+
static gboolean
id3v2_tag_to_taglist (ID3TagsWorking * work, const gchar * tag_name,
const gchar * tag_str)