xLoneStar 发表于 2004-7-31 17:25:07

gstreamer 读取 mp3 标记时中文乱码的研究结果

在分析 rhythmbox 显示中文 mp3 标记乱码的问题后,我们意识到这是一个 gstreamer 的问题。gstreamer 向 rhythmbox 提供了与乐曲格式无关的、Unicode 编码的标准化格式的标记信息。

gstreamer-plugins 中的一个插件,mad,负责 mp3 的解码工作。当发现该 mp3 中含有 id3v2 格式的标记信息时,它将调用一个名叫 libid3tag 的库去解析其中的内容。

在最初的 id3 标记信息规范中,没有对存储的字符串的编码作出规定。因此就像绝大多数情况那样,mp3 制作者使用各种形式的“地区编码”,比如 GB2312、Big-5 等,来存储该 mp3 的曲名、歌手等信息,并存储在 iso-8859 字段中。

当 id3v2 规范发布,并规定其中的字符串编码必须是 iso-8859 或者 unicode 时,已经太晚了,满世界的 mp3 都已经在 iso-8859 字段中填写了各类本地编码字符串。换句话说,所谓的 iso-8859 根本就不是它的字面意义,它只是表达说这是一个非 unicode 的字符串而已。

不幸的是 libid3tag 的作者显然并不生活在非西文地区。它忠实地执行了 id3v2 规范的内容:将 iso-8859 字段中的文字精确地按照 iso-8859->unicode 的方式进行转换,并向 gstreamer 提交 unicode 字符串。这样,存储在 iso-8859 字段中的一个中文字符就被编码成了2个 Unicode 字符。对其进行显示的结果,就是乱码。

在此似乎也无法苛责 libid3tag,毕竟它是根据规范而为。因此我选择了对 gstreamer-mad 打补丁,使其正确地按照当前系统所处的 locale,对存储在 iso-8859 字段中的字符串进行 unicode 转换。这样,当你的 locale 为中文时,就能通过 rhythmbox 正确看到中文 mp3 歌曲中的标记信息。

http://www.gnome-cn.org/Members/LoneStar/gst-plugins-native-tags.patch

mandrakechina 发表于 2004-8-2 11:54:40

实际上,libid3tag本身有必要向这种现实妥协。应该添加一个可选参数,表明待取信息的字符集。

xLoneStar 发表于 2004-8-2 15:53:10

从 libid3tag 中确实可以读出这个字符集信息,只是方法比较 ugly。读出之后再自行做转换,也比较 ugly。这2个就是我的补丁用到的方法。

w1ang 发表于 2004-8-3 17:05:09

fedora下对应的gst-plugins文件是哪个?我没找到。

xLoneStar 发表于 2004-8-4 00:28:11

gst-plugins 中的 mad 插件

其他的都在同一目录中

xLoneStar 发表于 2004-8-8 03:11:23

此问题已经报告至 bugzilla.gnome.org,可惜至今无下文。大家支持一把啊:

http://bugzilla.gnome.org/show_bug.cgi?id=149274

mandrakechina 发表于 2004-8-8 03:37:00

http://sourceforge.net/tracker/index.php?func=detail&aid=663888&group_id=12349&atid=112349

个人认为这个方法比较好一点。

xLoneStar 发表于 2004-8-8 10:07:31

这个人只提到了 id3v1...然而目前的状况是 v1 恰恰没有问题,问题出在 v2。v2 确实有编码标记,恰恰是这个标记是错的,才导致了目前的问题。

如果 libid3tag 愿意在此问题上向标准妥协,那么一切便迎刃而解了

mandrakechina 发表于 2004-8-9 13:46:58

问题应该就是在v1上吧。本来id3v1本身都是iso-8859-1的编码,就不应该在里面存放中文,但大家还是不管。id3v2中的中文部分是放在Unicode中。

xLoneStar 发表于 2004-8-9 14:29:24

你看见过哪款 mp3 使用了中文 unicode 标记么?我还没见到过。

用 Winamp 打开一个 v1 的 mp3, 在 id3v2 的框下点一下 Copy from ID3v1,就得到一个 ID3v2 的 mp3。你猜它是怎么编码的?你去网上搜搜,看哪个有 v2 的中文 mp3 使用过了Unicode。

再使用任何一款 windows 下的 mp3 播放软件,从 Realone 到 WMP,甚至随身 mp3 播放器,看有哪款不支持这种形式的 id3v2 标记。

这个问题对我们华人来说不难理解吧?

gstreamer 的 v1 处理代码没问题了,已经做了 locale-to-utf8 转换。现在就是 v2 部分,使用了“错误”的转换方法。

w1ang 发表于 2004-8-9 20:39:25

这是fedora的gstid3tag.c文件,请教如何补丁?

xLoneStar 发表于 2004-8-9 23:07:06

楼上的,下次还是用附件的好不好?看着累

这个文件处理了 id3v1。在其中函数 gst_tag_extract() 处我们可以看见已经调用了 g_locale_to_utf8() 进行转换,所以这段代码是没问题的,无须补丁。

mandrakechina 发表于 2004-8-9 23:41:24

gstreamer 的 v1 处理代码没问题了,已经做了 locale-to-utf8 转换。现在就是 v2 部分,使用了“错误”的转换方法。
我觉得现在的MP3似乎还是id3v1的比较多,设置了v2还是少数的。现在的情况是,连v1的都识别不了。看来不管是v1还是v2,只要是ISO-8859-1的部分,其实都是ANSI的了。

细究起来,强制从当前locale转到utf-8也不一定那么可行,最好是可选的locale,默认就是当前locale。

w1ang 发表于 2004-8-10 00:53:50

楼上的,下次还是用附件的好不好?看着累

这个文件处理了 id3v1。在其中函数 gst_tag_extract() 处我们可以看见已经调用了 g_locale_to_utf8() 进行转换,所以这段代码是没问题的,无须补丁。
那id3v2呢?我的无法正常显示中文曲目。

xLoneStar 发表于 2004-8-10 11:33:30

id3v2 的问题这里有个补丁,补的是 gst-plugin-mad。当然如前述,问题的根源出在 libid3tag。不过要改这个恐怕比较难

gst-plugin mad 的 id3v2 补丁
页: [1]
查看完整版本: gstreamer 读取 mp3 标记时中文乱码的研究结果