From: "とみたまさひろ" Date: 2009-09-30T23:54:20+09:00 Subject: [ruby-dev:39410] #2009 File.open memory leak とみたです。 # 英語はダメなので ruby-dev で… http://redmine.ruby-lang.org/issues/show/2009 の File.open memory leak ですが、原因は r21435 の gc.c の次の変更だと思います。 @@ -1274,8 +1291,11 @@ break; case T_FILE: if (RANY(obj)->as.file.fptr) { - rb_io_fptr_finalize(RANY(obj)->as.file.fptr); - RUBY_CRITICAL(free(RANY(obj)->as.file.fptr)); + struct rb_io_t *fptr = RANY(obj)->as.file.fptr; + make_deferred(RANY(obj)); + RDATA(obj)->dfree = (void (*)(void*))rb_io_fptr_finalize; + RDATA(obj)->data = fptr; + return 1; } break; case T_ICLASS: fptr の free() がなくなったためにメモリリークしてます。 次のようなすれば直りました。 Index: gc.c =================================================================== --- gc.c (リビジョン 25170) +++ gc.c (作業コピー) @@ -1243,6 +1243,14 @@ p->as.basic.flags = (p->as.basic.flags & ~T_MASK) | T_DEFERRED; } +static void +fptr_finalize_and_free(fptr) + void *fptr; +{ + rb_io_fptr_finalize(fptr); + free(fptr); +} + static int obj_free(obj) VALUE obj; @@ -1318,7 +1326,7 @@ if (RANY(obj)->as.file.fptr) { struct rb_io_t *fptr = RANY(obj)->as.file.fptr; make_deferred(RANY(obj)); - RDATA(obj)->dfree = (void (*)(void*))rb_io_fptr_finalize; + RDATA(obj)->dfree = (void (*)(void*))fptr_finalize_and_free; RDATA(obj)->data = fptr; return 1; } -- とみたまさひろ 3469 42CC 4D32 F53C AD98 65A5 8C37 FF09 69C1 6040