珍しく効果がでたのか・・・な?

Ruby 1.9.0のgc.cにあるis_pointer_to_heap関数でRuby Enterprisesみたいに前回検索したヒープのスロットをキャッシュするようにしてみました。なんかRuby 1.9.0でも効果があるみたいです。

結果

benchmark results:
    ruby 1.9.0 (2008-07-14 revision 15675)    改良版
app_answer	             0.249            0.620
app_erb	                     5.148            4.918                  
app_factorial	             1.215            1.172
app_fib	                     1.964            1.925
app_mandelbrot	             0.910            0.850
app_pentomino	            85.214           81.864
app_raise	             3.356            2.470
app_strconcat	             1.384            1.280
app_tak	                     3.578            3.544
app_tarai                    2.843            3.031
app_uri	                     4.719            4.659
io_file_create	            22.258           21.821

is_pointer_to_heap関数しかいじっていないので、is_pointer_to_heap関数全体を載せておきます。あと、キャッシュ用の変数を1つ追加しています。

static struct heaps_slot *heap_cache = NULL; /* ここが追加 */

static inline int
is_pointer_to_heap(rb_objspace_t *objspace, void *ptr)
{
    register RVALUE *p = RANY(ptr);
    register struct heaps_slot *heap;
    register size_t hi, lo, mid;

    if (p < lomem || p > himem) return Qfalse;
    if ((VALUE)p % sizeof(RVALUE) != 0) return Qfalse;

    /* Lookup prev slot (ここが追加されています)*/
    if (heap_cache != NULL) {
      heap = heap_cache;
      if (heap->slot <= p && p < heap->slot + heap->limit) {
	return Qtrue;
      }
    }

    /* check if p looks like a pointer using bsearch*/
    lo = 0;
    hi = heaps_used;
    while (lo < hi) {
	mid = (lo + hi) / 2;
	heap = &heaps[mid];
	if (heap->slot <= p) {
	    if (p < heap->slot + heap->limit){
	        heap_cache = heap;  /* ここが追加 */
		return Qtrue;
	    }
	    lo = mid + 1;
	}
	else {
	    hi = mid;
	}
    }
    return Qfalse;
}