· via dev.to (home feed)
Chuks v0.2.0-rc.1 asks developers to break its dual bytecode and native modes
Chuks v0.2.0-rc.1 is out, and its team wants developers to run real programs through both the bytecode VM and the native compiler and report any divergence.

Chuks, a language that compiles to both a bytecode virtual machine and native binaries, has shipped v0.2.0-rc.1 — and the release post is framed less as a feature announcement than as a request: take real programs, run them through both execution paths, and report any case where the results diverge.
The ask
According to the announcement on dev.to, every Chuks release depends on the two compilation modes computing the same result. The project's internal gate already runs golden tests on both backends, a differential fuzzer, 24 differential suites and cross-compilation to five targets. What that machinery cannot do, the post notes, is execute a program it has never seen. So the team is asking developers to build something with the release candidate — or point an existing program at it — and run it both ways:
chuks run main.chuks # the bytecode VM chuks build main.chuks # the native binary
If the two modes do not produce exactly the same printed output, that is a bug the team wants filed, along with the output of chuks --version and the smallest file that reproduces it.
Two bugs that explain the gap
The post describes two recently fixed defects, both found by building real programs rather than by automated tests.
The first was a grammar-level precedence bug affecting await and spawn. An expression like "[" + await f() + "]" used to parse so that await applied to the concatenation rather than the call. Because the flaw sat in the parser rather than in either backend, the two modes produced two different wrong results: the VM printed "Task(pending)" while the native binary printed "0". The team's fuzzer generates programs, the post explains, but does not yet imitate a developer hand-writing an async pipeline, which is how this one surfaced.
The second bug is the more instructive one. Closures created inside a loop all read one shared binding instead of a per-iteration value, so every function returned 3 — on both backends, identically. Differential testing can confirm that the VM and the native binary agree; it cannot confirm that what they agree on is correct. The post compares the failure to var in JavaScript before let introduced per-iteration bindings, and says the fix gives each loop pass its own binding. Shared bugs of this kind are exactly what only an outsider with expectations about real behavior can catch.
Also in the release candidate
- String indexing now counts bytes consistently on both backends, with accessors such as at and slice snapping to whole Unicode characters; previously some methods counted characters on the VM and bytes on the native side.
- A dropped spawn'd task whose failure used to disappear silently is now reported — at exit for a CLI program, immediately for an embedding host.
- Reserved words can now be used as record field and key names, so a payload's fields no longer have to be renamed to satisfy the language.
- Generic base classes now work correctly across module boundaries, and reflection through .stringify(this) sees the whole object, subclass fields included, identically on both backends.
The full changelog, including all breaking changes and migration notes, is published on the Chuks blog.
How to try it
Getting the candidate is opt-in. Existing users can run chuks upgrade --prerelease; new installs go through the project's install script followed by the same upgrade command. A plain chuks upgrade keeps users on v0.1.2 until the final v0.2.0 actually ships.
Why it matters
Chuks's dual-backend design turns every program into a consistency check, but the release post is candid about the limits of that strategy: matching outputs from two backends proves consistency, not correctness, because a bug baked into shared front-end logic can fool both. That admission — and the explicit invitation to break the release candidate on real workloads — is a useful template for any project that validates one implementation against another. For anyone evaluating young languages, it also signals a team that knows where its blind spots are and is actively recruiting users to find them. The divergences filed against rc.1 will directly shape whether v0.2.0 is fit to ship.
- #programming-language
- #release-candidate
- #compiler
- #bytecode
- #differential-testing