[#15625] rb_hash_initialize — Takaaki Tateishi <ttate@...>

立石です.

22 messages 2002/01/04
[#15627] Re: rb_hash_initialize — matz@... (Yukihiro Matsumoto) 2002/01/04

まつもと ゆきひろです

[#15628] Re: rb_hash_initialize — Takaaki Tateishi <ttate@...> 2002/01/04

立石です.

[#15685] undefined method `inherited' for false (NameError) — WATANABE Hirofumi <eban@...>

わたなべです。

13 messages 2002/01/15
[#15686] Re: undefined method `inherited' for false (NameError) — nobu.nakada@... 2002/01/15

なかだです。

[#15757] 文字列→整数変換 — nobu.nakada@...

なかだです。

30 messages 2002/01/25

[#15830] [ 提案 ] puts, print 等を IO から分離 — UENO Katsuhiro <unnie@...>

うえのです。

14 messages 2002/01/31

[ruby-dev:15700] method cache

From: Takaaki Tateishi <ttate@...>
Date: 2002-01-17 08:45:24 UTC
List: ruby-dev #15700
立石です.

メソッドキャッシュについてですが,メソッドが定義される等の度に
キャッシュ内を全探索してIDが同じエントリを削除しているようです
が,合っているでしょうか?
その場合,定義したメソッドのIDがキャッシュされている可能性があ
る場合にのみ全探索してエントリを削除するというように変更すると,
多少スピードが上がるようです.
僕がrubyのソース全部を把握できていないので不十分かもしれません
が,最後に付けたパッチを適用して,minirubyを使ってsample/test.rb
を実行したときのtimeの結果は以下のようになりました.

# 測定に使ったのがsample/test.rbなので偏りがあるかもしれませんが…

original miniruby
------------------
real    0m45.227s
user    0m35.910s
sys     0m8.330s

real    0m45.909s
user    0m36.150s
sys     0m8.290s

real    0m43.768s
user    0m35.370s
sys     0m8.070s

modified miniruby
-----------------
real    0m32.367s
user    0m23.640s
sys     0m8.240s

real    0m32.339s
user    0m23.570s
sys     0m8.410s

real    0m32.348s
user    0m23.700s
sys     0m8.250s

変更後のソースとのdiffは以下のものです.
IDがキャッシュされているかどうか調べるために,cache_damageという
配列を用意しているのですが,どの程度のサイズをとれば必要十分かは
全く考えていません.

Index: eval.c
===================================================================
RCS file: /src/ruby/eval.c,v
retrieving revision 1.245
diff -u -r1.245 eval.c
--- eval.c	2002/01/16 09:32:51	1.245
+++ eval.c	2002/01/17 08:19:11
@@ -186,7 +186,10 @@
 };
 
 static struct cache_entry cache[CACHE_SIZE];
+static ID cache_damage[CACHE_SIZE];
 
+#define CACHE_DAMAGE(id) cache_damage[id&CACHE_MASK]
+
 void
 rb_clear_cache()
 {
@@ -195,6 +198,9 @@
     ent = cache; end = ent + CACHE_SIZE;
     while (ent < end) {
 	ent->mid = 0;
+#ifdef CACHE_DAMAGE
+	CACHE_DAMAGE(ent->mid) = 0;
+#endif
 	ent++;
     }
 }
@@ -205,10 +211,17 @@
 {
     struct cache_entry *ent, *end;
 
+#ifdef CACHE_DAMAGE
+    if( !CACHE_DAMAGE(id) ) return ;
+#endif
+
     ent = cache; end = ent + CACHE_SIZE;
     while (ent < end) {
 	if (ent->mid == id) {
 	    ent->mid = 0;
+#ifdef CACHE_DAMAGE
+	    CACHE_DAMAGE(id) = 0;
+#endif
 	}
 	ent++;
     }
@@ -264,7 +277,10 @@
 
     if ((body = search_method(klass, id, &origin)) == 0 || !body->nd_body) {
 	/* store empty info in cache */
-	ent = cache + EXPR1(klass, id);
+        ent = cache + EXPR1(klass, id);
+#ifdef CACHE_DAMAGE
+	CACHE_DAMAGE(id) = 1;
+#endif
 	ent->klass  = klass;
 	ent->origin = klass;
 	ent->mid = ent->mid0 = id;
@@ -276,6 +292,9 @@
 
     /* store in cache */
     ent = cache + EXPR1(klass, id);
+#ifdef CACHE_DAMAGE
+    CACHE_DAMAGE(id) = 1;
+#endif
     ent->klass  = klass;
     ent->noex   = body->nd_noex;
     body = body->nd_body;
@@ -4626,6 +4645,9 @@
     }
     /* is it in the method cache? */
     ent = cache + EXPR1(klass, mid);
+#ifdef CACHE_DAMAGE
+    CACHE_DAMAGE(mid) = 1;
+#endif
     if (ent->mid == mid && ent->klass == klass) {
 	if (!ent->method)
 	    return rb_undefined(recv, mid, argc, argv, scope==2?CSTAT_VCALL:0);

In This Thread

Prev Next