perplexed by macro-expansion behavior near #%module-begin

30 views
Skip to first unread message

Matthew Butterick

unread,
Jan 13, 2020, 3:18:13 PM1/13/20
to Racket Users
Below, the two modules `test1` and `test2` use the same expander `exp` and otherwise differ only in the presence of the string "foo" as the second datum in `test2`.

The syntax objects passed to #%module-begin are more different than that, however: the syntax passed to the first is

#'(#%module-begin 'mac-result)

wheras the second gets:

#'(#%module-begin (mac 42) "foo")

Thus my question: why is `mac` getting expanded at different times based on the presence of "foo"?


;;;
#lang racket

(module exp racket
(provide #%datum mac (rename-out [mb #%module-begin]))

(define-syntax-rule (mac x) 'mac-result)

(define-syntax (mb stx)
(println (syntax->datum stx))
(syntax-case stx ()
[(_ . EXPRS)
#'(#%module-begin . EXPRS)])) )

(module test1 (submod ".." exp)
(mac 42))
(require 'test1)
;; '(#%module-begin 'mac-result)

(module test2 (submod ".." exp)
(mac 42) "foo")
(require 'test2)
;; '(#%module-begin (mac 42) "foo")

Michael MacLeod

unread,
Jan 13, 2020, 4:02:53 PM1/13/20
to Matthew Butterick, Racket Users
I believe this due to an edge case of 'module': when there is only one form provided, it is partially expanded to determine if its expansion would lead to a #%plain-module-begin form. Otherwise (more than one form provided) they are wrapped in #%module-begin with no partial expansion occurring.


If a single form is provided, then it is partially expanded in a module-begin context. If the expansion leads to #%plain-module-begin, then the body of the #%plain-module-begin is the body of the module. If partial expansion leads to any other primitive form, then the form is wrapped with #%module-begin using the lexical context of the module body; this identifier must be bound by the initial module-path import, and its expansion must produce a #%plain-module-begin to supply the module body. Finally, if multiple forms are provided, they are wrapped with #%module-begin, as in the case where a single form does not expand to #%plain-module-begin.

--
You received this message because you are subscribed to the Google Groups "Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to racket-users...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/racket-users/C0F76736-B28C-4F64-A1AA-D2B2EFD34BF8%40mbtype.com.
Reply all
Reply to author
Forward
0 new messages