On Sun, Jan 5, 2014 at 11:33 PM, William ML Leslie <
[email protected]> wrote:


> Well, the question is, how should I do /this/ in bitc? Do I not do it?
>

I'm not sure that /this/ is actually helpful in BitC. I suspect it depends
on whether adopting private/public is motivated. In the absence of
inheritance, /this/ really has no special properties at all. The procedures
that initialize the ifTable of a given interface are free to name the
parameter corresponding to the existentially encapsulated reference
whatever they wish - formal parameter names aren't part of the procedure
signature.

That said, the weight of prevailing usage and convention is a very powerful
thing. $100 says that if programmers are free to choose that parameter
name, the majority of those parameters will, in practice, be named "this".


> The "immediately cast to an interface" pattern for example is pretty
> common.  I often want to store collections of some interface, in
> particular.
>

Indeed. And that's part of why I was so careful about wording the lifespan
rule to be "an interface may not outlive the thing that it references". In
the kind of pattern you are talking about, the object tends to be heap
allocated. Either that or we know something about it's region. In either
case we can rely on GC and there is no problem storing the interface in the
collection. And in either case we can rely on region typing to tell us when
we have done something wrong in this regard.


> > It's a violation of the NoHeap effect, so it would show up as a type
> error.
> > In practice, this should only occur with interfaces to objects of
> reference
> > type, which are themselves already heap allocated. If so, there are
> > pre-existing noheap violations.
>
> But the problematic case is where an interface captures a value that
> it outlives.  It seems to me that you are suggesting that this case
> is:
>
> * I have a value V which I cast to an interface W
> * Region analysis infers r(W) > r(V), so the interface outlives the value
> * Static allocation pass rewrites V to be heap-allocated
> * NoHeap check detects violation
>
> I can't be /sure/ that you mean this, but it sounds a bit magical to
> me.  I would probably be really confused as to /why/ V was heap
> allocated.  I want more information.
>

Not quite. First, it's not a cast, because interface creation is
construction. But the rest is correct. If region analysis concludes r(W) >
r(V) and no corrective rewrite is possible, then that's an error and you
cannot instantiate the interface. And yes, if the "fix" forces the object
into the general heap, and you're doing all this under a noheap
restriction, you have written a program whose collective type requirements
cannot be simultaneously satisfied. Compilation should and must
(statically) fail.

I agree strongly that useful diagnostics for errors resulting from
unification (as in inference) can be very hard to track. This is something
that Swaroop, at my strong insistence, put some real thought into. If I get
a noheap rejection, I should certainly be told what ended up in the heap
that broke my requirements. If I didn't put it there by saying "new", I
should be told the region derivation and unification chain.

But my personal opinion is that this should not fail by putting V in the
heap. I think it should fail by reporting that r(W) > r(V), and telling the
programmer that (a) placing V in the general heap, or (b) more carefully
specifying the region containing V is the right solution.

Hmm. Maybe that's too strong. It seems pretty clear that the compiler
shouldn't go magically moving things into the heap when we are under a
noheap constraint. The more problematic case is when the effect type is
parametric. In that case, from a local partial typing perspective, we may
or may not end up under a noheap constraint. The problem in this case is
that moving an object into the heap "fixes" the noheap constraint to
!noheap, where we may really need to be able to instantiate either way.

So in the end I think this is a case where the compiler should tell me the
problem and let me decide what to do about it, and consider it a
compile-time error.

But it's interesting that the reverse argument is different. If V is
already in some heap-allocated region, then there is no reasonable
objection to placing W in a (temporally) "smaller" heap-allocated region
automatically. It's only when the magic fix *increases* the lifetime of an
object that we should diagnose rather than repair.

Sometimes, magic is not your friend. :-)


> And really, I think this condition is more accurately described by the
> region system.  "V may outlive W, but references it."


I think you mean "... described as a diagnostic ..." if so, that fits my
intuitions as well.


shap
_______________________________________________
bitc-dev mailing list
[email protected]
http://www.coyotos.org/mailman/listinfo/bitc-dev

Reply via email to