[xiph-commits] r13663 - in icecast/trunk/icecast: admin src

karl at svn.xiph.org karl at svn.xiph.org
Thu Aug 30 16:36:20 PDT 2007


Author: karl
Date: 2007-08-30 16:36:19 -0700 (Thu, 30 Aug 2007)
New Revision: 13663

Modified:
   icecast/trunk/icecast/admin/updatemetadata.xsl
   icecast/trunk/icecast/src/admin.c
   icecast/trunk/icecast/src/format.h
   icecast/trunk/icecast/src/format_mp3.c
   icecast/trunk/icecast/src/format_vorbis.c
   icecast/trunk/icecast/src/source.c
   icecast/trunk/icecast/src/util.c
   icecast/trunk/icecast/src/util.h
Log:
missed some NULL checks from previous character set commit. Add optional charset
setting on metadata update request and conversion code for it.



Modified: icecast/trunk/icecast/admin/updatemetadata.xsl
===================================================================
--- icecast/trunk/icecast/admin/updatemetadata.xsl	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/admin/updatemetadata.xsl	2007-08-30 23:36:19 UTC (rev 13663)
@@ -48,6 +48,7 @@
 </table>
 <input type="hidden" name="mount" value="{@mount}"/>
 <input type="hidden" name="mode" value="updinfo"/>
+<input type="hidden" name="charset" value="UTF-8"/>
 </form>
 
 <br />

Modified: icecast/trunk/icecast/src/admin.c
===================================================================
--- icecast/trunk/icecast/src/admin.c	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/admin.c	2007-08-30 23:36:19 UTC (rev 13663)
@@ -854,7 +854,7 @@
     int response)
 {
     const char *action;
-    const char *song, *title, *artist;
+    const char *song, *title, *artist, *charset;
     format_plugin_t *plugin;
     xmlDocPtr doc;
     xmlNodePtr node;
@@ -869,6 +869,7 @@
     COMMAND_OPTIONAL(client, "song", song);
     COMMAND_OPTIONAL(client, "title", title);
     COMMAND_OPTIONAL(client, "artist", artist);
+    COMMAND_OPTIONAL(client, "charset", charset);
 
     if (strcmp (action, "updinfo") != 0)
     {
@@ -886,15 +887,15 @@
     {
         if (song)
         {
-            plugin->set_tag (plugin, "song", song);
+            plugin->set_tag (plugin, "song", song, charset);
             INFO2 ("Metadata on mountpoint %s changed to \"%s\"", source->mount, song);
         }
         else
         {
             if (artist && title)
             {
-                plugin->set_tag (plugin, "title", title);
-                plugin->set_tag (plugin, "artist", artist);
+                plugin->set_tag (plugin, "title", title, charset);
+                plugin->set_tag (plugin, "artist", artist, charset);
                 INFO3("Metadata on mountpoint %s changed to \"%s - %s\"",
                         source->mount, artist, title);
             }
@@ -936,7 +937,7 @@
 
     if (source->format && source->format->set_tag)
     {
-        source->format->set_tag (source->format, "title", value);
+        source->format->set_tag (source->format, "title", value, NULL);
 
         DEBUG2("Metadata on mountpoint %s changed to \"%s\"", 
                 source->mount, value);

Modified: icecast/trunk/icecast/src/format.h
===================================================================
--- icecast/trunk/icecast/src/format.h	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/format.h	2007-08-30 23:36:19 UTC (rev 13663)
@@ -48,7 +48,7 @@
     int (*write_buf_to_client)(client_t *client);
     void (*write_buf_to_file)(struct source_tag *source, refbuf_t *refbuf);
     int (*create_client_data)(struct source_tag *source, client_t *client);
-    void (*set_tag)(struct _format_plugin_tag *plugin, const char *tag, const char *value);
+    void (*set_tag)(struct _format_plugin_tag *plugin, const char *tag, const char *value, const char *charset);
     void (*free_plugin)(struct _format_plugin_tag *self);
     void (*apply_settings)(client_t *client, struct _format_plugin_tag *format, struct _mount_proxy *mount);
 

Modified: icecast/trunk/icecast/src/format_mp3.c
===================================================================
--- icecast/trunk/icecast/src/format_mp3.c	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/format_mp3.c	2007-08-30 23:36:19 UTC (rev 13663)
@@ -61,7 +61,7 @@
 static void free_mp3_client_data (client_t *client);
 static int format_mp3_write_buf_to_client(client_t *client);
 static void write_mp3_to_file (struct source_tag *source, refbuf_t *refbuf);
-static void mp3_set_tag (format_plugin_t *plugin, const char *tag, const char *value);
+static void mp3_set_tag (format_plugin_t *plugin, const char *tag, const char *in_value, const char *charset);
 static void format_mp3_apply_settings(client_t *client, format_plugin_t *format, mount_proxy *mount);
 
 
@@ -124,42 +124,43 @@
 }
 
 
-static void mp3_set_tag (format_plugin_t *plugin, const char *tag, const char *value)
+static void mp3_set_tag (format_plugin_t *plugin, const char *tag, const char *in_value, const char *charset)
 {
     mp3_state *source_mp3 = plugin->_state;
     unsigned int len;
     const char meta[] = "StreamTitle='";
     int size = sizeof (meta) + 1;
+    char *value;
 
-    if (tag==NULL || value == NULL)
+    if (tag==NULL || in_value == NULL)
         return;
 
+    /* protect against multiple updaters */
+    thread_mutex_lock (&source_mp3->url_lock);
+
+    value = util_conv_string (in_value, charset, plugin->charset);
+    if (value == NULL)
+        value = strdup (in_value);
+
     len = strlen (value)+1;
     size += len;
-    /* protect against multiple updaters */
-    thread_mutex_lock (&source_mp3->url_lock);
+
     if (strcmp (tag, "title") == 0 || strcmp (tag, "song") == 0)
     {
-        char *p = strdup (value);
-        if (p)
-        {
-            free (source_mp3->url_title);
-            free (source_mp3->url_artist);
-            source_mp3->url_artist = NULL;
-            source_mp3->url_title = p;
-            source_mp3->update_metadata = 1;
-        }
+        free (source_mp3->url_title);
+        free (source_mp3->url_artist);
+        source_mp3->url_artist = NULL;
+        source_mp3->url_title = value;
+        source_mp3->update_metadata = 1;
     }
     else if (strcmp (tag, "artist") == 0)
     {
-        char *p = strdup (value);
-        if (p)
-        {
-            free (source_mp3->url_artist);
-            source_mp3->url_artist = p;
-            source_mp3->update_metadata = 1;
-        }
+        free (source_mp3->url_artist);
+        source_mp3->url_artist = value;
+        source_mp3->update_metadata = 1;
     }
+    else
+        free (value);
     thread_mutex_unlock (&source_mp3->url_lock);
 }
 

Modified: icecast/trunk/icecast/src/format_vorbis.c
===================================================================
--- icecast/trunk/icecast/src/format_vorbis.c	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/format_vorbis.c	2007-08-30 23:36:19 UTC (rev 13663)
@@ -67,7 +67,7 @@
 static refbuf_t *process_vorbis_page (ogg_state_t *ogg_info,
                 ogg_codec_t *codec, ogg_page *page);
 static refbuf_t *process_vorbis (ogg_state_t *ogg_info, ogg_codec_t *codec);
-static void vorbis_set_tag (format_plugin_t *plugin, const char *tag, const char *value);
+static void vorbis_set_tag (format_plugin_t *plugin, const char *tag, const char *value, const char *charset);
 
 
 static void free_ogg_packet (ogg_packet *packet)
@@ -413,12 +413,13 @@
 /* called from the admin interface, here we update the artist/title info
  * and schedule a new set of header pages
  */
-static void vorbis_set_tag (format_plugin_t *plugin, const char *tag, const char *value)
+static void vorbis_set_tag (format_plugin_t *plugin, const char *tag, const char *in_value, const char *charset)
 {   
     ogg_state_t *ogg_info = plugin->_state;
     ogg_codec_t *codec = ogg_info->codecs;
     vorbis_codec_t *source_vorbis;
     int change = 0;
+    char *value;
 
     /* avoid updating if multiple codecs in use */
     if (codec && codec->next == NULL)
@@ -426,43 +427,37 @@
     else
         return;
 
+    value = util_conv_string (value, charset, "UTF-8");
+    if (value == NULL)
+        value = strdup (in_value);
+
     if (strcmp (tag, "artist") == 0)
     {
-        char *p = strdup (value);
-        if (p)
-        {
-            free (ogg_info->artist);
-            ogg_info->artist = p;
-            change = 1;
-        }
+        free (ogg_info->artist);
+        ogg_info->artist = value;
+        change = 1;
     }
     if (strcmp (tag, "title") == 0)
     {
-        char *p = strdup (value);
-        if (p)
-        {
-            free (ogg_info->title);
-            ogg_info->title = p;
-            change = 1;
-        }
+        free (ogg_info->title);
+        ogg_info->title = value;
+        change = 1;
     }
     if (strcmp (tag, "song") == 0)
     {
-        char *p = strdup (value);
-        if (p)
-        {
-            free (ogg_info->artist);
-            free (ogg_info->title);
-            ogg_info->artist = NULL;
-            ogg_info->title = p;
-            change = 1;
-        }
+        free (ogg_info->artist);
+        free (ogg_info->title);
+        ogg_info->artist = NULL;
+        ogg_info->title = value;
+        change = 1;
     }
     if (change)
     {
         source_vorbis->stream_notify = 1;
         source_vorbis->rebuild_comment = 1;
     }
+    else
+        free (value);
 }
 
 

Modified: icecast/trunk/icecast/src/source.c
===================================================================
--- icecast/trunk/icecast/src/source.c	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/source.c	2007-08-30 23:36:19 UTC (rev 13663)
@@ -949,6 +949,10 @@
     if (source->client)
         parser = source->client->parser;
 
+    /* to be done before possible non-utf8 stats */
+    if (source->format && source->format->apply_settings)
+        source->format->apply_settings (source->client, source->format, mountinfo);
+
     /* public */
     if (mountinfo && mountinfo->yp_public >= 0)
         val = mountinfo->yp_public;
@@ -994,7 +998,8 @@
             str = "Unspecified name";
         } while (0);
     }
-    stats_event_conv (source->mount, "server_name", str, source->format->charset);
+    if (str && source->format)
+        stats_event_conv (source->mount, "server_name", str, source->format->charset);
 
     /* stream description */
     if (mountinfo && mountinfo->stream_description)
@@ -1011,7 +1016,8 @@
             str = "Unspecified description";
         } while (0);
     }
-    stats_event_conv (source->mount, "server_description", str, source->format->charset);
+    if (str && source->format)
+        stats_event_conv (source->mount, "server_description", str, source->format->charset);
 
     /* stream URL */
     if (mountinfo && mountinfo->stream_url)
@@ -1027,7 +1033,8 @@
             if (str) break;
         } while (0);
     }
-    stats_event (source->mount, "server_url", str);
+    if (str && source->format)
+        stats_event_conv (source->mount, "server_url", str, source->format->charset);
 
     /* stream genre */
     if (mountinfo && mountinfo->stream_genre)
@@ -1044,7 +1051,8 @@
             str = "various";
         } while (0);
     }
-    stats_event_conv (source->mount, "genre", str, source->format->charset);
+    if (str && source->format)
+        stats_event_conv (source->mount, "genre", str, source->format->charset);
 
     /* stream bitrate */
     if (mountinfo && mountinfo->bitrate)
@@ -1132,8 +1140,6 @@
     if (mountinfo && mountinfo->fallback_when_full)
         source->fallback_when_full = mountinfo->fallback_when_full;
 
-    if (source->format && source->format->apply_settings)
-        source->format->apply_settings (source->client, source->format, mountinfo);
     avl_tree_unlock (source->client_tree);
 }
 

Modified: icecast/trunk/icecast/src/util.c
===================================================================
--- icecast/trunk/icecast/src/util.c	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/util.c	2007-08-30 23:36:19 UTC (rev 13663)
@@ -633,3 +633,43 @@
      return result;
 }
 #endif
+
+
+/* helper function for converting a passed string in one character set to another
+ * we use libxml2 for this
+ */
+char *util_conv_string (const char *string, const char *in_charset, const char *out_charset)
+{
+    xmlCharEncodingHandlerPtr in, out;
+    char *ret = NULL;
+
+    if (string == NULL || in_charset == NULL || out_charset == NULL)
+        return NULL;
+
+    in  = xmlFindCharEncodingHandler (in_charset);
+    out = xmlFindCharEncodingHandler (out_charset);
+
+    if (in && out)
+    {
+        xmlBufferPtr orig = xmlBufferCreate ();
+        xmlBufferPtr utf8 = xmlBufferCreate ();
+        xmlBufferPtr conv = xmlBufferCreate ();
+
+        INFO2 ("converting metadata from %s to %s", in_charset, out_charset);
+        xmlBufferCCat (orig, string);
+        if (xmlCharEncInFunc (in, utf8, orig) > 0)
+        {
+            xmlCharEncOutFunc (out, conv, NULL);
+            if (xmlCharEncOutFunc (out, conv, utf8) >= 0)
+                ret = strdup ((const char *)xmlBufferContent (conv));
+        }
+        xmlBufferFree (orig);
+        xmlBufferFree (utf8);
+        xmlBufferFree (conv);
+    }
+    xmlCharEncCloseFunc (in);
+    xmlCharEncCloseFunc (out);
+
+    return ret;
+}
+

Modified: icecast/trunk/icecast/src/util.h
===================================================================
--- icecast/trunk/icecast/src/util.h	2007-08-30 18:36:19 UTC (rev 13662)
+++ icecast/trunk/icecast/src/util.h	2007-08-30 23:36:19 UTC (rev 13663)
@@ -51,5 +51,6 @@
 #ifndef HAVE_LOCALTIME_R
 struct tm *localtime_r (const time_t *timep, struct tm *result);
 #endif
+char *util_conv_string (const char *string, const char *in_charset, const char *out_charset);
 
 #endif  /* __UTIL_H__ */



More information about the commits mailing list