"What if your ML model couldn't have bugs?"
We have a problem. A big one.
Machine learning models are being deployed in:
- Medical diagnosis - Wrong predictions can kill
- Autonomous vehicles - Wrong predictions can kill
- Financial systems - Wrong predictions can destroy lives
- Criminal justice - Wrong predictions can imprison innocents
And yet, our tools for building these systems are... inadequate.
# This is how we build AI systems that make life-or-death decisions
class MedicalAI(nn.Module):
def __init__(self):
self.conv1 = nn.Conv2d(3, 64, 3)
self.fc1 = nn.Linear(64 * 30 * 30, 10) # Probably right?
def forward(self, x):
x = self.conv1(x)
x = F.relu(x)
x = x.view(x.size(0), -1) # Reshape... hope this is correct
x = self.fc1(x) # RuntimeError after 3 hours of training
return F.softmax(x, dim=1)
# Did you catch the bug? There are actually 3.This is insane.
We would never accept this in aerospace. In nuclear power. In bridge construction.
Why do we accept it in AI?
What if ML frameworks worked like compilers?
Compilers catch bugs before your code runs. They verify types, check syntax, ensure consistency.
Axiom.jl brings this to machine learning:
@axiom MedicalAI begin
input :: Tensor{Float32, (224, 224, 3)}
output :: Probabilities(10)
features = input |> Conv(64, (3,3))
output = features |> Dense(10) # COMPILE ERROR!
# "Shape mismatch at Dense layer
# Expected input: Vector
# Got: Tensor{Float32, (222, 222, 64)}
#
# Solution: Add Flatten layer between Conv and Dense
#
# Would you like me to fix this? [y/N]"
endThe bug is caught immediately. Not after training. Not in production. Now.
# In Axiom.jl, the type system encodes tensor shapes
input :: Tensor{Float32, (batch, 28, 28, 1)}
# Shape errors are COMPILE errors
Dense(10)(input) # Error: Dense expects 2D, got 4D
# Correct code:
Flatten()(input) |> Dense(784, 10) # ✓ CompilesWhat this means: You can't run code with shape errors. Period.
@axiom Classifier begin
input :: Image
output :: Probabilities(10)
# ... layers ...
# @ensure adds runtime contracts; @prove attempts to discharge them statically
@ensure sum(output) ≈ 1.0
@ensure all(output .>= 0)
@prove ∀x. no_nan(output(x))
endWhat this means: @ensure attaches runtime contracts that are checked on every
forward pass; @prove attempts to discharge a property statically — via
known-pattern heuristics, or an SMT solver when SMTLib.jl is loaded — and honestly
returns :unknown when it cannot. It is not a blanket claim that every property is
formally proved.
# Development: Julia backend (fast iteration)
model = compile(MyModel, backend=JuliaBackend())
# Production: Zig backend (native SIMD kernels)
model = compile(MyModel, backend=ZigBackend("/path/to/libaxiom_zig.so"), optimize=:aggressive)
# Competitive with PyTorch on small/medium workloads — see benchmark/ for measured mediansWhat this means: verification guarantees without giving up competitive performance.
Python is dynamically typed. You can't encode shape constraints in the type system.
# This is valid Python - no way to prevent it
def broken(x):
return torch.matmul(x, torch.randn(999, 999)) # Probably wrong
# Only crashes at runtime, maybeSystems languages like Zig are great for native kernels. But ML research needs:
- REPL exploration - Try ideas instantly
- Interactive visualization - Plot results immediately
- Rapid iteration - Change code, see results
// Edit code
// Wait 30s-2min for compilation
// Run
// Find bug
// Repeat
// This is a flow killer for researchJulia for research:
julia> model = Sequential(Dense(10, 5), ReLU())
julia> model(randn(4, 10)) # Instant feedback
4×5 Matrix{Float32}:
0.0 0.123 0.0 0.456 0.789
...Zig for production:
# When you're done experimenting
production_model = compile(model, backend=ZigBackend("/path/to/libaxiom_zig.so"))
# Native SIMD kernels; competitive on small/medium ops (see benchmark/)Best of both worlds.
Axiom.jl provides multiple levels of verification:
# The compiler catches this
Conv(64, (3,3))(input_2d) # Error: Expected 4D input
# No code to write - it just works@axiom Model begin
# ...
@ensure sum(output) ≈ 1.0 # Checked at runtime
@ensure all(output .>= 0)
end@axiom Model begin
# ...
@prove ∀x. sum(softmax(x)) == 1.0 # discharged via @prove (known pattern; SMT when SMTLib.jl loaded)
@prove ∀x ε. (ε < δ) ⟹ stable(f(x), f(x+ε)) # Robustness
end# Generate proof certificate for regulatory approval
cert = generate_certificate(model, properties)
save_certificate(cert, "fda_submission.cert")- Catch bugs faster
- Iterate more quickly
- Publish reproducible results
- Deploy with confidence
- Debug production issues
- Meet performance requirements
- Medical AI (FDA approval)
- Autonomous vehicles (safety certification)
- Financial systems (regulatory compliance)
- Aerospace (DO-178C compliance)
- Core DSL and type system
- Basic verification (@ensure)
- Julia backend
- PyTorch import
- Full Rust backend
- GPU acceleration (CUDA, Metal)
- Distributed training
- ONNX export
- SMT solver integration
- Automated proof generation
- Robustness certification
- Fairness verification
- Model zoo (verified models)
- Hugging Face integration
- Cloud deployment
- Industry certifications
We're building the future of machine learning. A future where:
- Bugs are caught before they cause harm
- Models come with mathematical guarantees
- Safety and performance aren't trade-offs
- AI systems can be trusted
Want to help?
"The best way to predict the future is to invent it." — Alan Kay
Let's invent verified ML together.