Skip to main content
  1. Projects/

Z-Lisp Programming Language

C Lisp MPC Parser WebAssembly
Table of Contents
AzzamAlsharafi/Z-Lisp

A Lisp-like programming language.

C
0
0

Try it out!

A Lisp-like programming language interpreter written in C, following Build Your Own Lisp and extended with additional features, including WebAssembly support for in-browser execution.

Overview
#

Z-Lisp is an interpreted Lisp-like programming language born from following the Build Your Own Lisp book, then extended with additional features and capabilities. The interpreter is implemented in C for performance and portability, with WebAssembly compilation support enabling execution directly in web browsers.

The language features a simple yet powerful syntax based on S-expressions, supporting fundamental data types including numbers, strings, symbols, lists, and functions. Built-in operators cover arithmetic operations, list manipulation, variable definition, control flow, and functions.

Features
#

  • S-expression syntax - Expressions use parentheses (), Lists use curly braces {}
  • Dynamic typing - Supports integers, floats, strings, lists, and functions
  • Function definitions - Anonymous functions with fun and variable binding with def
  • Built-in operations - Arithmetic, comparison, logical, and list manipulation functions
  • Control flow - Conditional statements with if and local variable binding with =
  • File loading - Load and execute Z-Lisp code from files using load
  • REPL environment - Interactive development and testing
  • WebAssembly support - Compiled with Emscripten for in-browser execution

Try It Live
#

Experience Z-Lisp directly in your browser with the interactive terminal:

Interactive Z-Lisp interpreter running in your browser via WebAssembly.

Language Syntax
#

Basic Components
#

Z-Lisp syntax follows simple rules:

42                           ; Numbers - integers and floats
3.14159                      ; Floating point numbers
"Hello, World!"              ; Strings - enclosed in double quotes
x                            ; Symbols - names for variables and functions
{1 2 3 4 5}                  ; Lists - use curly braces, not evaluated
(+ 1 2 3)                    ; Expressions - use parentheses, evaluated
(fun {x} {* x x})            ; Anonymous function definition
; This is a comment          ; Comments - anything after ; is ignored

Basic Operations
#

(+ 10 20 30)                 ; => 60.0 - Arithmetic addition
(- 100 25)                   ; => 75.0 - Subtraction
(* 5 5 5)                    ; => 125.0 - Multiplication
(/ 100 4)                    ; => 25.0 - Division
(% 7 3)                      ; => 1.0 - Modulo
(^ 2 3)                      ; => 8.0 - Power
(> 10 5)                     ; => 1 (true) - Greater than
(< 3 7)                      ; => 1 (true) - Less than
(== 5 5)                     ; => 1 (true) - Equality
(&& 1 0)                     ; => 0 (false) - Logical AND
(|| 0 1)                     ; => 1 (true) - Logical OR
(! 0)                        ; => 1 (true) - Logical NOT

Variables and Functions
#

(def {x name} 10 "Z-Lisp")        ; Define variables globally
(= {y} 20)                        ; Define local variables
(fun {x} {* x x})                 ; Define anonymous functions
(def {square} (fun {x} {* x x}))  ; Define named functions
(def {factorial} (fun {n} {if (== n 0) {1} {* n (factorial (- n 1))}}))  ; Recursive function
(square 5)                        ; => 25.0 - Use functions
(factorial 5)                     ; => 120.0 - Call factorial

Control Flow
#

(if (> x 0) {print "positive"} {print "non-positive"})     ; Conditional expressions
(= {x y} 10 20)              ; Local variable bindings
(+ x y)                      ; => 30.0 - Use local variables
(env)                        ; Returns current environment

List Operations
#

(def {nums} {1 2 3 4 5})     ; Create lists
(list 1 2 3 4 5)             ; Creates {1 2 3 4 5}
(get nums 0)                 ; => 1 (get element at index)
(remove nums 0)              ; => {2 3 4 5} (remove element at index)
(len nums)                   ; => 5 (list length)
(+ {1 2} {3 4})              ; => {1 2 3 4} - List concatenation
(+ nums 6)                   ; => {1 2 3 4 5 6} - Add element to list
(+ "Hello " "World")         ; => "Hello World" - String concatenation

Built-in Functions
#

Z-Lisp provides a comprehensive set of built-in functions covering arithmetic, list manipulation, control flow, and I/O operations:

FunctionDescriptionExample
+Addition (numbers), concatenation (strings/lists)(+ 1 2 3)6.0
-Subtraction or negation(- 10 3)7.0
*Multiplication(* 2 3 4)24.0
/Division(/ 10 2)5.0
%Modulo(% 7 3)1.0
^Power(^ 2 3)8.0
>Greater than(> 5 3)1
<Less than(< 3 5)1
==Equality(== 5 5)1
&&Logical AND(&& 1 1)1
||Logical OR(|| 0 1)1
!Logical NOT(! 0)1
listCreate list(list 1 2 3){1 2 3}
getGet element by index(get {a b c} 1)b
removeRemove element by index(remove {a b c} 1){a c}
lenList length(len {1 2 3})3
defDefine global variables(def {x} 10)
=Define local variables(= {y} 20)
funDefine anonymous function(fun {x} {* x x})
ifConditional expression(if (> x 0) {"pos"} {"neg"})
evalEvaluate list as expression(eval {+ 1 2})3.0
loadLoad and execute file(load "script.zl")
printPrint to console(print "Hello")
errorPrint error message(error "Oops!")
exitExit program(exit())
envShow current environment(env())
typeofGet type as string(typeof 42)"Integer"
stringConvert to string(string 42)"42"
intConvert to integer(int "42")42
floatConvert to float(float "3.14")3.14

Implementation Details
#

Architecture
#

The Z-Lisp interpreter is built in C using the MPC (Micro Parser Combinators) library for parsing. The architecture follows a classic interpreter design:

  1. Lexical Analysis - Tokenizes input into meaningful symbols
  2. Parsing - Grammar-based parsing using MPC combinators
  3. AST Evaluation - Tree-walking interpreter with environment-based scoping
  4. Memory Management - Manual memory management with proper cleanup

WebAssembly Compilation
#

The interpreter compiles to WebAssembly using Emscripten, enabling:

  • Browser execution - Run Z-Lisp directly in web browsers
  • Portability - No server dependencies required
  • Interactive REPL - Full REPL functionality preserved in browser environment

Building from Source
#

Native Build
#

# Clone the repository
git clone https://github.com/AzzamAlsharafi/Z-Lisp.git
cd Z-Lisp

# Build the interpreter
make

# Run the REPL
./zlisp

# Run a Z-Lisp file
./zlisp program.zsp

WebAssembly Build
#

# Install Emscripten
git clone https://github.com/emscripten-core/emsdk.git
cd emsdk
./emsdk install latest
./emsdk activate latest
source ./emsdk_env.sh

# Build WASM module
cd /path/to/Z-Lisp
make wasm

# Generated files: main.js, main.wasm, main.data

Example Programs
#

Fibonacci Sequence
#

(def {fib} (fun {n} {if (< n 2) {n} {+ (fib (- n 1)) (fib (- n 2))}}))   ; Define fibonacci function
(fib 0)                          ; => 0.0
(fib 1)                          ; => 1.0
(fib 5)                          ; => 5.0
(fib 10)                         ; => 55.0

Factorial Function
#

(def {factorial} (fun {n} {if (== n 0) {1} {* n (factorial (- n 1))}}))  ; Define factorial function
(factorial 5)                    ; => 120.0
(factorial 0)                    ; => 1.0

List Processing
#

(def {numbers} {1 2 3 4 5})      ; Define a list of numbers
(get numbers 0)                  ; => 1 - Get first element
(get numbers 2)                  ; => 3 - Get third element
(len numbers)                    ; => 5 - List length
(+ numbers 6)                    ; => {1 2 3 4 5 6} - Add element
(+ {0} numbers)                  ; => {0 1 2 3 4 5} - Prepend element
(remove numbers 0)               ; => {2 3 4 5} - Remove first element