These tests show the type of syntax definitions the Schemes in the suite understand. The following Schemes do not support syntax extension of any (known) kind, and are excluded below: NexJ, JScheme, KSi, Shoe, TinyScheme, BDC, XLisp, Schemik, UMB, Llava, FemtoLisp, Oaklisp, Inlab
Define-macro
is a low-level bare macro definition, analogous to Common Lisp defmacro
.
I tested (define-macro x (lambda (y) y))
followed by (x (+ 3 4))
,
expecting it to return 7 on Schemes that support define-macro
and an error otherwise.
Define-macro
is not part of any Scheme standard.
Supported: Gambit, Bigloo, Guile, Kawa, SISC, Ypsilon, SigScheme, S7[*], Scheme 9, STklos, RScheme, Rep, Elk, Dfsch[*], Picrin
Not supported: Racket, Gauche, MIT, Chicken, Scheme48/scsh, SCM, Chez, Vicare, Larceny, Mosh, IronScheme, SXM, Sagittarius, Foment, Owl Lisp, Chibi, Sizzle[*]
Supported as the only kind of macros: S7, RScheme, Rep, Elk, Dfsch
Supported as the only kind of low-level macros: Scheme 9
[*] S7 and Dfsch accept the define
-style syntax (define-macro (x y) y)
only.
The Sizzle documentation claims to do the same, but it didn't work for me.
Define-syntax
is a wrapper for any of the following syntax transformations.
Other such wrappers are let-syntax
, let*-syntax
, and letrec-syntax
,
which define local macros.
The following additional Schemes do not support define-syntax
and are excluded below:
SigScheme, S7, Rep, Elk, Sizzle, Dfsch.
RScheme accepts only a non-standard form of define-syntax
and is also excluded below.
Syntax-rules
is a syntax transformer used with define-syntax
and its relatives.
It was described but not standardized in R4RS;
with minor extensions, it is part of the R5RS, R6RS, and R7RS-small standards.
I tested (define-syntax x (syntax-rules () ((x y) y)))
,
which is essentially equivalent to the define-macro
macro used above, but with hygiene.
Supported: Racket, Gauche, MIT, Gambit (with the -:s
switch), Chicken, Bigloo,
Scheme48/scsh, Guile, Kawa, SISC, SCM (with the -r5 -m
switches),
Chez, Vicare, Larceny, Ypsilon, Mosh, IronScheme, STklos, Scheme 9,
SXM, Sagittarius, Foment, Picrin, Owl Lisp, Chibi, Loko
Not supported: (none)
Supported as the only kind of hygienic macros: Bigloo
Syntax-case
is a hybrid low/high-level macro system that is standardized in R6RS.
The test used here is (define-syntax x (lambda (x) (syntax-case x () ((x y) (syntax y)))))
,
which is exactly equivalent to the syntax-rules
macro used above.
Supported: Chibi (incomplete), Gambit, Kawa, SISC, SXM, and all R6RS implementations: Racket, Guile, Chez, Vicare, Larceny (SRFI 72, buggy), Ypsilon, Mosh, IronScheme, SXM, Sagittarius, Loko
Not supported: Gauche, MIT, Chicken, Bigloo, SCM, STklos, Scheme 9, Foment, Picrin, Owl Lisp
Supports both syntax-case
and another low-level hygienic macro system:
Larceny (ER), Sagittarius (ER), Chibi (SC)
Explicit renaming is a low-level macro system supported by Gauche, MIT, Chicken, Scheme48/scsh, Sagittarius, Picrin, Chibi, Larceny (with different syntax).
Supported as the only kind of low-level hygienic macros: Scheme48/scsh
Supported without syntax-case
support: Gauche, MIT, Chicken, Scheme48/scsh, Picrin
Implicit renaming is a low-level macro system supported by Chicken, Picrin.
Supported as the only kind of low-level hygienic macros: (none)
Syntactic closures is a low-level macro system supported by MIT, Picrin, Chibi.
Supported as the only kind of low-level hygienic macros: (none)
Identifier syntax specifies an identifier which macroexpands to an expression.
It can also specify the expansion of a set!
expression that specifies a
procedure call rather than a variable, such as (set! (car x) y)
.
The second version is equivalent to SRFI 17
Supported by all implementations that support syntax-case
, but no others.