A Lua 5.4 implementation in Rust. Currently an AST-walking interpreter built
on gc-arena; the long-term goal is to
experiment with JIT compilation while keeping high compatibility.
$ cargo run --release -- script.lua [args...]src/lexer.rs— hand-written lexer for the full 5.4 token set (long strings/comments, all escapes, int/float/hex/hex-float numerals, PUC-stylenear '...'error context). Also home toparse_number, the string-to-number coercion used bytonumberand arithmetic.src/ast.rs,src/parser.rs— recursive-descent parser doing single-pass scope resolution in the style of PUC's lparser.c: every variable reference is resolved at parse time to a frame slot, an upvalue index (threaded through enclosing functions), or a global; goto/label validity and<const>assignments are checked at parse time. String constants are deduplicated into a per-chunk string table.src/value.rs,src/table.rs— the object model.Valueis a small Copy enum over gc-arenaGcpointers; strings are immutable byte strings with precomputed hashes; tables have an array part plus an insertion-ordered hash part with Lua's key normalization (float keys with integer values collapse to integers;nextstays valid when fields are cleared during traversal).src/interp.rs— the tree-walking evaluator. Locals live in per- declaration heap cells (Gc<Lock<Value>>), so closures capture variables per loop iteration exactly like real Lua. Full 5.4 numeric semantics: integer/float subtypes, wrapping integer arithmetic, floor division/modulo, mathematically exact mixed int/float comparisons. Errors carrychunk:line:positions and PUC-style culprit info (local 'x',field 'y', ...).src/pattern.rs— a faithful port of lstrlib.c's pattern matcher over byte slices.src/stdlib/— base library (print,pairs,pcall,error,load, ...),string(patterns,formatincluding%q/%p),table,math(PUC's exact xoshiro256** PRNG),os,io, and minimaldebug/utf8stubs.
The interpreter recurses on the Rust stack, so luawa::run executes chunks
on a dedicated thread with a 1 GiB (lazily committed) stack; Lua call depth
is capped at 32k and raises a catchable stack overflow error.
Metatables (and metamethods), coroutines, _ENV, garbage-collector control
(collection runs implicitly; collectgarbage is a stub), weak tables and
finalizers, string.pack/string.dump, io file objects, and the utf8
library. getmetatable truthfully returns nil; setmetatable with a
non-nil metatable raises an error rather than silently misbehaving. String
values index the string library directly, so ("x"):rep(2) works without
a string metatable.
$ cargo test- Unit tests live with each module (lexer, parser, interpreter semantics, pattern matcher, every stdlib module).
tests/scripts/*.luaare our own assert-based feature tests, run by thelua_scriptsintegration test.tests/lua-5.4.8/vendors the official Lua 5.4.8 test suite. A curated subset runs as integration tests:vararg,code, andmathunmodified, andgoto,literals,pm,sort,constructs, andstringswith minimal, clearly marked-- [luawa]patches that disable only the sections needing unsupported features (metatables, coroutines,<close>,_ENVrebinding,string.pack,%ahex floats, string interning). Every patch site is greppable via the[luawa]marker.