Extending the language using Racket, defining helper functions with macros

I am stuck with a problem for several hours. I am trying to define DSL using the extension features of the Racket language. I want to do something like the following pseudocode. Ultimately, I would like to generate functions and macros based on input in DSL, and most of them seem to work now, the problem is to provide definitions that should work at the same level as declarations. Is it possible? It's late, and I'm sure I'm missing something truly trivial. The simplest example of a problem:

tinylang.rkt:

#lang racket ; here we redefine module begin. (provide (all-defined-out) (except-out (all-from-out racket) #%module-begin) (rename-out [module-begin #%module-begin]) ) (define-syntax (module-begin stx) (syntax-case stx () [(_ stmts ...) #`(#%module-begin (define (hello) (print "Yes!") (newline)) ; (provide (for-syntax hello)) (print "Function defined.") stmts ... )])) 

Now I'm trying to use this new language elsewhere:

try.rkt:

 #lang s-exp "tinylang.rkt" (hello) 

But when I load the second module, I get the error message "hello: unbound identifier in module in: hello".

+4
source share
1 answer

The problem is that hello is defined in the lexical scope of tinylang.rkt , but you want it to be in the scope of try.rkt . You can use datum->syntax to set the lexical context of a piece of syntax.

This will fix the problem:

 #lang racket ; here we redefine module begin. (provide (all-defined-out) (except-out (all-from-out racket) #%module-begin) (rename-out [module-begin #%module-begin]) ) (define-syntax (module-begin stx) (syntax-case stx () [(_ stmts ...) #`(#%module-begin #,(datum->syntax stx (syntax->datum #'(define (hello) (print "Yes!") (newline)))) (print "Function defined.") stmts ... )])) 

UPDATE:

In response to comments, the previous solution can be simplified:

 (define-syntax (module-begin stx) (syntax-case stx () [(_ stmts ...) (with-syntax ([hello-fn (datum->syntax stx 'hello)]) #`(#%module-begin (define (hello-fn) (print "Yes!") (newline)) (print "Function defined.") stmts ... ))])) 
+5
source

Source: https://habr.com/ru/post/1502465/


All Articles