3 [![Build Status](https://travis-ci.org/kanaka/mal.svg?branch=master)](https://travis-ci.org/kanaka/mal)
7 **1. Mal is a Clojure inspired Lisp interpreter**
9 **2. Mal is implemented in 75 languages**
11 | Language | Creator |
12 | -------- | ------- |
13 | [Ada](#ada) | [Chris Moore](https://github.com/zmower) |
14 | [GNU Awk](#gnu-awk) | [Miutsuru Kariya](https://github.com/kariya-mitsuru) |
15 | [Bash 4](#bash-4) | [Joel Martin](https://github.com/kanaka) |
16 | [BASIC](#basic-c64-and-qbasic) (C64 & QBasic) | [Joel Martin](https://github.com/kanaka) |
17 | [C](#c) | [Joel Martin](https://github.com/kanaka) |
18 | [C++](#c-1) | [Stephen Thirlwall](https://github.com/sdt) |
19 | [C#](#c-2) | [Joel Martin](https://github.com/kanaka) |
20 | [ChucK](#chuck) | [Vasilij Schneidermann](https://github.com/wasamasa) |
21 | [Clojure](#clojure) (Clojure & ClojureScript) | [Joel Martin](https://github.com/kanaka) |
22 | [CoffeeScript](#coffeescript) | [Joel Martin](https://github.com/kanaka) |
23 | [Common Lisp](#common-lisp) | [Iqbal Ansari](https://github.com/iqbalansari) |
24 | [Crystal](#crystal) | [Linda_pp](https://github.com/rhysd) |
25 | [D](#d) | [Dov Murik](https://github.com/dubek) |
26 | [Dart](#dart) | [Harry Terkelsen](https://github.com/hterkelsen) |
27 | [Elixir](#elixir) | [Martin Ek](https://github.com/ekmartin) |
28 | [Elm](#elm) | [Jos van Bakel](https://github.com/c0deaddict) |
29 | [Emacs Lisp](#emacs-lisp) | [Vasilij Schneidermann](https://github.com/wasamasa) |
30 | [Erlang](#erlang) | [Nathan Fiedler](https://github.com/nlfiedler) |
31 | [ES6](#es6-ecmascript-2015) (ECMAScript 2015) | [Joel Martin](https://github.com/kanaka) |
32 | [F#](#f) | [Peter Stephens](https://github.com/pstephens) |
33 | [Factor](#factor) | [Jordan Lewis](https://github.com/jordanlewis) |
34 | [Fantom](#fantom) | [Dov Murik](https://github.com/dubek) |
35 | [Forth](#forth) | [Chris Houser](https://github.com/chouser) |
36 | [GNU Guile](#gnu-guile-21) | [Mu Lei](https://github.com/NalaGinrut) |
37 | [GNU Smalltalk](#gnu-smalltalk) | [Vasilij Schneidermann](https://github.com/wasamasa) |
38 | [Go](#go) | [Joel Martin](https://github.com/kanaka) |
39 | [Groovy](#groovy) | [Joel Martin](https://github.com/kanaka) |
40 | [Haskell](#haskell) | [Joel Martin](https://github.com/kanaka) |
41 | [Haxe](#haxe-neko-python-c-and-javascript) (Neko, Python, C++, & JS) | [Joel Martin](https://github.com/kanaka) |
42 | [Hy](#hy) | [Joel Martin](https://github.com/kanaka) |
43 | [Io](#io) | [Dov Murik](https://github.com/dubek) |
44 | [Java](#java-17) | [Joel Martin](https://github.com/kanaka) |
45 | [JavaScript](#javascriptnode) ([Demo](http://kanaka.github.io/mal)) | [Joel Martin](https://github.com/kanaka) |
46 | [Julia](#julia) | [Joel Martin](https://github.com/kanaka) |
47 | [Kotlin](#kotlin) | [Javier Fernandez-Ivern](https://github.com/ivern) |
48 | [LiveScript](#livescript) | [Jos van Bakel](https://github.com/c0deaddict) |
49 | [Logo](#logo) | [Dov Murik](https://github.com/dubek) |
50 | [Lua](#lua) | [Joel Martin](https://github.com/kanaka) |
51 | [GNU Make](#gnu-make-381) | [Joel Martin](https://github.com/kanaka) |
52 | [mal itself](#mal) | [Joel Martin](https://github.com/kanaka) |
53 | [MATLAB](#matlab-gnu-octave-and-matlab) (GNU Octave & MATLAB) | [Joel Martin](https://github.com/kanaka) |
54 | [miniMAL](#minimal) ([Repo](https://github.com/kanaka/miniMAL), [Demo](https://kanaka.github.io/miniMAL/)) | [Joel Martin](https://github.com/kanaka) |
55 | [NASM](#nasm) | [Ben Dudson](https://github.com/bendudson) |
56 | [Nim](#nim-0170) | [Dennis Felsing](https://github.com/def-) |
57 | [Object Pascal](#object-pascal) | [Joel Martin](https://github.com/kanaka) |
58 | [Objective C](#objective-c) | [Joel Martin](https://github.com/kanaka) |
59 | [OCaml](#ocaml-4010) | [Chris Houser](https://github.com/chouser) |
60 | [Perl](#perl-58) | [Joel Martin](https://github.com/kanaka) |
61 | [Perl 6](#perl-6) | [Hinrik Örn Sigurðsson](https://github.com/hinrik) |
62 | [PHP](#php-53) | [Joel Martin](https://github.com/kanaka) |
63 | [Picolisp](#picolisp) | [Vasilij Schneidermann](https://github.com/wasamasa) |
64 | [PL/pgSQL](#plpgsql-postgres-sql-procedural-language) (Postgres) | [Joel Martin](https://github.com/kanaka) |
65 | [PL/SQL](#plsql-oracle-sql-procedural-language) (Oracle) | [Joel Martin](https://github.com/kanaka) |
66 | [PostScript](#postscript-level-23) | [Joel Martin](https://github.com/kanaka) |
67 | [PowerShell](#powershell) | [Joel Martin](https://github.com/kanaka) |
68 | [Python](#python-2x-and-3x) (2.X & 3.X) | [Joel Martin](https://github.com/kanaka) |
69 | [RPython](#rpython) | [Joel Martin](https://github.com/kanaka) |
70 | [R](#r) | [Joel Martin](https://github.com/kanaka) |
71 | [Racket](#racket-53) | [Joel Martin](https://github.com/kanaka) |
72 | [Rexx](#rexx) | [Dov Murik](https://github.com/dubek) |
73 | [Ruby](#ruby-19) | [Joel Martin](https://github.com/kanaka) |
74 | [Rust](#rust-100-nightly) | [Joel Martin](https://github.com/kanaka) |
75 | [Scala](#scala) | [Joel Martin](https://github.com/kanaka) |
76 | [Scheme (R7RS)](#scheme-r7rs) | [Vasilij Schneidermann](https://github.com/wasamasa) |
77 | [Skew](#skew) | [Dov Murik](https://github.com/dubek) |
78 | [Swift 2](#swift) | [Keith Rollin](https://github.com/keith-rollin) |
79 | [Swift 3](#swift-3) | [Joel Martin](https://github.com/kanaka) |
80 | [Swift 4](#swift-4) | [陆遥](https://github.com/LispLY) |
81 | [Tcl](#tcl-86) | [Dov Murik](https://github.com/dubek) |
82 | [TypeScript](#typescript) | [Masahiro Wakame](https://github.com/vvakame) |
83 | [VHDL](#vhdl) | [Dov Murik](https://github.com/dubek) |
84 | [Vimscript](#vimscript) | [Dov Murik](https://github.com/dubek) |
85 | [Visual Basic.NET](#visual-basicnet) | [Joel Martin](https://github.com/kanaka) |
86 | [WebAssembly](#webassembly-wasm) (wasm) | [Joel Martin](https://github.com/kanaka) |
87 | [Yorick](#yorick) | [Dov Murik](https://github.com/dubek) |
90 **3. Mal is a learning tool**
92 Each implementation of mal is separated into
93 11 incremental, self-contained (and testable) steps that demonstrate
94 core concepts of Lisp. The last step is capable of self-hosting
95 (running the mal implementation of mal). See the [make-a-lisp process
96 guide](process/guide.md).
98 The make-a-lisp steps are:
100 * [step0_repl](process/guide.md#step0)
101 * [step1_read_print](process/guide.md#step1)
102 * [step2_eval](process/guide.md#step2)
103 * [step3_env](process/guide.md#step3)
104 * [step4_if_fn_do](process/guide.md#step4)
105 * [step5_tco](process/guide.md#step5)
106 * [step6_file](process/guide.md#step6)
107 * [step7_quote](process/guide.md#step7)
108 * [step8_macros](process/guide.md#step8)
109 * [step9_try](process/guide.md#step9)
110 * [stepA_mal](process/guide.md#stepA)
112 Each make-a-lisp step has an associated architectural diagram. That elements
113 that are new for that step are highlighted in red.
114 Here is the final diagram for [step A](process/guide.md#stepA):
116 ![stepA_mal architecture](process/stepA_mal.png)
118 If you are interesting in creating a mal implementation (or just
119 interested in using mal for something), please drop by the #mal
120 channel on freenode. In addition to the [make-a-lisp process
121 guide](process/guide.md) there is also a [mal/make-a-lisp
122 FAQ](docs/FAQ.md) where I attempt to answer some common questions.
127 Mal was presented publicly for the first time in a lightning talk at
128 Clojure West 2014 (unfortunately there is no video). See
129 examples/clojurewest2014.mal for the presentation that was given at the
130 conference (yes, the presentation is a mal program).
132 At Midwest.io 2015, Joel Martin gave a presentation on Mal titled
133 "Achievement Unlocked: A Better Path to Language Learning".
134 [Video](https://www.youtube.com/watch?v=lgyOAiRtZGw),
135 [Slides](http://kanaka.github.io/midwest.io.mal/).
137 More recently Joel gave a presentation on "Make Your Own Lisp Interpreter
138 in 10 Incremental Steps" at LambdaConf 2016:
139 [Part 1](https://www.youtube.com/watch?v=jVhupfthTEk),
140 [Part 2](https://www.youtube.com/watch?v=X5OQBMGpaTU),
141 [Part 3](https://www.youtube.com/watch?v=6mARZzGgX4U),
142 [Part 4](https://www.youtube.com/watch?v=dCO1SYR5kDU),
143 [Slides](http://kanaka.github.io/lambdaconf/).
145 ## Building/running implementations
147 The simplest way to run any given implementation is to use docker.
148 Every implementation has a docker image pre-built with language
149 dependencies installed. You can launch the REPL using a convenient
150 target in the top level Makefile (where IMPL is the implementation
151 directory name and stepX is the step to run):
154 make DOCKERIZE=1 "repl^IMPL^stepX"
155 # OR stepA is the default step:
156 make DOCKERIZE=1 "repl^IMPL"
162 The Ada implementation was developed with GNAT 4.9 on debian. It also
163 compiles unchanged on windows if you have windows versions of git,
164 GNAT and (optionally) make. There are no external dependencies
165 (readline not implemented).
175 The GNU awk implementation of mal has been tested with GNU awk 4.1.1.
179 gawk -O -f stepX_YYY.awk
189 ### BASIC (C64 and QBasic)
191 The BASIC implementation uses a preprocessor that can generate BASIC
192 code that is compatible with both C64 BASIC (CBM v2) and QBasic. The
193 C64 mode has been tested with
194 [cbmbasic](https://github.com/kanaka/cbmbasic) (the patched version is
195 currently required to fix issues with line input) and the QBasic mode
196 has been tested with [qb64](http://www.qb64.net/).
198 Generate C64 code and run it using cbmbasic:
206 Generate QBasic code and load it into qb64:
210 make MODE=qbasic stepX_YYY.bas
214 Thanks to [Steven Syrek](https://github.com/sjsyrek) for the original
215 inspiration for this implementation.
220 The C implementation of mal requires the following libraries (lib and
221 header packages): glib, libffi6, libgc, and either the libedit or GNU readline
232 The C++ implementation of mal requires g++-4.9 or clang++-3.5 and
233 a readline compatible library to build. See the `cpp/README.md` for
247 The C# implementation of mal has been tested on Linux using the Mono
248 C# compiler (mcs) and the Mono runtime (version 2.10.8.1). Both are
249 required to build and run the C# implementation.
259 The ChucK implementation has been tested with ChucK 1.3.5.2.
268 For the most part the Clojure implementation requires Clojure 1.5,
269 however, to pass all tests, Clojure 1.8.0-RC4 is required.
273 lein with-profile +stepX trampoline run
279 sudo npm install -g coffee-script
286 The implementation has been tested with SBCL, CCL, CMUCL, GNU CLISP, ECL and
287 Allegro CL on Ubuntu 16.04 and Ubuntu 12.04, see
288 the [README](common-lisp/README.org) for more details. Provided you have the
289 dependencies mentioned installed, do the following to run the implementation
299 The Crystal implementation of mal has been tested with Crystal 0.26.1.
303 crystal run ./stepX_YYY.cr
305 make # needed to run tests
311 The D implementation of mal was tested with GDC 4.8. It requires the GNU
322 The Dart implementation has been tested with Dart 1.20.
331 The Emacs Lisp implementation of mal has been tested with Emacs 24.3
332 and 24.5. While there is very basic readline editing (`<backspace>`
333 and `C-d` work, `C-c` cancels the process), it is recommended to use
338 emacs -Q --batch --load stepX_YYY.el
339 # with full readline support
340 rlwrap emacs -Q --batch --load stepX_YYY.el
345 The Elixir implementation of mal has been tested with Elixir 1.0.5.
350 # Or with readline/line editing functionality:
356 The Elm implementation of mal has been tested with Elm 0.18.0
366 The Erlang implementation of mal requires [Erlang/OTP R17](http://www.erlang.org/download.html)
367 and [rebar](https://github.com/rebar/rebar) to build.
373 MAL_STEP=stepX_YYY rebar compile escriptize # build individual step
377 ### ES6 (ECMAScript 2015)
379 The ES6 / ECMAScript 2015 implementation uses the
380 [babel](https://babeljs.io) compiler to generate ES5 compatible
381 JavaScript. The generated code has been tested with Node 0.12.4.
386 node build/stepX_YYY.js
392 The F# implementation of mal has been tested on Linux using the Mono
393 F# compiler (fsharpc) and the Mono runtime (version 3.12.1). The mono C#
394 compiler (mcs) is also necessary to compile the readline dependency. All are
395 required to build and run the F# implementation.
405 The Factor implementation of mal has been tested with Factor 0.97
406 ([factorcode.org](http://factorcode.org)).
410 FACTOR_ROOTS=. factor -run=stepX_YYY
415 The Fantom implementation of mal has been tested with Fantom 1.0.70.
419 make lib/fan/stepX_YYY.pod
434 guile -L ./ stepX_YYY.scm
439 The Smalltalk implementation of mal has been tested with GNU Smalltalk 3.2.91.
448 The Go implementation of mal requires that go is installed on on the
449 path. The implementation has been tested with Go 1.3.1.
460 The Groovy implementation of mal requires Groovy to run and has been
461 tested with Groovy 1.8.6.
466 groovy ./stepX_YYY.groovy
471 The Haskell implementation requires the ghc compiler version 7.10.1 or
472 later and also the Haskell parsec and readline (or editline) packages.
480 ### Haxe (Neko, Python, C++ and JavaScript)
482 The Haxe implementation of mal requires Haxe version 3.2 to compile.
483 Four different Haxe targets are supported: Neko, Python, C++, and
493 python3 ./stepX_YYY.py
504 The Hy implementation of mal has been tested with Hy 0.13.0.
513 The Io implementation of mal has been tested with Io version 20110905.
522 The Java implementation of mal requires maven2 to build.
527 mvn -quiet exec:java -Dexec.mainClass=mal.stepX_YYY
529 mvn -quiet exec:java -Dexec.mainClass=mal.stepX_YYY -Dexec.args="CMDLINE_ARGS"
542 The Julia implementation of mal requires Julia 0.4.
551 The Kotlin implementation of mal has been tested with Kotlin 1.0.
556 java -jar stepX_YYY.jar
561 The LiveScript implementation of mal has been tested with LiveScript 1.5.
566 node_modules/.bin/lsc stepX_YYY.ls
571 The Logo implementation of mal has been tested with UCBLogo 6.0.
580 The Lua implementation of mal has been tested with Lua 5.2. The
581 implementation requires that luarocks and the lua-rex-pcre library
586 make # to build and link linenoise.so
592 Running the mal implementation of mal involves running stepA of one of
593 the other implementations and passing the mal step to run as a command
598 IMPL_STEPA_CMD ../mal/stepX_YYY.mal
611 The NASM implementation of mal is written for x86-64 Linux, and has been tested
612 with Linux 3.16.0-4-amd64 and NASM version 2.11.05.
622 The Nim implementation of mal has been tested with Nim 0.17.0.
634 The Object Pascal implementation of mal has been built and tested on
635 Linux using the Free Pascal compiler version 2.6.2 and 2.6.4.
645 The Objective C implementation of mal has been built and tested on
646 Linux using clang/LLVM 3.6. It has also been built and tested on OS
663 ### MATLAB (GNU Octave and MATLAB)
665 The MatLab implementation has been tested with GNU Octave 4.2.1.
666 It has also been tested with MATLAB version R2014a on Linux. Note that
667 MATLAB is a commercial product.
672 octave -q --no-gui --no-history --eval "stepX_YYY();quit;"
673 matlab -nodisplay -nosplash -nodesktop -nojvm -r "stepX_YYY();quit;"
674 # OR with command line arguments
675 octave -q --no-gui --no-history --eval "stepX_YYY('arg1','arg2');quit;"
676 matlab -nodisplay -nosplash -nodesktop -nojvm -r "stepX_YYY('arg1','arg2');quit;"
681 [miniMAL](https://github.com/kanaka/miniMAL) is small Lisp interpreter
682 implemented in less than 1024 bytes of JavaScript. To run the miniMAL
683 implementation of mal you need to download/install the miniMAL
684 interpreter (which requires Node.js).
687 # Download miniMAL and dependencies
689 export PATH=`pwd`/node_modules/minimal-lisp/:$PATH
690 # Now run mal implementation in miniMAL
696 For readline line editing support, install Term::ReadLine::Perl or
697 Term::ReadLine::Gnu from CPAN.
706 The Perl 6 implementation was tested on Rakudo Perl 6 2016.04.
715 The PHP implementation of mal requires the php command line interface
725 The Picolisp implementation requires libreadline and Picolisp 3.1.11
733 ### PL/pgSQL (Postgres SQL Procedural Language)
735 The PL/pgSQL implementation of mal requires a running Postgres server
736 (the "kanaka/mal-test-plpgsql" docker image automatically starts
737 a Postgres server). The implementation connects to the Postgres server
738 and create a database named "mal" to store tables and stored
739 procedures. The wrapper script uses the psql command to connect to the
740 server and defaults to the user "postgres" but this can be overridden
741 with the PSQL_USER environment variable. A password can be specified
742 using the PGPASSWORD environment variable. The implementation has been
743 tested with Postgres 9.4.
747 ./wrap.sh stepX_YYY.sql
749 PSQL_USER=myuser PGPASSWORD=mypass ./wrap.sh stepX_YYY.sql
752 ### PL/SQL (Oracle SQL Procedural Language)
754 The PL/pgSQL implementation of mal requires a running Oracle DB
755 server (the "kanaka/mal-test-plsql" docker image automatically
756 starts an Oracle Express server). The implementation connects to the
757 Oracle server to create types, tables and stored procedures. The
758 default SQL*Plus logon value (username/password@connect_identifier) is
759 "system/oracle" but this can be overridden with the ORACLE_LOGON
760 environment variable. The implementation has been tested with Oracle
761 Express Edition 11g Release 2. Note that any SQL*Plus connection
762 warnings (user password expiration, etc) will interfere with the
763 ability of the wrapper script to communicate with the DB.
767 ./wrap.sh stepX_YYY.sql
769 ORACLE_LOGON=myuser/mypass@ORCL ./wrap.sh stepX_YYY.sql
772 ### Postscript Level 2/3
774 The Postscript implementation of mal requires ghostscript to run. It
775 has been tested with ghostscript 9.10.
779 gs -q -dNODISPLAY -I./ stepX_YYY.ps
784 The PowerShell implementation of mal requires the PowerShell script
785 language. It has been tested with PowerShell 6.0.0 Alpha 9 on Linux.
789 powershell ./stepX_YYY.ps1
792 ### Python (2.X and 3.X)
801 You must have [rpython](https://rpython.readthedocs.org/) on your path
802 (included with [pypy](https://bitbucket.org/pypy/pypy/)).
806 make # this takes a very long time
812 The R implementation of mal requires R (r-base-core) to run.
816 make libs # to download and build rdyncall
822 The Racket implementation of mal requires the Racket
823 compiler/interpreter to run.
832 The Rexx implementation of mal has been tested with Regina Rexx 3.6.
837 rexx -a ./stepX_YYY.rexxpp
847 ### Rust (1.0.0 nightly)
849 The rust implementation of mal requires the rust compiler and build
850 tool (cargo) to build.
854 cargo run --release --bin stepX_YYY
859 Install scala and sbt (http://www.scala-sbt.org/0.13/tutorial/Installing-sbt-on-Linux.html):
863 sbt 'run-main stepX_YYY'
866 scala -classpath target/scala*/classes stepX_YYY
869 ### Scheme (R7RS) ###
871 The Scheme implementation of mal has been tested with Chibi-Scheme
872 0.7.3, Kawa 2.4, Gauche 0.9.5, CHICKEN 4.11.0, Sagittarius 0.8.3,
873 Cyclone 0.6.3 (Git version) and Foment 0.4 (Git version). You should
874 be able to get it running on other conforming R7RS implementations
875 after figuring out how libraries are loaded and adjusting the
876 `Makefile` and `run` script accordingly.
882 scheme_MODE=chibi ./run
885 scheme_MODE=kawa ./run
887 scheme_MODE=gauche ./run
890 scheme_MODE=chicken ./run
892 scheme_MODE=sagittarius ./run
895 scheme_MODE=cyclone ./run
897 scheme_MODE=foment ./run
902 The Skew implementation of mal has been tested with Skew 0.7.42.
913 The Swift implementation of mal requires the Swift 2.0 compiler (XCode
914 7.0) to build. Older versions will not work due to changes in the
915 language and standard library.
925 The Swift 3 implementation of mal requires the Swift 3.0 compiler. It
926 has been tested with Swift 3 Preview 3.
936 The Swift 4 implementation of mal requires the Swift 4.0 compiler. It
937 has been tested with Swift 4.2.3 release.
947 The Tcl implementation of mal requires Tcl 8.6 to run. For readline line
948 editing support, install tclreadline.
952 tclsh ./stepX_YYY.tcl
957 The TypeScript implementation of mal requires the TypeScript 2.2 compiler.
958 It has been tested with Node.js v6.
968 The VHDL implementation of mal has been tested with GHDL 0.29.
973 ./run_vhdl.sh ./stepX_YYY
978 The Vimscript implementation of mal requires Vim 8.0 to run.
982 ./run_vimscript.sh ./stepX_YYY.vim
985 ### Visual Basic.NET ###
987 The VB.NET implementation of mal has been tested on Linux using the Mono
988 VB compiler (vbnc) and the Mono runtime (version 2.10.8.1). Both are
989 required to build and run the VB.NET implementation.
997 ### WebAssembly (wasm) ###
999 The WebAssembly implementation is written in
1000 [Wam](https://github.com/kanaka/wam) (WebAssembly Macro language) and
1001 runs under the [wac/wace](https://github.com/kanaka/wac) WebAssembly
1007 wace ./stepX_YYY.wasm
1012 The Yorick implementation of mal was tested on Yorick 2.2.04.
1016 yorick -batch ./stepX_YYY.i
1023 The top level Makefile has a number of useful targets to assist with
1024 implementation development and testing. The `help` target provides
1025 a list of the targets and options:
1031 ### Functional tests
1033 The are over 600 generic functional tests (for all implementations)
1034 in the `tests/` directory. Each step has a corresponding test file
1035 containing tests specific to that step. The `runtest.py` test harness
1036 launches a Mal step implementation and then feeds the tests one at
1037 a time to the implementation and compares the output/return value to
1038 the expected output/return value.
1040 * To run all the tests across all implementations (be prepared to wait):
1046 * To run all tests against a single implementation:
1056 * To run tests for a single step against all implementations:
1066 * To run tests for a specific step against a single implementation:
1069 make "test^IMPL^stepX"
1072 make "test^ruby^step3"
1073 make "test^ps^step4"
1076 ### Self-hosted functional tests
1078 * To run the functional tests in self-hosted mode, you specify `mal`
1079 as the test implementation and use the `MAL_IMPL` make variable
1080 to change the underlying host language (default is JavaScript):
1082 make MAL_IMPL=IMPL "test^mal^step2"
1085 make "test^mal^step2" # js is default
1086 make MAL_IMPL=ruby "test^mal^step2"
1087 make MAL_IMPL=python "test^mal^step2"
1090 ### Starting the REPL
1092 * To start the REPL of an implementation in a specific step:
1095 make "repl^IMPL^stepX"
1098 make "repl^ruby^step3"
1099 make "repl^ps^step4"
1102 * If you omit the step, then `stepA` is used:
1112 * To start the REPL of the self-hosted implementation, specify `mal` as the
1113 REPL implementation and use the `MAL_IMPL` make variable to change the
1114 underlying host language (default is JavaScript):
1116 make MAL_IMPL=IMPL "repl^mal^stepX"
1119 make "repl^mal^step2" # js is default
1120 make MAL_IMPL=ruby "repl^mal^step2"
1121 make MAL_IMPL=python "repl^mal"
1124 ### Performance tests
1126 Warning: These performance tests are neither statistically valid nor
1127 comprehensive; runtime performance is a not a primary goal of mal. If
1128 you draw any serious conclusions from these performance tests, then
1129 please contact me about some amazing oceanfront property in Kansas
1130 that I'm willing to sell you for cheap.
1132 * To run performance tests against a single implementation:
1140 * To run performance tests against all implementations:
1145 ### Generating language statistics
1147 * To report line and byte statistics for a single implementation:
1155 * To report line and bytes statistics for general Lisp code (env, core
1158 make "stats-lisp^IMPL"
1161 make "stats-lisp^js"
1164 ## Dockerized testing
1166 Every implementation directory contains a Dockerfile to create
1167 a docker image containing all the dependencies for that
1168 implementation. In addition, the top-level Makefile contains support
1169 for running the tests target (and perf, stats, repl, etc) within
1170 a docker container for that implementation by passing *"DOCKERIZE=1"*
1171 on the make command line. For example:
1174 make DOCKERIZE=1 "test^js^step3"
1177 Existing implementations already have docker images built and pushed
1178 to the docker registry. However, if
1179 you wish to build or rebuild a docker image locally, the toplevel
1180 Makefile provides a rule for building docker images:
1183 make "docker-build^IMPL"
1188 * Docker images are named *"kanaka/mal-test-IMPL"*
1189 * JVM-based language implementations (Groovy, Java, Clojure, Scala):
1190 you will probably need to run this command once manually
1191 first `make DOCKERIZE=1 "repl^IMPL"` before you can run tests because
1192 runtime dependencies need to be downloaded to avoid the tests timing
1193 out. These dependencies are downloaded to dot-files in the /mal
1194 directory so they will persist between runs.
1197 ## External Implementations
1199 The following implementations are maintained as separate projects:
1203 * [by Alexander Bagnalla](https://github.com/bagnalla/holyc_mal)
1207 * [by Tim Morgan](https://github.com/seven1m/mal-rust)
1208 * [by vi](https://github.com/vi/mal-rust-vi) - using [Pest](https://pest.rs/) grammar, not using typical Mal infrastructure (cargo-ized steps and built-in converted tests).
1211 ## Other mal Projects
1213 * [malc](https://github.com/dubek/malc) - Mal (Make A Lisp) compiler. Compiles a Mal program to LLVM assembly language, then binary.
1214 * [malcc](https://git.sr.ht/~tim/malcc) (@seven1m) - malcc is an incremental compiler implementation for the Mal language. It uses the Tiny C Compiler as the compiler backend and has full support for the Mal language, including macros, tail-call elimination, and even run-time eval. ["I Built a Lisp Compiler"](https://mpov.timmorgan.org/i-built-a-lisp-compiler/) post about the process.
1215 * [frock](https://github.com/chr15m/frock) - Clojure-flavoured PHP. Uses mal/php to run programs.
1219 Mal (make-a-lisp) is licensed under the MPL 2.0 (Mozilla Public
1220 License 2.0). See LICENSE.txt for more details.