[racket] Ready for the next phase - or how to shift the phase of a namespace
2014-07-20 1:19 GMT+02:00 Matthias Felleisen <matthias at ccs.neu.edu>:
>
> Can't you just put forms2 into a constructed module that requires the desired module at the phase where you want it? -- Matthias
That would be tricky. I am writing an interpreter that evaluates
Racket bytecode represented as zo-structures.
The main entry is:
; eval-zo : compilation-top [namespace] -> values(s)
(define (eval-zo zo [ns (make-start-namespace)])
(unless (compilation-top? zo)
(error 'eval-zo "expected a compilation-top, got ~a" zo))
; evaluation always occur within a top-level namespace
(parameterize ([current-namespace ns])
(eval-top zo)))
The structure of the interpreter is a straight forward recursive descent.
The "phase 0" forms and expressions are done and works fine.
I have also managed to evaluate the stxs part of the prefix.
The instruction I need shift-phase for is seq-for-syntax.
>From the docs on begin-for-syntax:
Evaluation of an expr within begin-for-syntax is parameterized to
set current-namespace as in let-syntax.
>From the docs on (let-syntax ([id trans-expr] ...) body ...+)
The evaluation of each trans-expr is parameterized to
set current-namespace to a namespace that shares
bindings and variables with the namespace being used to
expand the let-syntax form, except that its base phase is one greater.
Here is what I'd like to write:
(define (eval-form form globs stack closed stx-ht)
(match form
...
[(struct seq-for-syntax (forms prefix max-let-depth dummy))
; push the prefix
(define array (eval-prefix prefix stx-ht))
(define new-stack (mlist array stack))
; shift phase and evalate each form
(parameterize ([current-namespace (shift-phase (current-namespace) +1)])
(for ([form (in-list forms)])
(let-syntaxes ([() (begin (eval-form (car forms) globs
new-stack closed stx-ht)
(values))])
(void))))]
/Jens Axel
> On Jul 19, 2014, at 3:52 PM, Jens Axel Søgaard wrote:
>
>> I am looking for a way to change the base phase of a namespace.
>> Or perhaps to make a new namespace with the same mappings except a
>> shift in phases.
>> I hope I have missed a trick, but I couldn't find a
>> namespace-shift-phase in the docs.
>>
>> Consider the following program which defines a variable x to 0, 1, 2, and, 3
>> in phases 0, 1, 2, and, 3 respectively. It does so by evalunting the
>> forms in forms.
>>
>> Then it displays the values of x in phases 1 and 2 with the results 1 and 2.
>> It does so by evaluating the forms in forms2.
>>
>> I'd like to shift the base phase of the namespace (or make a copy with
>> new base phase),
>> so evaluating the forms in forms2 again will give results 2 and 3.
>>
>> #lang racket
>> (define (eval* forms [ns (current-namespace)])
>> (for ([form forms])
>> (displayln (~a "> " form))
>> (eval form ns)))
>>
>> (define forms '((module m0 racket (provide x) (define x 0))
>> (module m1 racket (provide x) (define x 1))
>> (module m2 racket (provide x) (define x 2))
>> (module m3 racket (provide x) (define x 3))
>> (require (for-meta 0 'm0))
>> (require (for-meta 1 'm1))
>> (require (for-meta 2 'm2))
>> (require (for-meta 3 'm3))))
>>
>> (define forms2 '(; display the value of x in phase 1
>> (define-syntaxes () (begin (displayln x) (values)))
>> ; display the value of x in phase 2
>> (define-syntaxes () (begin (let-syntaxes ([() (begin
>> (displayln x) (values))])
>> (void)) (values)))))
>>
>> (define ns (make-base-empty-namespace))
>> (parameterize ([current-namespace ns])
>> ; setup the namespace
>> (namespace-require '(for-meta 0 racket/base))
>> (namespace-require '(for-meta 1 racket/base))
>> (namespace-require '(for-meta 2 racket/base))
>> (namespace-require '(for-meta 3 racket/base))
>> ; declare and require the modules
>> (eval* forms)
>> ; display the value of x in phase 1 and 2
>> (eval* forms2) ; displays 1 and 2
>> ; (namespace-shift-phase ns +1) ; on the wish list
>> ; (eval* forms2) ; would display 2 and 3
>> )
>>
>> The output is:
>>
>>> (module m0 racket (provide x) (define x 0))
>>> (module m1 racket (provide x) (define x 1))
>>> (module m2 racket (provide x) (define x 2))
>>> (module m3 racket (provide x) (define x 3))
>>> (require (for-meta 0 (quote m0)))
>>> (require (for-meta 1 (quote m1)))
>>> (require (for-meta 2 (quote m2)))
>>> (require (for-meta 3 (quote m3)))
>>> (define-syntaxes () (begin (displayln x) (values)))
>> 1
>>> (define-syntaxes () (begin (let-syntaxes ((() (begin (displayln x) (values)))) (void)) (values)))
>> 2
>>
>> --
>> Jens Axel Søgaard
>>
>> ____________________
>> Racket Users list:
>> http://lists.racket-lang.org/users
>
--
--
Jens Axel Søgaard