From: Leopold Toetsch <[EMAIL PROTECTED]>
Date: Sun, 24 Apr 2005 09:25:43 +0200
Nicholas Clark <[EMAIL PROTECTED]> wrote:
> In effect morph has to be friends of both A and B, because it needs to
break
> encapsulation?
Yep. The same is true for C<assign_pmc>, which additionally to C<morph>,
gets the value from A and sets it on B . . .
But there is more weirdness:
A = new Env
morph A, .Integer # error "Parrot VM: Can't modify a singleton"
or
assign B, A # error "Parrot VM: Can't turn to a singleton type!"
IMHO, it's only going to get worse. In order to complete the repertoire
of arithmetic types, Common Lisp needs a LispRatio (being the ratio of
two integers, either of which could be a BigInt) and a LispComplex
(where the real and imaginary parts could be any real number,
i.e. integer, ratio, or float). The easiest thing would be a "boxed"
approach, where the subcomponents are themselves PMCs -- I hope to start
work on something like this (before I get much older).
The necessity for C<morph> and C<assign> is basically due to the (now
almost gone) inability to create new values in unary and infix
operations. *But* there is the problem with Perl references, which seems
to create a need for such a behavior.
$a = 4;
$b = \$a;
$a = 41;
++$$b;
print $a; # 42
It probably just depends on the implementation of Perl5 references.
> Nicholas Clark
leo
Hmm. I'm probably missing something (it wouldn't be a first), but if
the reference points to $a itself rather than the PMC to which $a
refers, then you could implement this without morphing, at the cost of
an extra indirection for each Perl deref. This assumes a ScalarRef PMC
class, that knows that it's pointing to a scalar variable, for GC
marking.
But, without PMC morphing, referencing the middle of an array is more
problematic:
my @b = (1, 2, 3);
my $c = \$b[1];
$$c *= 4;
# prints "1 8 3\n".
print(join(' ', @b), "\n");
To make this work, $c would need to contain a pointer (i.e. a reference
PMC) into the middle of @b, which could be trickier for GC.
The concept reminds me of "locative pointers" in the old Lisp
Machines; the feature was not considered for the ANSI language because
it was thought too expensive for conventional architectures. But a
LispM locative was merely a tagged pointer, so you had to have a
reliable way to mark an arbitrary object given only a pointer into the
middle of it, which in turn required scanning backward through memory
for the object header. Parrot's unconventional architecture and
non-copying GC make this significantly easier. If the ref PMC also has
a pointer to the header of the containing object, then GC marking is
trivial.
You may be way ahead of me here, but I am beginning to think that a
morph-free Parrot might be feasible. I am going out on a limb to
suggest all of this because, IMHO, it might make Parrot simpler and more
robust overall, and certainly ought to interoperate better between Perl
and non-Perl.
So, tell me, what have I missed?
-- Bob Rogers
http://rgrjr.dyndns.org/