This is the mail archive of the
guile@cygnus.com
mailing list for the Guile project.
Re: Weak observers (was Re: The taming of the before-gc-hook)
- To: Mikael Djurfeldt <mdj@mdj-pc.nada.kth.se>
- Subject: Re: Weak observers (was Re: The taming of the before-gc-hook)
- From: Jost Boekemeier <jostobfe@calvados.zrz.TU-Berlin.DE>
- Date: 28 Jul 1999 18:18:53 +0200
- Cc: Jim Blandy <jimb@red-bean.com>, Greg Harvey <Greg.Harvey@thezone.net>, guile@cygnus.com, djurfeldt@nada.kth.se
- References: <xy790807qgl.fsf_-_@mdj-pc.nada.kth.se>
Mikael Djurfeldt <mdj@mdj-pc.nada.kth.se> writes:
> Ah, you need it for the module system?
> Then it is probably highly time critical code.
Yes, and no, it is not very time critical. An observer is a scheme
function observing an environment. The function is called whenever a
location of a (symbol . value) binding changes (either because it
has been removed or re-exported).
The environment points to a list of observer smobs. Each observer smob
holds the observer (`scheme'), a flag that indicates whether `scheme'
is weak (must be marked or not) and a forward/backward pointer. Whenever one of
the following happens the observer-smob must remove itself from the list:
1. The environment has been garbage collected
2. The observer smob is removed via (environment-unobserve <smob>)
3. The scheme function stored in the observer smob has
been garbage collected.
Case 1: When the environment has been gc'ed the observer-smobs
will no longer be marked and will go away.
Case 2: Obvious :)
Case 3: That's the real problem:
In the environment mark function:
scm_gc_mark (environment->obarray);
/* now mark all observer smobs */
node = environment->root.link.right;
while (SCM_NIMP(node))
{
struct environment_observer *observer = SCM_OBSERVER_STRUCT(node);
if(!observer->weak_p || !is_zombie(observer->scheme, observer_guard))
{
/* mark the whole observer smob, scheme will be marked later by the
smob's mark fkt */
scm_gc_mark(node);
}
node = observer->link.right;
}
The problem is the function is_zombie() which iterates over all
all zombies until the right one has been found.
The following would be better:
register_gc_callback_for(observer->scheme, remove_observer_smob)
This registers the finit() function 'remove_observer_smob' for the
object observer->scheme. The garbage collector must call this
function after scheme has been garbage collected.
All I need is a simple notification that "this object has been garbage
collected".
Jost