NORTHTEK Labs · Research

Kryos: A Capability-Safe Systems Language for Trustworthy Software

An open-source compiled language where a program's authority to touch the outside world is part of its type signature, checked by the compiler before the program ever runs.

What I built

Kryos is a compiled, general-purpose programming language built around one idea I kept coming back to: a program's authority to do things, like reading a file, opening a socket, or spawning a process, should show up in its type signature and get checked by the compiler, not discovered at runtime after something's already gone wrong.

Here's the plain English version, for anyone who isn't a programmer. If you ask an AI agent to write and run code against your systems, you want a guarantee that the code can't quietly do something you never authorized, even if the agent, or some library it pulled in, tries to. Kryos calls this capability typing. A function that only needs to compute a hash can't secretly read a file or call out to the network. The compiler throws the program out before it ever runs.

For an engineer, here's the fuller picture: Kryos is a memory-safe, garbage-collector-free language with a complete toolchain (compiler, formatter, LSP, debug info, package manager), written in Rust, self-hosted in its own source, and shipped with three backends: a fast Cranelift path for the development loop, an LLVM path for optimized release binaries, and a WebAssembly path for the browser, WASI, and edge sandboxes.

As AI agents take on more real actions, filesystem writes, API calls, spending money, the language a system is written in becomes part of the trust boundary. My bet with Kryos is that this boundary belongs at compile time, not buried in a code review someone might skim.

What it does, and why it's different

Capability enforcement is compile time, not convention

Every function can declare @capabilities(...) for the authority it needs, io, net, process, whatever, or @pure for none at all. The compiler tracks that declaration through the entire call graph: direct calls, method dispatch, even a builtin function passed around as a value, and it throws a compile error (E05xx) the moment a function reaches for authority it never declared. There are three enforcement modes: permissive (you can opt out), inferred (deny-by-default, where the compiler figures out what your internal helper functions need on its own), and strict (--strict-capabilities, which I run against all 90 of the project's own example programs in CI). Deny-by-default is what you get out of the box: run a Kryos program with no flags and no project file, and it already rejects any undeclared authority. You declare what you need once, on main, and the compiler works out what every helper underneath it needs. Alongside capabilities, @budget refuses to run before it would overspend, and a Tracked<T> type carries where a value came from as part of its type.

The same governed program runs anywhere

A capability-checked binary compiles natively for Linux, macOS, and Windows, on both Intel and Apple Silicon. It also compiles to an explicit-subset WebAssembly target (scalars, strings, closures, host-import I/O; anything outside that subset fails to compile, it never silently miscompiles), and it can be loaded into Python, Go, Node, or C# hosts through a C ABI, carrying a machine-readable manifest that spells out exactly what it's allowed to do.

Memory safety without the complexity tax

Kryos uses automatic reference counting plus move semantics instead of Rust's borrow checker. You never write a lifetime annotation, and there's no garbage-collector pause to work around. It's a genuinely different, Swift-like trade: simpler to write than Rust, though it doesn't carry Rust's compile-time proof that your program is free of data races.

None of this is theoretical, and I didn't want to just claim it works. The toolchain is complete: 30+ CLI subcommands, a 15-capability language server, a formatter, REPL, debug info, and a package manager, backed by 66 standard library modules covering strings, collections, JSON, HTTP, regex, datetime, crypto, files, processes, and channels. The compiler is written in Kryos itself and self-hosts to a byte-identical fixed point: a self-host-compiled compiler recompiling its own source produces a bit-for-bit identical binary, verified by SHA-256. That's the compiler proving it can reproduce itself exactly, not me asserting it. On top of that, a differential fuzzer has run more than 14,000 randomly generated programs through both the JIT and the AOT compiler and found zero divergences between them. A separate mutation harness has thrown 1,168 deliberately broken programs at the compiler, and every single time, it produced a diagnostic, not a crash.

I also wanted the performance numbers to be honest, losses included, not cherry-picked. The table below is best of 10 runs on a sandbox VM with a roughly 30-millisecond subprocess-launch floor, so the very fast programs cluster near that floor and the real signal shows up in the slower workloads. Full methodology is in the repository's BENCHMARKS.md.

Benchmark Kryos (LLVM) Rust --release gcc -O3 Go Python
fib(35) 0.032 0.032 0.032 0.064 1.118
mandelbrot 0.032 0.032 0.032 0.032 0.716
nbody 0.032 0.008 0.008 0.016 0.817
binary_trees 0.008 0.003 0.001 0.003 0.064
fannkuch 0.114 0.016 0.016 0.008 0.466
matmul 0.064 0.032 0.032 0.032 2.976

Seconds, lower is better.

Kryos matches Rust and gcc on simple loops, recursion, and floating-point arithmetic. It still trails the C and Rust frontier on tight inner loops that lean on aggressive loop unrolling and bounds-check elision (fannkuch, nbody, and matmul). I'm reporting those as losses, not hiding them in a footnote.

Every package in the Kryos ecosystem, the compiler itself, all 90 shipped examples, and the self-host compiler, is deny-by-default. My own ecosystem check enforces this in continuous integration (259 of 259 passing), and a bare kryos run with no flags refuses undeclared authority right out of the box. Repo: github.com/NORTHTEKDevs/kryos-lang.

Why this might matter

There are two ways to read this, and I think both are worth holding onto at once.

The conservative read: Kryos today is a real, complete toolchain. A fast compiled language with a working package manager, language server, and editor extensions, self-hosting with cryptographically verified reproducibility, and benchmarked honestly against Rust, C, Go, and Python. That alone is useful if you want Go-like ergonomics with native performance and don't want to take on Rust's learning curve.

The more ambitious read is about AI-written and AI-run code specifically, which is honestly the reason I built this. As agents get handed more real actions, filesystem writes, network calls, spending money, the question stops being whether the model meant well and becomes whether the system can prove what a piece of code is and isn't allowed to do, before it ever runs. Kryos's capability system is my compile-time answer to that question: authority is part of the type signature, deny-by-default is what you get out of the box, and the same governed binary can run natively, inside a browser sandbox, or embedded in a Python or Node host with a machine-readable manifest of what it can touch.

The honest version sits between the two: a working, self-verifying toolchain today, and a plausible foundation for trustworthy agent tooling if the idea keeps holding up once it's out in the world, not just inside its own repo.

What it isn't

Trust matters more than hype, so here's what Kryos isn't, and what I'm not claiming yet:

How it works, in plain English

You write code that looks close to Go or Python: structs, enums, pattern matching, closures, channels. There's no lifetime syntax to learn. The compiler manages memory automatically through reference counting and move semantics, so values get freed deterministically and there's no garbage-collector pause to tune around.

Authority works the same way types do everywhere else in the language. A function that needs to touch the filesystem or the network says so, right in its signature. The compiler follows every path that function can be reached from and refuses to compile the program if that authority was never declared. You don't have to trust that some library behaves itself. The compiler checks it for you.

The same source builds three different ways, depending on what you need: a fast Cranelift build to iterate locally, an optimized LLVM build to ship, or a WebAssembly build to run inside a browser or a sandboxed host.

The compiler's claims about itself are checked, not just asserted. Before a release, the self-hosting compiler has to reproduce itself bit-for-bit, and a differential fuzzer cross-checks the Cranelift and LLVM backends against each other on thousands of randomly generated programs, so the two backends can't quietly disagree with each other.

See the code

Kryos is Apache 2.0 licensed and public on GitHub. Current status: v1.0.0-rc.2, feature-complete beta, one primary author, still me, not yet externally stress-tested. Clone it, run kryos doctor and kryos welcome, and read STABILITY.md before you build on the frozen 1.x surface.

Where to go deeper

If you want more than this page, here's where I'd point you:

Come see for yourself

The full repo is on GitHub. Clone it, read STABILITY.md, and run the self-host bootstrap yourself if you don't want to just take my word for the SHA-256 claim.

github.com/NORTHTEKDevs/kryos-lang →

Built by Kristian Baer / Northtek. Apache 2.0 licensed. Status and versioning in STABILITY.md and VERSIONING.md.