http://news.gmane.org/group/gmane.emacs.w3m/thread=5249/force_load=t
から始まるスレッドにつなげます。最初の白井さんの記事を要約すると、
テキストを何かの coding system でエンコードしたものを unibyte
なバッファに挿入してからデコードするときに、2005年3月の時点の
Emacs 22.0.50 では、次のような順序で行なうとうまくいかなかった
ようです。
;; [1]
(decode-coding-region (point-min) (point-max) 'CODING-SYSTEM)
(set-buffer-multibyte t)
そこで、これに該当するコードを使っている emacs-w3m では、以下
のように順序を逆にしました。
;; [2]
(set-buffer-multibyte t)
(decode-coding-region (point-min) (point-max) 'CODING-SYSTEM)
ところが、現在の Emacs 22.0.50 では [1] のやり方でも問題無いよう
に見えます。加えて、最新の Emacs 23.0.0 では、[1] のやり方を使わ
ないと正しくデコードできません。例えば [2] の場合、Emacs 23.0.0
ではこんなふうになります:
(let ((str (encode-coding-string
(string (make-char 'chinese-gb2312 86 80)
(make-char 'chinese-gb2312 57 122))
'gb2312))
(default-enable-multibyte-characters nil)
str1 str2)
(with-temp-buffer
(insert str)
(setq str1 (buffer-string))
(set-buffer-multibyte t)
(setq str2 (buffer-string))
(decode-coding-region (point-min) (point-max) 'gb2312)
(list str1 str2 (buffer-string))))
=> ("\326\320\271\372"
"\326■\372"
#("\326■\301\272" 0 2 (charset chinese-gb2312)))
今後は [1] のやり方に統一しようと思うのですが、ご意見をいただけ
ますか?
それから、これに関連して、[2] のやり方では扱うデータによっては
decode-coding-region の時点で Emacs 23.0.0 がクラッシュするとい
う報告があります[3]。それを再現するコードを作ってみました。やり
方はともかく、こういう条件で Emacs がクラッシュしてはいけないの
ですよね。
試す場合は、添付した test.html を /tmp などに置いて下さい。
(let ((buffer (get-buffer-create "*testing*")))
(with-current-buffer buffer
(erase-buffer)
(set-buffer-multibyte nil)
(let ((coding-system-for-read 'binary))
(insert-file-contents "/tmp/test.html"))
(set-buffer-multibyte t)
(decode-coding-region (point-min) (point-max) 'gb2312))
(pop-to-buffer buffer))
[3]
http://news.gmane.org/group/gmane.emacs.w3m/thread=5886/force_load=tAttachment:
test.html.gz
Description: GNU Zip compressed data