A really nice explanation of lisp semantics, using userland code!
For example, you can define let in terms of let* and vice versa.
miniblog.
Related Posts
TIL Tcl has a notion of 'safe interpreters', a mode where you can run untrusted code in a sandbox: https://www.tcl.tk/man/tcl8.4/TclCmd/safe.htm
Not many programming languages have this, but it's way safer to include in the implementation than try to build as a userland library.
Every time I implement an interpreter with recursion, I regret it.
As soon as I want TCO, or userland control of stack limits, or resumable exceptions, I need my own stack.
This is awkward because it's an upfront design decision. Changing the stack model is a big refactoring.
Implementing Execute-Only Memory in userland: https://www.tedunangst.com/flak/post/userland-xnr-jit (an elegant way of hardening JITs to ROP exploits!)