- Rust 99%
- Nix 1%
| book | ||
| examples | ||
| lib | ||
| src | ||
| tests | ||
| .envrc | ||
| .gitignore | ||
| book.toml | ||
| Cargo.lock | ||
| Cargo.toml | ||
| flake.lock | ||
| flake.nix | ||
| LICENSE | ||
| README.md | ||
narju 🐱
narju gismu - x₁ is orange [color] in shade x₂ [medium red-yellow].
The reference implementations of this family of collapsible-tower languages are named Pink and Black. Following that tradition, narju takes its name from the Lojban word for orange - after a handsome orange cat. 🐱
A multi-stage Lisp and collapsible tower of interpreters - an implementation of the language of Nada Amin and Tiark Rompf, Collapsing Towers of Interpreters (POPL 2018, https://doi.org/10.1145/3158140), following the reference implementations in namin/pink and namin/lms-black. It may deviate from the references in places; where it does, the book and the source comments say so.
The system is three layers, only the first of which is Rust:
- the floor, λ↑↓ - a small Lisp with two staging operators,
liftandrun; evaluating a program that usesliftproduces a program, and there is no other compiler anywhere in the system; - Pink (
lib/pink-forms.naj) - a metacircular evaluator for λ↑↓ written stage-polymorphically in λ↑↓: an interpreter when run, a compiler when staged, through the third Futamura projection; - Purple (
lib/tower.naj,lib/purple.naj) - an interactive session on a reflective tower of such evaluators, withEMto rebind the running interpreter andclambdato compile against it.
Running
$ nix run git+https://git.avery.garden/thorn/narju # or: cargo run --release
The default invocation boots the Purple session. The nix-built binary
carries its lib/*.naj libraries with it (NARJU_LIB is baked in);
when running from source, start in the repository root so the boot
finds them by relative path. A taste:
> (define fib (lambda (n) (if (eq? n 0) 1 (if (eq? n 1) 1 (+ (fib (- n 1)) (fib (- n 2)))))))
> (fib 10)
89
> (EM (define counter 0))
'counter
> (EM (set! eval-var (lambda (e r k) (begin (set! counter (+ counter 1)) (eval-var e r k)))))
narju --raw starts the plain λ↑↓ REPL instead. narju --load file.naj
boots the Purple session and runs a .naj file through the tower -
the scripting mode for programs that use define, EM, clambda, and
load. Output comes from explicit print calls; paths in the file
resolve against the working directory first, so a project's own
libraries take precedence over $NARJU_LIB. narju --help lists the rest.
The book
The guide - from no Lisp at all, through staging and Pink, to the
tower - lives in book/ and builds with mdBook and a custom
preprocessor that executes every example against the real
interpreter at build time; a broken example is a broken build.
$ nix build .#book # rendered book in ./result
$ nix build .#docs # rustdoc for the floor crate
Without nix: cargo build --release --features mdbook, put
target/release on PATH, then mdbook build.
Development
$ nix develop # toolchain, rust-analyzer, mdbook, nil, schemat
$ cargo nextest run --all-features
$ nix flake check # tests, clippy, fmt, and the book
The flake also exports packages.{narju,mdbook-narju,docs,book},
apps for nix run, and overlays.default providing narju and
mdbook-narju.
License
MIT.