[ruby-dev:14967] Re: alias var and trace_var
From:
nobu.nakada@...
Date:
2001-10-19 13:57:13 UTC
List:
ruby-dev #14967
なかだです。
At Fri, 19 Oct 2001 16:51:07 +0900,
K.Kosako <kosako@sofnec.co.jp> wrote:
> > 半分くらいそう意図してたんですが(半分は何も考えてなかった)、
> > 共通にトレースしたほうがいいでしょうか。
>
> 個人的にはトレースに漏れがあり得るということに
> 違和感があります。
一応やってみました。global_entryを分割してますが、おそらくこ
れが一番確実だと思います。1.48のようにgetter/setterをいじくる方
向では、これ以上は無理があるでしょう。
最新の1.48からではなく、その前の1.47からの差分です。
Index: variable.c
===================================================================
RCS file: /cvs/ruby/src/ruby/variable.c,v
retrieving revision 1.47
diff -u -2 -p -r1.47 variable.c
--- variable.c 2001/10/03 07:19:11 1.47
+++ variable.c 2001/10/19 13:54:11
@@ -292,6 +292,5 @@ struct trace_var {
};
-struct global_entry {
- ID id;
+struct global_variable {
void *data;
VALUE (*getter)();
@@ -302,4 +301,9 @@ struct global_entry {
};
+struct global_entry {
+ struct global_variable *var;
+ ID id;
+};
+
static VALUE undef_getter();
static void undef_setter();
@@ -321,14 +325,17 @@ rb_global_entry(id)
if (!st_lookup(rb_global_tbl, id, &entry)) {
+ struct global_variable *var;
entry = ALLOC(struct global_entry);
st_add_direct(rb_global_tbl, id, entry);
+ var = ALLOC(struct global_variable);
entry->id = id;
- entry->data = 0;
- entry->getter = undef_getter;
- entry->setter = undef_setter;
- entry->marker = undef_marker;
+ entry->var = var;
+ var->data = 0;
+ var->getter = undef_getter;
+ var->setter = undef_setter;
+ var->marker = undef_marker;
- entry->block_trace = 0;
- entry->trace = 0;
+ var->block_trace = 0;
+ var->trace = 0;
}
return entry;
@@ -346,15 +353,15 @@ undef_getter(id)
static void
-undef_setter(val, id, data, entry)
+undef_setter(val, id, data, var)
VALUE val;
ID id;
void *data;
- struct global_entry *entry;
+ struct global_variable *var;
{
- entry->getter = val_getter;
- entry->setter = val_setter;
- entry->marker = val_marker;
+ var->getter = val_getter;
+ var->setter = val_setter;
+ var->marker = val_marker;
- entry->data = (void*)val;
+ var->data = (void*)val;
}
@@ -373,11 +380,11 @@ val_getter(id, val)
static void
-val_setter(val, id, data, entry)
+val_setter(val, id, data, var)
VALUE val;
ID id;
void *data;
- struct global_entry *entry;
+ struct global_variable *var;
{
- entry->data = (void*)val;
+ var->data = (void*)val;
}
@@ -429,7 +436,8 @@ mark_global_entry(key, entry)
{
struct trace_var *trace;
+ struct global_variable *var = entry->var;
- (*entry->marker)(entry->data);
- trace = entry->trace;
+ (*var->marker)(var->data);
+ trace = var->trace;
while (trace) {
if (trace->data) rb_gc_mark_maybe(trace->data);
@@ -468,12 +476,12 @@ rb_define_hooked_variable(name, var, get
void (*setter)();
{
- struct global_entry *entry;
+ struct global_variable *gvar;
ID id = global_id(name);
- entry = rb_global_entry(id);
- entry->data = (void*)var;
- entry->getter = getter?getter:var_getter;
- entry->setter = setter?setter:var_setter;
- entry->marker = var_marker;
+ gvar = rb_global_entry(id)->var;
+ gvar->data = (void*)var;
+ gvar->getter = getter?getter:var_getter;
+ gvar->setter = setter?setter:var_setter;
+ gvar->marker = var_marker;
}
@@ -533,9 +541,9 @@ rb_f_trace_var(argc, argv)
}
trace = ALLOC(struct trace_var);
- trace->next = entry->trace;
+ trace->next = entry->var->trace;
trace->func = rb_trace_eval;
trace->data = cmd;
trace->removed = 0;
- entry->trace = trace;
+ entry->var->trace = trace;
return Qnil;
@@ -543,8 +551,8 @@ rb_f_trace_var(argc, argv)
static void
-remove_trace(entry)
- struct global_entry *entry;
+remove_trace(var)
+ struct global_variable *var;
{
- struct trace_var *trace = entry->trace;
+ struct trace_var *trace = var->trace;
struct trace_var t;
struct trace_var *next;
@@ -557,8 +565,10 @@ remove_trace(entry)
trace->next = next->next;
free(next);
+ }
+ else {
+ trace = next;
}
- trace = next;
}
- entry->trace = t.next;
+ var->trace = t.next;
}
@@ -579,5 +589,5 @@ rb_f_untrace_var(argc, argv)
}
- trace = entry->trace;
+ trace = entry->var->trace;
if (NIL_P(cmd)) {
VALUE ary = rb_ary_new();
@@ -589,7 +599,6 @@ rb_f_untrace_var(argc, argv)
trace = next;
}
- entry->trace = 0;
- if (!entry->block_trace) remove_trace(entry);
+ if (!entry->var->block_trace) remove_trace(entry->var);
return ary;
}
@@ -598,5 +607,5 @@ rb_f_untrace_var(argc, argv)
if (trace->data == cmd) {
trace->removed = 1;
- if (!entry->block_trace) remove_trace(entry);
+ if (!entry->var->block_trace) remove_trace(entry->var);
return rb_ary_new3(1, cmd);
}
@@ -606,9 +615,11 @@ rb_f_untrace_var(argc, argv)
return Qnil;
}
+
VALUE
rb_gvar_get(entry)
struct global_entry *entry;
{
- return (*entry->getter)(entry->id, entry->data, entry);
+ struct global_variable *var = entry->var;
+ return (*var->getter)(entry->id, var->data, var);
}
@@ -633,8 +644,8 @@ trace_ev(data)
static VALUE
trace_en(entry)
- struct global_entry *entry;
+ struct global_variable *var;
{
- entry->block_trace = 0;
- remove_trace(entry);
+ var->block_trace = 0;
+ remove_trace(var);
return Qnil; /* not reached */
}
@@ -646,14 +657,15 @@ rb_gvar_set(entry, val)
{
struct trace_data trace;
+ struct global_variable *var = entry->var;
if (rb_safe_level() >= 4)
rb_raise(rb_eSecurityError, "Insecure: can't change global variable value");
- (*entry->setter)(val, entry->id, entry->data, entry);
+ (*var->setter)(val, entry->id, var->data, var);
- if (entry->trace && !entry->block_trace) {
- entry->block_trace = 1;
- trace.trace = entry->trace;
+ if (var->trace && !var->block_trace) {
+ var->block_trace = 1;
+ trace.trace = var->trace;
trace.val = val;
- rb_ensure(trace_ev, (VALUE)&trace, trace_en, (VALUE)entry);
+ rb_ensure(trace_ev, (VALUE)&trace, trace_en, (VALUE)var);
}
return val;
@@ -685,5 +697,5 @@ rb_gvar_defined(entry)
struct global_entry *entry;
{
- if (entry->getter == undef_getter) return Qfalse;
+ if (entry->var->getter == undef_getter) return Qfalse;
return Qtrue;
}
@@ -727,9 +739,5 @@ rb_alias_variable(name1, name2)
entry1 = rb_global_entry(name1);
entry2 = rb_global_entry(name2);
-
- entry1->data = entry2->data;
- entry1->getter = entry2->getter;
- entry1->setter = entry2->setter;
- entry1->marker = entry2->marker;
+ entry1->var = entry2->var;
}
--
--- 僕の前にBugはない。
--- 僕の後ろにBugはできる。
中田 伸悦