[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[freewnn:00924] Re: dtoa SEGV



添付ではなく、インラインにしたので長いです。


まあ、私の環境でのみ発生している問題という可能性はありますが……

かなり、ヘビー(トリッキー?)な使い方になっているという自信はありますので、
一般の方が遭遇しないバグに出会っているという可能性も有り。


亀井> >> 辞書のフォーマットが、分からないんですよねぇ。
亀井> >> 特にマッピングというかファイル内オフセットと内容。
青野> 
青野>> Wnn/manual/6.jutil/dictionary とかは参考になりますか?
青野>> 

亀井> 参考にしました。
亀井> 添付ファイルに、マップ結果を付けます。


私の使用環境は、[freewnn:00911]の通り。


正常辞書 zpOK と、
zpOK にEmacsからの対話登録(egg-toroku-region)で数単語登録した後、
wnn-close をしてみたら壊れてしまっていた辞書、 zpNG の2つについて、
目視で内容を比較確認してみました。

zpOK, zpNGそのものは添付しませんので、ご参考程度に。


○ファイルの中の値
[0080]	Wnn/include/jdata.h:struct JT
					zpNGの場合	zpOKの場合
    [0080]	syurui			3		←
    [0084]	maxcomment		5		←
    [0088]	maxhinsi_list		1		←
    [008C]	maxserial		194	0x00C2	192	0x00C0
    [0090]	maxkanji		3392	0x0D40	3366	0x0D26
    [0094]	maxtable		0		←
    [0098]	maxhontai		0		←
    [009C]	gosuu			194	0x00C2	192	0x00C0
    [00A0]	パスワード
    [00B0]	total			0		←
    [00B4]	maxri1[D_YOMI]		191	0x00BF	189	0x00BD
    [00B8]	maxri1[D_KANJI]		193	0x00C1	191	0x00BF
    [00BC]	maxri2			194	0x00C2	192	0x00C0
    [00C0]	NUL×56
[00F8]	不定サイズ領域
    [00F8]	[00F8]
    	コメント    w_char [maxcomment]	    Wnn/jutil/ujisf.c:file_comment[]
    [0102]	[0102]
	品詞リスト  w_char [maxhinsi_list]  Wnn/jutil/ujisf.c:hinsi_list[]
    [0104]	[0104]
	頻度	    char [maxserial]	    Wnn/jutil/ujisf.c:jeary[]->hindo
    [01C6]	[01C4]
	品詞	    w_char [maxserial]	    Wnn/jutil/ujisf.c:jeary[]->hinsi
						    hinsi[]
    [034A]	[0344]
	漢字	    char [maxkanji]		    kanji[]
	    各エントリは、 
		char	    エントリのバイト数
		char	    state
		    state bit2 offの時
			w_char [m]  読み文字列(state bit0 onの時)
			w_char [n]  漢字文字列
			w_char [o]  コメント文字列(state bit1 onの時)
		    state bit2 onの時
			int offset  本エントリからのバイト・オフセット
			    そのオフセット先が実際のエントリになる
    [108A]	[106A]
	(不使用)    struct uind1 [0]		    table[]
    [108A]	[106A]
	読みの表    struct rind1 [maxri1[D_YOMI]]   ri1[D_YOMI]
	    各エントリは、
		int	rind1のindex
		int	rind2のindex
    [1682]	[1652]
	漢字の表    struct rind1 [maxri1[D_KANJI]]  ri1[D_KANJI]
	    各エントリは、
		int	rind1のindex
		int	rind2のindex
    [1C8A]	[1C4A]
	(不使用)    char [maxhontai]		    hontai
    [1C8A]	[1C4A]
	辞書エントリの表    struct rind2[maxserial] ri2
	    各エントリは、
		int	rind2のindex
		int	rind2のindex
		int	w_char kanjiのindex


○zpNG がおかしいところ
    [01C3-01C5] の3つの頻度が全て、0x80になっていて、これはおかしい?
	正常なzpOKでは、そのようなことはない。

zpNG[01C3-01C5]
    000001b0: 0000 0002 0000 0001 0300 0300 0200 0500  ................
    000001c0: 0300 0080 8080 0031 fdf1 000a 000a 000a  .......1........
    000001d0: 000a 000a 000a 000a 000a 000a 002b 0031  .............+.1

zpOK[...-01C3]
    000001b0: 0000 0000 0002 0000 0001 0300 0300 0200  ................
    000001c0: 0500 0300 0031 fdf1 000a 000a 000a 000a  .....1..........
    000001d0: 000a 000a 000a 000a 000a 002b 0031 000a  ...........+.1..


    [14A2-1C89]
	読みの表、漢字の表等、
	    正常ならば
		(-1 or m, n) m < maxri1[D_YOMI], n < maxri2
		(-1 or o, p) o < maxri1[D_KANJI], p < maxri2
	    となるべき?が、
	    zpNGでは、m, n, o, p共に異常値が散見される。

zpNG[14A2-1C89]
    00001480: 007d ffff ffff 0000 007e ffff ffff 0000  .}.......~......
    00001490: 007f ffff ffff 0000 0080 ffff ffff 0000  ................
    000014a0: 001b 2c41 7fff ffff 1b28 4200 0000 1b2c  ..,A.....(B....,
    000014b0: 427f ffff ff1b 2842 0000 001b 2c43 7fff  B.....(B....,C..
    000014c0: ffff 1b28 4200 0000 c000 0000 8500 0000  ...(B...........
    000014d0: 1b2c 447f ffff ff1b 2842 0000 001b 2c54  .,D.....(B....,T
    000014e0: 7fff ffff 1b28 4200 0000 1b2c 467f ffff  .....(B....,F...
    000014f0: ff1b 2842 0000 001b 2c47 7fff ffff 1b28  ..(B....,G.....(

zpOK[12E2-...]
    000012e0: 004e ffff ffff 0000 004f ffff ffff 0000  .N.......O......
    000012f0: 0050 ffff ffff 0000 0051 ffff ffff 0000  .P.......Q......
    00001300: 0052 0000 0052 0000 0053 ffff ffff 0000  .R...R...S......
    00001310: 0054 ffff ffff 0000 0055 ffff ffff 0000  .T.......U......


    [1C8A-XXXX]
	辞書エントリの表、
	    正常ならば
		(-1 or m, -1 or n, o) m < maxri2, n < maxri2, o < maxkanji
	    となるべき?が、
	    zpNGでは、特に m, n が異常値となっている。

zpNG[1C8A-...]
    00001c80: 4aff ffff ff00 0000 1b2c 5f7f ffff ff1b  J........,_.....
    00001c90: 2842 0000 004d ffff ffff 0000 004b ffff  (B...M.......K..
    00001ca0: ffff 0000 003e ffff ffff 0000 009e ffff  .....>..........
    00001cb0: ffff 0000 004f ffff ffff 0000 0065 ffff  .....O.......e..
    00001cc0: ffff 0000 0037 ffff ffff 0000 001b 2428  .....7........$(
    00001cd0: 307f 7fff ff1b 2842 0000 00a1 ffff ffff  0.....(B........
    00001ce0: 0000 000c ffff ffff 0000 0054 ffff ffff  ...........T....

zpOK[1C4A-...]
    00001c40: 0086 ffff ffff 0000 006e ffff ffff ffff  .........n......
    00001c50: ffff 0000 0000 ffff ffff ffff ffff 0000  ................
    00001c60: 0016 ffff ffff ffff ffff 0000 0026 ffff  .............&..
    00001c70: ffff ffff ffff 0000 0036 ffff ffff ffff  .........6......



○zpNGにおいてSEGVとなるのは、
	1.  辞書エントリ表 ri2[] の最初の要素を参照。
	2.  kanjipter を取り出す。
		通常は 0 だが、zpNGでは壊れていて、いきなり 0x4D。
	3.  kanji[0x4D] からのエントリを取り出す。
		0x4D < maxkanji = 0x0D40 なので、kanji[] 境界内。
		但し取出し位置は不正なので、有らぬエントリ取り出しである。
	4.  エントリのstate コードを見ると bit2 on なので、FORWARDED 扱い。
		    但し本来は state コードではなく、漢字コードの一部。
		kanji[0x4E-4F] の 4バイトを取り出す。
		この場合、 0x1401 が得られる。
		この値を、
		    当エントリ(&kanji[0x4D])からのバイト・オフセットとして、
		    FORWARDED 先のエントリの取り出しを試みる。
		    然し、
			0x4D×2 + 0x1401 > maxkanji = 0x0D40
		    なので、 kanji[] の境界を越えてしまい、 SEGV。

    zpNGは、maxserialを見ると、zpOKに2単語追加しただけに見えるが、
	kanji[] 相当の部分を見る限りでは、
	    後ろの方に更に4単語程度の追加の形跡がある。
	    ※ 全て対話登録分。
	この追加分は、それまでのものと違って、
	    読み(鏡文字列)順にソートされていない。
	    単純に後ろに追加されたように見える。
	……ここで、 maxkanji と、 maxserial 他との不整合が出ているような。

zpNG[104E-1089]
    00001040: a4a6 a4e5 a4b8 0000 edb8 ecfa 0000 1601  ................
    00001050: a5eb a5b5 a5f3 a5b3 0000 a5eb a5b5 a5f3  ................
    00001060: a5b3 0000 0c01 a4a8 a4ab 0000 b4d4 0000  ................
    00001070: 0c01 a4de a4bf 0000 b6f6 0000 0e01 a4ad  ................
    00001080: a4a2 0000 a4ad b6f5 0000 ffff ffff 0000  ................

壊れた辞書については、こんなところです。


jserverの方はどうやって調べたらいいのかな?
確実な再現手順を見つけていないので、いかんとも。

-- 
	   亀井 信義