$Id: fish-wcsncpy.md 810 2006-05-09 02:02:28Z sakurai $
fish、ホ・ミ・ー、ス、タオ、キ、ソサ、ホオュマソ、ヌ、ケ。」 ・ミ・ース、タオ、ホ・ア。シ・ケ・ケ・ソ・ヌ・」、ネ、キ、ニス、ュ、゙、キ、ソ。」
fish、ヌ・ソ・ヨハ莇ー、ケヤ、ヲ、ネ。「SIGSEGV、ヌヘ、チ、サ、ャ、「、。」
NetBSD-3.0、ホlibc、ヒニ、テ、ニ、、、wcsncpy、マbuffer overflow、ホ・ミ・ー、ャ、「、。」 current、ヌ、マ、ウ、ホ・ミ・ー、マトセ、テ、ニ、、、、隍ヲ、タ。」
SIGSEGV、ヌヘ、チ、、ホ、マ。「ツ酘、ス、ホ・「・ラ・熙ャノヤタオ、ハ・皈筵チ犲(シ遉ヒ・フ・・ン・、・・ソ・「・ッ・サ・ケ)、ケヤ、テ、ニ、、、サ、ヌ、「、。」 ケ・アソ、ヒ、簣、チ、、ホ、コニクス、ケ、サ、ャ、ヌ、ュ、、ホ、ヌ。「gdbセ螟ヌfish、ヘ、ネ、キ、ニ、荀サ、ヌ。「・ス。シ・ケ、ホ、ノ、ホケヤ、ヌヘ、チ、ニ、、、、ォ、テホ、サ、ャ、ヌ、ュ、。」
、゙、コ。「Makefile、ホCFLAGS、ヒ-g、サリト熙キ。「・ヌ・ミ・テ・ー・キ・・ワ・ノユ、ュ、ヌfish、・ウ・・ム・、・、ケ、。」
ハムケケチー
CFLAGS:= -I/usr/pkg/include/ -std=c99 -fno-optimize-sibling-calls -Wall
ハムケケク
CFLAGS:= -I/usr/pkg/include/ -std=c99 -fno-optimize-sibling-calls -Wall -g
fish、gdbセ螟ヌシツケヤ、キ。「fish、ヘ、ネ、キ、ニ、荀。」
$ gdb /usr/local/bin/fish
(gdb) run
fish> (、ウ、ウ、ヌ。「fish、ヘ、ネ、ケ)
Program received signal SIGSEGV, Segmentation fault.
0x0806ddee in hash_search (h=0x80ada20, key=0x80b4780) at util.c:225
225 if( (h->arr[pos].key == 0 ) ||
(gdb)
l・ウ・゙・・ノ、ヌ。「、゙、、熙ホケヤ、ノスシィ、ケ、サ、筅ヌ、ュ、。」
220
221 hv = h->hash_func( key );
222 pos = abs(hv) % h->size;
223 while(1)
224 {
225 if( (h->arr[pos].key == 0 ) ||
226 ( h->compare_func( h->arr[pos].key, key ) ) )
227 {
228 return pos;
229 }
(gdb)
SIGSEGV、マツ酘・フ・・ン・、・・ソ・「・ッ・サ・ケ、ヌネッタク、ケ、、ホ、ヌ。「h、ォh->arr、ャ0、ヒ、ハ、テ、ニ、、、、ホ、タ、、ヲ。」
(gdb) print h
$3 = (hash_table_t *) 0x80ada20
(gdb) print h->arr
$4 = (hash_struct_t *) 0x0
(gdb)
・モ・・エ。」h->arr、ャ0、ヒ、ハ、テ、ニ、、、。」 h->arr、ャ0、ネ、、、ヲサ、マ。「h->arr、マヌロホ、ヌ、マ、ハ、ッ。「・ン・、・・ソ、ネ、、、ヲサ、タ。」 ・ィ・ヌ・」・ソ、ヌhash_struct_t、ホトオチ、クォ、、ネ。「
typedef struct hash_table
{
/** The array containing the data */
hash_struct_t *arr;
、ネ、「、遙「、荀テ、ム、鸞rr、マ・ン・、・・ソ、ヌ、「、テ、ソ。」 、ウ、、ャ0、ヒ、ハ、テ、ニ、、、、ネ、、、ヲサ、マ。「malloc、キヒコ、、ニ、、、、ォ。「、ノ、ウ、ォ、ヌ0、・サ・テ・ネ、キ、ニ、キ、゙、テ、ニ、、、、ホ、タ、、ヲ。」
h->arr、ヒテヘ、・サ・テ・ネ、キ、ニ、、、イユス熙テオ、ケ。」
$ grep 'h->arr' *
util.c: h->arr = malloc( sizeof(hash_struct_t)*sz );
util.c: h->arr[i].key = 0;
util.c: h->arr = 0;
util.c: free( h->arr );
...
util.c: func( h->arr[i].key, h->arr[i].data, aux );
$
、「、熙ャ、ソ、、サ、ヒ。「h->arr、ヒ・「・ッ・サ・ケ、キ、ニ、、、、ホ、マ。「util.c、タ、ア、ホ、隍ヲ、タ。」 util.c、クォ、、ネ。「h->arr、ヒテヘ、・サ・テ・ネ、キ、ニ、、、、ホ、マ。「hash_init2()、ネhash_init(), hash_realloc()、タ、ア、ネ、、、ヲサ、ャ、、ォ、テ、ソ。」 、ヲ。シ、爍」ニテ、ヒ、ェ、ォ、キ、、ス熙マクォ、ト、ォ、鬢ハ、、。」
bt(backtrace)・ウ・゙・・ノ、ヌ。「エリソ、ホクニ、モスミ、キヘホ、ノスシィ、キ、ニ、゚、。」
(gdb) bt
#0 0x0806ddee in hash_search (h=0x80ada20, key=0x80b4780) at util.c:225
#1 0x0806e083 in hash_get (h=0x80ada20, key=0x80b4780) at util.c:311
#2 0x080502b2 in complete_get_desc_suffix (suff_orig=0x80b46d4) at complete.c:857
#3 0x08050778 in complete_get_desc (filename=0x80b4680) at complete.c:993
#4 0x08064d46 in get_desc (fn=0x80b4680, sb=0xbfbfdc20, is_cmd=0) at wildcard.c:330
#5 0x0806534c in wildcard_expand (wc=0x80b45b8, base_dir=0x80bb000, flags=9, out=0xbfbfdeb0)
at wildcard.c:558
#6 0x08065647 in wildcard_expand (wc=0x80b4598, base_dir=0x80b6000, flags=9, out=0xbfbfdeb0)
at wildcard.c:703
#7 0x08065647 in wildcard_expand (wc=0x80b4584, base_dir=0x807e658, flags=9, out=0xbfbfdeb0)
at wildcard.c:703
#8 0x08057d72 in expand_string (context=0x0, str=0x80ad880, end_out=0xbfbfe430, flags=9)
at expand.c:1614
#9 0x080518e5 in complete_param_expand (str=0x80ad820, comp_out=0xbfbfe430, do_file=1)
at complete.c:1732
#10 0x08052006 in complete (cmd=0x80b2ac0, comp=0xbfbfe430) at complete.c:2049
#11 0x08062ef5 in reader_readline () at reader.c:2477
#12 0x0806274d in read_i () at reader.c:2259
#13 0x08063a35 in reader_read (fd=0) at reader.c:2965
#14 0x08075bc1 in main (argc=1, argv=0xbfbfe59c) at main.c:283
#15 0x0804a1d6 in ___start ()
(gdb)
backtrace、ネcomplete.c、ニノ、爨ネ。「ーハイシ、ホサ、ャ、、ォ、テ、ソ。」
、ウ、ホク螂ス。シ・ケ、、隍ッニノ、、ヌ、゚、ソ、ホ、タ、ャ。「、ェ、ォ、キ、、ス熙マクォ、「、ソ、鬢ハ、ォ、テ、ソ。」 、チ、遉テ、ネ、ェシセ螟イ。」
、ウ、ヲ、ハ、テ、ソ、鮗ヌク螟ホシテハ。」watch point、サネ、ェ、ヲ。」 watch point、サネ、ヲ、ネ。「ハムソ、ホテヘ、ャハム、、・ソ・、・゚・・ー、ヌ・ヨ・。シ・ッ、、ォ、ア、サ、ャ、ヌ、ュ、。」 、ソ、タ、キ。「watch point、サネ、ヲ、ネ・ラ・・ー・鬣爨ホシツケヤ、マサ爨フ、ロ、ノテル、ッ、ハ、。」
suffix_hash->arr、ャ、ノ、ウ、ォ、ヌ0、ヒ、オ、、ニ、、、、ホ、ヌ。「、ス、、クォ、ト、ア、。」
fish> (ctrl-C、ヌgdb、リ)
Program received signal SIGINT, Interrupt.
0xbdb04f2f in select () from /usr/lib/libc.so.12
(gdb) watch suffix_hash->arr (watch point、ホ・サ・テ・ネ)
Watchpoint 1: suffix_hash->arr
(gdb) c (fish、ホシツケヤ、コニウォ)
Continuing.
(fish、ヘ、ネ、ケ)
Watchpoint 1: suffix_hash->arr
Old value = (hash_struct_t *) 0x80bde00
New value = (hash_struct_t *) 0x0
0xbdb07df6 in wcsncpy () from /usr/lib/libc.so.12
(gdb)
libc、ホwcsncpy()、ホテ讀ヌsuffix_hash->arr、ャ0、ヒ、ハ、テ、ニ、サ、ャ、、ォ、テ、ソ。」 、ェ、ス、鬢ッ。「wcsncpy、ヒナマ、ケーソ、ャノヤタオ、ハハェ、ヒ、ハ、テ、ニ、、、、ホ、タ、、ヲ。」 bt、ヌ。「wcsncpy、ャ、ノ、ウ、ォ、鮑ニ、ミ、、ニ、、、、ホ、ォ、トエ、ル、。」
(gdb) bt
#0 0xbdb07df6 in wcsncpy () from /usr/lib/libc.so.12
#1 0x080726a5 in wcsndup (in=0x80b4598, c=7) at fallback.c:821
#2 0x0806544b in wildcard_expand (wc=0x80b4598, base_dir=0x80b6000, flags=9, out=0xbfbfdeb0)
at wildcard.c:628
...
wcsncpy()、マ。「fallback.c、ホwcsndup()、ォ、鮑ニ、ミ、、ニ、、、。」 wcsndup()、ホ・ス。シ・ケ、クォ、ニ、゚、。」
(gdb) l fallback.c:819
814 wchar_t *wcsndup( const wchar_t *in, int c )
815 {
816 wchar_t *res = malloc( sizeof(wchar_t)*(c+1) );
817 if( res == 0 )
818 {
819 return 0;
820 }
821 wcsncpy( res, in, c+1 );
822 res[c] = L'\0';
823 return res;
(gdb)
、「、?malloc、キ、ニ、ス、ウ、ヒハクサホ、・ウ・ヤ。シ、キ、ニ、、、、タ、ア、ハ、ホ、ヌ。「ークォ、キ、ニ、ェ、ォ、キ、、ス熙マイソ、篋ォ、ト、ォ、鬢ハ、、。」 wcsncpy、マwide charネヌ、ホstrncpy、ハ、ホ、ヌ。「ツ霆ーーソ(c+1)ーハセ螟ホホホー隍ヒ、マス、ュケ、゚、キ、ハ、、、マ、コ。」
、ヲ。シ、爍」
、ネ、熙「、ィ、コ。「ハムソ、ホテヘ、クォ、ニ、゚、隍ヲ。」
(gdb) print in
$1 = (const wchar_t *) 0x80b4598
(gdb) print c
$2 = 7
(gdb) print res
$3 = (wchar_t *) 0x80ada00
(gdb) print sizeof(wchar_t)
$4 = 4
malloc、キ、ソホホー隍ヒス、ュケ、爨ネsuffix_hash->arr、ャ0、ヒ、ハ、テ、ニ、キ、゙、ヲ、テ、ニサ、マ。「 res、ネsuffix_hash、ホ・「・ノ・・ケ、マカ皃、、ホ、タ、、ヲ、ォ。」 suffix_hash、ホ・「・ノ・・ケ、クォ、ニ、゚、。」
(gdb) print suffix_hash
$5 = (hash_table_t *) 0x80ada20
(gdb)
res、マsuffix_hash、隍32・ミ・、・ネチー、ヒーフテヨ、キ、ニ、、、。」 res、ホ・「・ノ・・ケ、char、ヌ・タ・・ラ、キ、ニ、゚、、ネ。「
(gdb) x/40c res
0x80ada00: 115 's' 0 '\0' 0 '\0' 0 '\0' 97 'a' 0 '\0' 0 '\0' 0 '\0'
0x80ada08: 107 'k' 0 '\0' 0 '\0' 0 '\0' 117 'u' 0 '\0' 0 '\0' 0 '\0'
0x80ada10: 114 'r' 0 '\0' 0 '\0' 0 '\0' 97 'a' 0 '\0' 0 '\0' 0 '\0'
0x80ada18: 105 'i' 0 '\0' 0 '\0' 0 '\0' 47 '/' 0 '\0' 0 '\0' 0 '\0'
0x80ada20: 0 '\0' 0 '\0' 0 '\0' 0 '\0' 2 '\002' 0 '\0' 0 '\0' 0 '\0'
(gdb)
クォサ、ヒsuffix_hash、ホタ霹ャ、ャ0、ヒ、ハ、テ、ニ、、、。」
malloc、ヌ4*(7+1)=32・ミ・、・ネウホハン、キ。「wcsncpy、ヌ32・ミ・、・ネ、゙、ヌ、キ、ォス、ュケ、゚、キ、ニ、、、ハ、、、マ、コ、タ、隍ハ、「。」 、ス、ホク螟、ホsuffix_hash、イ、ケ、、ア、マ、ハ、、、ホ、タ、ア、ノ。」
、メ、遉テ、ネ、キ、ニ。「、メ、遉テ、ネ、ケ、、ネ。ト
wcsncpy、ホ・ミ・ー?
/usr/src/lib/libc/string/wcsncpy.c、クォ、ニ、゚、。」
wchar_t *
wcsncpy(s1, s2, n)
wchar_t *s1;
const wchar_t *s2;
size_t n;
{
wchar_t *p;
const wchar_t *q;
_DIAGASSERT(s1 != NULL);
_DIAGASSERT(s2 != NULL);
*s1 = '\0';
p = s1;
q = s2;
while (n && *q) {
*p++ = *q++;
n--;
}
*p = '\0';
return s1;
}
、「、??
*p = '\0'
、ャノャ、コシツケヤ、オ、、ニ、、、。」、筅キn、ャ1、ハ、鬘「n+1、ホホホー隍ホス、ュケ、゚、ケ、サ、ヒ、ハ、。」 、ウ、、テ、ニ。「wcsncpy、ホ・ミ・ー、タ、隍ハ、「。」、ュ、テ、ネ。」
NetBSD-current、ヌ、籠セ、テ、ニ、ハ、、、隍ヲ、ハ、鬘「・ミ・ー・・ン。シ・ネ、スミ、キ、ニ、ェ、ッ、ォ。」 CVS、ホwcsncpy.c 、、゚、、ネ。「コヌソキ・ス。シ・ケ(rev1.3)、ヌ、マトセ、テ、ニ、、、、゚、ソ、、。」 NetBSD-3.0、ヒ、マbackport、オ、、ハ、、、ハ、、、ネ、、、ヲサ、ォ。」