On Tue, 2 Sep 2003, Leopold Toetsch wrote:
> Dan Sugalski <[EMAIL PROTECTED]> wrote:
> > On Tue, 2 Sep 2003, Leopold Toetsch wrote:
>
> >> So if it was mark()ed already we return. That's not possible for freeze,
> >> thaw, dump, clone whatever. These must keep track of already visited
> >> objects via an hash for freeze, dump, clone, and via an ID array for
> >> thaw.
>
> > No, this isn't necessary. What you need to do when freezing an already
> > frozen PMC is to emit a marker label that refers to the original version
> > of the PMC,
>
> So I have to do a lookup to get the marker, or...
Or nothing. Freezing a PMC that refers to one or more PMCs will have to
handle this.
> > ... or always emit the marker when a PMC freezes another PMC and
> > defer actual freezing of the PMC until the master freeze function walks
> > over the PMC to freeze it.
>
> on first freeze generate a maker (store it where in the PMC?) and
> then... When I defer freezing of the aggregate the thawing doesn't work.
> When everything gets defered, you have to walk the whole defered list
> again, for simple types too, which already would have been done. Then in
> another run, the marker has to get cleared.
Nope.
First off, the freeze and thaw code *must* deal with potentially
self-referential or circular data structures. They're depressingly common,
and to not be able to handle something as simple as:
$foo = \$foo;
freeze($foo);
would be a big problem. As would this:
$foo[0] = \$bar;
$foo[1] = \$bar;
freeze(@foo);
generating a structure that, when reconstituted, had elements 0 and 1
pointing to different PMCs. So with that in mind, handling labels and
deferred or already-instantiated PMCs is a necessity.
Doing the walk is *also* easy. You clear the next PMC pointer, just as
with a normal DOD run setup. call the DOD mark on the inital PMC, and call
its freeze routine. Inside the freeze for the PMC, it calls mark on any
PMCs it needs frozen, which will then go on the list if they've not
already been frozen. A marker for that PMC, probably based on the PMC
header address, goes in the frozen data structure. When the initial freeze
routine exits, the freeze code just follows the next for DOD pointer
chain, calling freeze on each of those PMCs, until it runs off the end of
the chain, just as the DOD does.
Now, granted, we won't use the DOD's intimate knowledge of base array/hash
types, rather deferring to their freeze routines, but that's fine and as
it should be.
Reconstituting these things may be somewhat problematic, but there's not
much for it--reconstituting circular data structures that require some
sort of active setup is problematic in general.
> *If* that works it still adds extra complexity to DOD.
It doesn't add anything to the DOD. Worst case it turns out that
disabling a DOD sweep during a freeze is untenable, which is possible. In
that case we'll need an alternate pointer chain.
Dan