Roc rewrites the compiler in Zig

Motivation for the Rewrite (Rust → Zig)

  • Central reason cited is compile-time performance: Rust compile times are experienced as a major friction point, especially for a large (~300k LOC) organically grown codebase.
  • Commenters note any Rust→Zig compiler speed comparison will be inherently “unfair” because the rewrite will also remove technical debt and redesign architecture.
  • Some argue Rust’s slow compiles come from many features and high codegen quality; others say compile times aren’t proportional to safety gains in their projects.
  • Rust contributors point out that Rust has always cared about compile times, but language features (e.g. borrow checking) and ecosystem choices (macros, serde) make further improvements hard.

Why Zig (and Not OCaml, Go, or Roc Itself)

  • Zig is seen as in the “C/C++/Rust/Zig tier” of systems languages, with potential for very fast generated code and low-level control.
  • OCaml is praised for fast compiles and good compiler-writing features, but multiple comments emphasize ultimate compiler performance (the compiled Roc code) over compiler-writer convenience.
  • Go is rejected as unsuitable for parsers, interop, and low-level control; its runtime is considered too “black box.”
  • Roc explicitly does not plan to self-host: it targets “fast for a GC’d, high-level, memory-safe language,” not the “as-fast-as-possible systems compiler” niche. Using Roc for the compiler would sacrifice that performance goal.

Parser Strategy: Combinators vs Recursive Descent

  • Current Rust parser uses parser combinators; the team wants to move to a hand-written recursive descent parser in Zig.
  • Supporters say combinators are fine for small DSLs but hurt readability, error-reporting control, and contributor approachability in a large production compiler.
  • Others note most combinator libraries are still recursive descent under the hood and think some localized hand-written pieces might have sufficed.

Zig’s Maturity, Safety, and Tooling

  • Concerns raised about betting on a pre-1.0 language with known bugs and breaking changes; defenders reply they can pin Zig versions and have a close relationship with the Zig team.
  • Debate over Zig’s “unsafe” status: some worry about using it for security-sensitive infrastructure; others reply only the compiled Roc programs must be safe, and compiler memory bugs are comparatively tolerable.
  • Experiences with Zig compile times are mixed: some see it as “blazingly fast” vs Rust, others report slow first builds and note missing incremental compilation and linker support.

Roc Language Design Reactions

  • Discussion branches into Roc’s philosophy: simple but expressive types (with generics and “abilities” instead of typeclasses), no implicit currying, and focus on friendliness.
  • The recent syntax change from \args -> to |args| for lambdas (to avoid confusion with a new type-level arrow feature) is divisive: some see it as more approachable; others feel it abandons a clean, Haskell/Elm-style aesthetic.
  • Point-free style and currying debates surface: several argue point-free encourages unreadable “write-only” code; others think avoiding currying is pandering to least-common-denominator familiarity.

Dogfooding and Trust Signals

  • A few commenters lose interest when a language’s compiler isn’t written in that language, seeing it as a lack of confidence.
  • Others counter that dogfooding can happen outside the compiler, and optimizing the compiler for a different design space than the language itself is reasonable.

Broader Language-Wars Context

  • The thread becomes a proxy debate: Rust vs Zig vs Go vs OCaml vs Odin, etc., with recurring themes of complexity vs simplicity, memory safety vs control, ABI stability, and culture.
  • Some are enthusiastic about Zig’s “pragmatic C replacement” vibe and powerful comptime; others question its usefulness relative to plain C and criticize its slow march to 1.0.