guile-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Special variables to relax boxing


From: Stefan Israelsson Tampe
Subject: Re: Special variables to relax boxing
Date: Sat, 23 Mar 2013 16:34:03 +0100

Ok, I have felt your punches against the idea and have thought about it
somewhat more.

1. I can only conclude that today it's already difficult to reason about code
with respect to multiple restarts of continuation and the main reason is that
at least I have been sloppy to add a ! to the macros that use set! internally.

To a fun example:

I have been pondering to poer common-lisp iterate for fun to learn and enjoy
guile. In there they have generators e.g. (generati i ...) and then take out the
values with (next i) construct. For a simple i = 1 ... one would expand next i
to (begin (set! i (+ i 1)) i). So next is really next!. So this will
not mix well with
undo and redo. It's possible to define i as a special variable though
and you will
get the feature of proper undo redo support but now another problem appears
we will as Mark and Daniel introduce i into any uses of next i in user
and can get
hard to reason about properties when the value is put into a lambda. So next
is not next or next! but what? maybe next~ To indicate that lambdas that include
this must expect to mutate when one does a redo!. Conventions like this is
problematic because coders will most certainly be sloppy to follow
this convention
resulting in a mess. One really long for a type system to help clarify
the matters here.

Typically macro writers that post a binding a, might want users to use
the underlying
a~, variable as well and it would probably be good practice to let
users refer to this
at will e.g. reference it with (~ a), set it with (set~ a 1) as well
as (set! a 1) and refer
to it with e.g. a just as ordinary scheme. I would suggest that both
reference a variable
with set!,a, and with set~, (~ a) should be an error. Otherwise if the
macro writer
manages the macro  correct and basically uses a user guard that we
should provide
e.g. (with-user (a) user-code ...) especially this means that if a is
set! ed then we know
that redo undo cannot work and we will force the underlying variable
to be a usual
variable.

To accomplish this I would formulate the semantics as follows.

Consider
* k, the r5rs continuation
* dynamic-wind, r5rs dynamic wind with the addition that k is an argument
  to the rewinder.

Introduce (with-special ((a:id kind:object) ...) code ...) and (set~
a:id v:obj)

Let self identifying the dynamic wind object lexically

Introduce
(special-set! self k value)
(special-ref self k)

Also define
(guard-special? k kind)
A setter and a getter of an object indexed by self and k

Then the semantic for with-special in guard mode would be

(let ((last #f))
  (dynamic-wind
     (lambda (k)
        (when (guard-special? k kind)
            (set! a (special-ref self k))))
     (lambda ()
        (call-with-values (lambda () (begin code ...))
           (lambda ret
              (set! last #t)
              (apply values ret))))
     (lambda (k . l)
        (unless last
            (special-set! self k a))))

Guard mode is entered only if a is referenced with set~ and never with
set! if it can be proved
Otherwise guard mode is never entered. The semantics of set~ is the
same as with set! otherwise.

if with-special is not in guard-mode then it behaves just as (let ()  code ....)

I really hope that I mange to converge a good concept with this discussion!

WDYT










On Thu, Mar 21, 2013 at 8:03 PM, Mark H Weaver <address@hidden> wrote:
> Stefan, you're still describing your proposal in terms of low-level
> implementation details such as stacks.  In the general case, we cannot
> store environment structures on the stack.  Furthermore, in the general
> case *all* variables in scheme are bound to locations, not values.  Only
> in special cases can we use stacks, and only in special cases can we
> avoid boxing variables.  These are only _optimizations_.
>
> If you're serious about this proposal, please read sections 3.1 and 3.4
> of the R5RS carefully.  Explain your proposed _semantics_ (not the
> implementation details) in those terms, where *all* variables are bound
> to _locations_, and where there is no stack at all (everything is
> conceptually stored in a garbage-collected heap).
>
> We need to understand the *semantics* in the simplest possible terms
> before we even begin to think about how to implement it.
>
>     Thanks,
>       Mark



reply via email to

[Prev in Thread] Current Thread [Next in Thread]